From patchwork Fri Jul 17 14:33:38 2015 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: John Harrison X-Patchwork-Id: 6816611 Return-Path: X-Original-To: patchwork-intel-gfx@patchwork.kernel.org Delivered-To: patchwork-parsemail@patchwork2.web.kernel.org Received: from mail.kernel.org (mail.kernel.org [198.145.29.136]) by patchwork2.web.kernel.org (Postfix) with ESMTP id B15EDC05AC for ; Fri, 17 Jul 2015 14:34:42 +0000 (UTC) Received: from mail.kernel.org (localhost [127.0.0.1]) by mail.kernel.org (Postfix) with ESMTP id 7379A20670 for ; Fri, 17 Jul 2015 14:34:40 +0000 (UTC) Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) by mail.kernel.org (Postfix) with ESMTP id 1BA7D20687 for ; Fri, 17 Jul 2015 14:34:39 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id E6E026ED8E; Fri, 17 Jul 2015 07:34:36 -0700 (PDT) X-Original-To: Intel-GFX@lists.freedesktop.org Delivered-To: Intel-GFX@lists.freedesktop.org Received: from mga11.intel.com (mga11.intel.com [192.55.52.93]) by gabe.freedesktop.org (Postfix) with ESMTP id 2BEE56ED79 for ; Fri, 17 Jul 2015 07:34:25 -0700 (PDT) Received: from orsmga002.jf.intel.com ([10.7.209.21]) by fmsmga102.fm.intel.com with ESMTP; 17 Jul 2015 07:34:25 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.15,497,1432623600"; d="scan'208";a="766366877" Received: from johnharr-linux.isw.intel.com ([10.102.226.190]) by orsmga002.jf.intel.com with ESMTP; 17 Jul 2015 07:34:23 -0700 From: John.C.Harrison@Intel.com To: Intel-GFX@Lists.FreeDesktop.Org Date: Fri, 17 Jul 2015 15:33:38 +0100 Message-Id: <1437143628-6329-30-git-send-email-John.C.Harrison@Intel.com> X-Mailer: git-send-email 1.9.1 In-Reply-To: <1437143628-6329-1-git-send-email-John.C.Harrison@Intel.com> References: <1437143628-6329-1-git-send-email-John.C.Harrison@Intel.com> Organization: Intel Corporation (UK) Ltd. - Co. Reg. #1134945 - Pipers Way, Swindon SN3 1RJ Subject: [Intel-gfx] [RFC 29/39] drm/i915: Added trace points to scheduler X-BeenThere: intel-gfx@lists.freedesktop.org X-Mailman-Version: 2.1.18 Precedence: list List-Id: Intel graphics driver community testing & development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Errors-To: intel-gfx-bounces@lists.freedesktop.org Sender: "Intel-gfx" X-Spam-Status: No, score=-5.4 required=5.0 tests=BAYES_00, RCVD_IN_DNSWL_MED, RP_MATCHES_RCVD, UNPARSEABLE_RELAY autolearn=unavailable version=3.3.1 X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on mail.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: John Harrison Added trace points to the scheduler to track all the various events, node state transitions and other interesting things that occur. Change-Id: I9886390cfc7897bc1faf50a104bc651d8baed8a5 For: VIZ-1587 Signed-off-by: John Harrison --- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 2 + drivers/gpu/drm/i915/i915_scheduler.c | 34 ++++- drivers/gpu/drm/i915/i915_trace.h | 208 +++++++++++++++++++++++++++++ drivers/gpu/drm/i915/intel_lrc.c | 2 + 4 files changed, 244 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem_execbuffer.c b/drivers/gpu/drm/i915/i915_gem_execbuffer.c index 1325b19..f90a2c8 100644 --- a/drivers/gpu/drm/i915/i915_gem_execbuffer.c +++ b/drivers/gpu/drm/i915/i915_gem_execbuffer.c @@ -1291,6 +1291,8 @@ i915_gem_ringbuffer_submission(struct i915_execbuffer_params *params, i915_gem_execbuffer_move_to_active(vmas, params->request); + trace_i915_gem_ring_queue(ring, params); + qe = container_of(params, typeof(*qe), params); ret = i915_scheduler_queue_execbuffer(qe); if (ret) diff --git a/drivers/gpu/drm/i915/i915_scheduler.c b/drivers/gpu/drm/i915/i915_scheduler.c index 66dbc20..408bedc 100644 --- a/drivers/gpu/drm/i915/i915_scheduler.c +++ b/drivers/gpu/drm/i915/i915_scheduler.c @@ -101,6 +101,8 @@ int i915_scheduler_queue_execbuffer(struct i915_scheduler_queue_entry *qe) qe->scheduler_index = scheduler->index++; + trace_i915_scheduler_queue(qe->params.ring, qe); + WARN_ON(qe->params.fence_wait && (atomic_read(&qe->params.fence_wait->status) == 0)); @@ -253,6 +255,9 @@ int i915_scheduler_queue_execbuffer(struct i915_scheduler_queue_entry *qe) not_flying = i915_scheduler_count_flying(scheduler, ring) < scheduler->min_flying; + trace_i915_scheduler_queue(ring, node); + trace_i915_scheduler_node_state_change(ring, node); + spin_unlock_irqrestore(&scheduler->lock, flags); if (not_flying) @@ -280,6 +285,9 @@ static int i915_scheduler_fly_node(struct i915_scheduler_queue_entry *node) node->status = i915_sqs_flying; + trace_i915_scheduler_fly(ring, node); + trace_i915_scheduler_node_state_change(ring, node); + if (!(scheduler->flags[ring->id] & i915_sf_interrupts_enabled)) { bool success = true; @@ -344,6 +352,8 @@ static void i915_scheduler_node_requeue(struct i915_scheduler_queue_entry *node) BUG_ON(!I915_SQS_IS_FLYING(node)); node->status = i915_sqs_queued; + trace_i915_scheduler_unfly(node->params.ring, node); + trace_i915_scheduler_node_state_change(node->params.ring, node); } /* Give up on a popped node completely. For example, because it is causing the @@ -354,6 +364,8 @@ static void i915_scheduler_node_kill(struct i915_scheduler_queue_entry *node) BUG_ON(!I915_SQS_IS_FLYING(node)); node->status = i915_sqs_dead; + trace_i915_scheduler_unfly(node->params.ring, node); + trace_i915_scheduler_node_state_change(node->params.ring, node); } /* Abandon a queued node completely. For example because the driver is being @@ -365,6 +377,7 @@ static void i915_scheduler_node_kill_queued(struct i915_scheduler_queue_entry *n BUG_ON(!I915_SQS_IS_QUEUED(node)); node->status = i915_sqs_dead; + trace_i915_scheduler_node_state_change(node->params.ring, node); } /* The system is toast. Terminate all nodes with extreme prejudice. */ @@ -429,8 +442,10 @@ static void i915_scheduler_seqno_complete(struct intel_engine_cs *ring, uint32_t * if a completed entry is found then there is no need to scan further. */ list_for_each_entry(node, &scheduler->node_queue[ring->id], link) { - if (I915_SQS_IS_COMPLETE(node)) + if (I915_SQS_IS_COMPLETE(node)) { + trace_i915_scheduler_landing(ring, seqno, node); return; + } if (seqno == node->params.request->seqno) break; @@ -441,8 +456,12 @@ static void i915_scheduler_seqno_complete(struct intel_engine_cs *ring, uint32_t * like cache flushes and page flips. So don't complain about if * no node was found. */ - if (&node->link == &scheduler->node_queue[ring->id]) + if (&node->link == &scheduler->node_queue[ring->id]) { + trace_i915_scheduler_landing(ring, seqno, NULL); return; + } + + trace_i915_scheduler_landing(ring, seqno, node); WARN_ON(!I915_SQS_IS_FLYING(node)); @@ -457,6 +476,7 @@ static void i915_scheduler_seqno_complete(struct intel_engine_cs *ring, uint32_t /* Node was in flight so mark it as complete. */ node->status = i915_sqs_complete; + trace_i915_scheduler_node_state_change(ring, node); got_changes = true; } @@ -481,6 +501,8 @@ int i915_scheduler_handle_irq(struct intel_engine_cs *ring) seqno = ring->get_seqno(ring, false); + trace_i915_scheduler_irq(ring, seqno); + if (i915.scheduler_override & i915_so_direct_submit) return 0; @@ -625,6 +647,8 @@ static int i915_scheduler_remove(struct intel_engine_cs *ring) /* Launch more packets now? */ do_submit = (queued > 0) && (flying < scheduler->min_flying); + trace_i915_scheduler_remove(ring, min_seqno, do_submit); + spin_unlock_irqrestore(&scheduler->lock, flags); if (do_submit) @@ -634,6 +658,8 @@ static int i915_scheduler_remove(struct intel_engine_cs *ring) node = list_first_entry(&remove, typeof(*node), link); list_del(&node->link); + trace_i915_scheduler_destroy(ring, node); + #ifdef CONFIG_SYNC if (node->params.fence_wait) sync_fence_put(node->params.fence_wait); @@ -1016,6 +1042,8 @@ static int i915_scheduler_pop_from_queue_locked(struct intel_engine_cs *ring, INIT_LIST_HEAD(&best->link); best->status = i915_sqs_popped; + trace_i915_scheduler_node_state_change(ring, best); + ret = 0; } else { /* Can only get here if: @@ -1073,6 +1101,8 @@ static int i915_scheduler_pop_from_queue_locked(struct intel_engine_cs *ring, #endif } + trace_i915_scheduler_pop_from_queue(ring, best); + *pop_node = best; return ret; } diff --git a/drivers/gpu/drm/i915/i915_trace.h b/drivers/gpu/drm/i915/i915_trace.h index 796c630..8774192 100644 --- a/drivers/gpu/drm/i915/i915_trace.h +++ b/drivers/gpu/drm/i915/i915_trace.h @@ -9,6 +9,7 @@ #include "i915_drv.h" #include "intel_drv.h" #include "intel_ringbuffer.h" +#include "i915_scheduler.h" #undef TRACE_SYSTEM #define TRACE_SYSTEM i915 @@ -786,6 +787,213 @@ TRACE_EVENT(switch_mm, __entry->dev, __entry->ring, __entry->to, __entry->vm) ); +TRACE_EVENT(i915_scheduler_queue, + TP_PROTO(struct intel_engine_cs *ring, + struct i915_scheduler_queue_entry *node), + TP_ARGS(ring, node), + + TP_STRUCT__entry( + __field(u32, ring) + __field(u32, uniq) + __field(u32, seqno) + ), + + TP_fast_assign( + __entry->ring = ring->id; + __entry->uniq = node ? node->params.request->uniq : 0; + __entry->seqno = node ? node->params.request->seqno : 0; + ), + + TP_printk("ring=%d, uniq=%d, seqno=%d", + __entry->ring, __entry->uniq, __entry->seqno) +); + +TRACE_EVENT(i915_scheduler_fly, + TP_PROTO(struct intel_engine_cs *ring, + struct i915_scheduler_queue_entry *node), + TP_ARGS(ring, node), + + TP_STRUCT__entry( + __field(u32, ring) + __field(u32, uniq) + __field(u32, seqno) + ), + + TP_fast_assign( + __entry->ring = ring->id; + __entry->uniq = node ? node->params.request->uniq : 0; + __entry->seqno = node ? node->params.request->seqno : 0; + ), + + TP_printk("ring=%d, uniq=%d, seqno=%d", + __entry->ring, __entry->uniq, __entry->seqno) +); + +TRACE_EVENT(i915_scheduler_unfly, + TP_PROTO(struct intel_engine_cs *ring, + struct i915_scheduler_queue_entry *node), + TP_ARGS(ring, node), + + TP_STRUCT__entry( + __field(u32, ring) + __field(u32, uniq) + __field(u32, seqno) + ), + + TP_fast_assign( + __entry->ring = ring->id; + __entry->uniq = node ? node->params.request->uniq : 0; + __entry->seqno = node ? node->params.request->seqno : 0; + ), + + TP_printk("ring=%d, uniq=%d, seqno=%d", + __entry->ring, __entry->uniq, __entry->seqno) +); + +TRACE_EVENT(i915_scheduler_landing, + TP_PROTO(struct intel_engine_cs *ring, u32 seqno, + struct i915_scheduler_queue_entry *node), + TP_ARGS(ring, seqno, node), + + TP_STRUCT__entry( + __field(u32, ring) + __field(u32, uniq) + __field(u32, seqno) + __field(u32, status) + ), + + TP_fast_assign( + __entry->ring = ring->id; + __entry->uniq = node ? node->params.request->uniq : 0; + __entry->seqno = seqno; + __entry->status = node ? node->status : ~0U; + ), + + TP_printk("ring=%d, uniq=%d, seqno=%d, status=%d", + __entry->ring, __entry->uniq, __entry->seqno, __entry->status) +); + +TRACE_EVENT(i915_scheduler_remove, + TP_PROTO(struct intel_engine_cs *ring, + u32 min_seqno, bool do_submit), + TP_ARGS(ring, min_seqno, do_submit), + + TP_STRUCT__entry( + __field(u32, ring) + __field(u32, min_seqno) + __field(bool, do_submit) + ), + + TP_fast_assign( + __entry->ring = ring->id; + __entry->min_seqno = min_seqno; + __entry->do_submit = do_submit; + ), + + TP_printk("ring=%d, min_seqno = %d, do_submit=%d", + __entry->ring, __entry->min_seqno, __entry->do_submit) +); + +TRACE_EVENT(i915_scheduler_destroy, + TP_PROTO(struct intel_engine_cs *ring, + struct i915_scheduler_queue_entry *node), + TP_ARGS(ring, node), + + TP_STRUCT__entry( + __field(u32, ring) + __field(u32, uniq) + __field(u32, seqno) + ), + + TP_fast_assign( + __entry->ring = ring->id; + __entry->uniq = node ? node->params.request->uniq : 0; + __entry->seqno = node ? node->params.request->seqno : 0; + ), + + TP_printk("ring=%d, uniq=%d, seqno=%d", + __entry->ring, __entry->uniq, __entry->seqno) +); + +TRACE_EVENT(i915_scheduler_pop_from_queue, + TP_PROTO(struct intel_engine_cs *ring, + struct i915_scheduler_queue_entry *node), + TP_ARGS(ring, node), + + TP_STRUCT__entry( + __field(u32, ring) + __field(u32, uniq) + __field(u32, seqno) + ), + + TP_fast_assign( + __entry->ring = ring->id; + __entry->uniq = node ? node->params.request->uniq : 0; + __entry->seqno = node ? node->params.request->seqno : 0; + ), + + TP_printk("ring=%d, uniq=%d, seqno=%d", + __entry->ring, __entry->uniq, __entry->seqno) +); + +TRACE_EVENT(i915_scheduler_node_state_change, + TP_PROTO(struct intel_engine_cs *ring, + struct i915_scheduler_queue_entry *node), + TP_ARGS(ring, node), + + TP_STRUCT__entry( + __field(u32, ring) + __field(u32, uniq) + __field(u32, seqno) + __field(u32, status) + ), + + TP_fast_assign( + __entry->ring = ring->id; + __entry->uniq = node ? node->params.request->uniq : 0; + __entry->seqno = node->params.request->seqno; + __entry->status = node->status; + ), + + TP_printk("ring=%d, uniq=%d, seqno=%d, status=%d", + __entry->ring, __entry->uniq, __entry->seqno, __entry->status) +); + +TRACE_EVENT(i915_scheduler_irq, + TP_PROTO(struct intel_engine_cs *ring, uint32_t seqno), + TP_ARGS(ring, seqno), + + TP_STRUCT__entry( + __field(u32, ring) + __field(u32, seqno) + ), + + TP_fast_assign( + __entry->ring = ring->id; + __entry->seqno = seqno; + ), + + TP_printk("ring=%d, seqno=%d", __entry->ring, __entry->seqno) +); + +TRACE_EVENT(i915_gem_ring_queue, + TP_PROTO(struct intel_engine_cs *ring, + struct i915_execbuffer_params *params), + TP_ARGS(ring, params), + + TP_STRUCT__entry( + __field(u32, ring) + __field(u32, seqno) + ), + + TP_fast_assign( + __entry->ring = ring->id; + __entry->seqno = params->request->seqno; + ), + + TP_printk("ring=%d, seqno=%d", __entry->ring, __entry->seqno) +); + #endif /* _I915_TRACE_H_ */ /* This part must be outside protection */ diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index d3e7399..41dca2a 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -886,6 +886,8 @@ int intel_execlists_submission(struct i915_execbuffer_params *params, i915_gem_execbuffer_move_to_active(vmas, params->request); + trace_i915_gem_ring_queue(ring, params); + qe = container_of(params, typeof(*qe), params); ret = i915_scheduler_queue_execbuffer(qe); if (ret)