All of lore.kernel.org
 help / color / mirror / Atom feed
From: Umesh Nerlige Ramappa <umesh.nerlige.ramappa@intel.com>
To: Riana Tauro <riana.tauro@intel.com>
Cc: intel-xe@lists.freedesktop.org
Subject: Re: [PATCH v2 2/8] RFC drm/xe/guc: Add interface for engine busyness ticks
Date: Wed, 20 Dec 2023 16:49:59 -0800	[thread overview]
Message-ID: <ZYOLtyll4gC9RHyh@unerlige-ril> (raw)
In-Reply-To: <20231207125802.3730165-3-riana.tauro@intel.com>

On Thu, Dec 07, 2023 at 06:27:56PM +0530, Riana Tauro wrote:
>GuC provides engine busyness ticks as a 64 bit counter which count
>as clock ticks. These counters are maintained in a
>shared memory buffer and updated on a continuous basis.
>
>Add functions that initialize Engine busyness and get
>the current accumulated busyness.
>
>Signed-off-by: Riana Tauro <riana.tauro@intel.com>
>---
> drivers/gpu/drm/xe/Makefile                 |   1 +
> drivers/gpu/drm/xe/abi/guc_actions_abi.h    |   1 +
> drivers/gpu/drm/xe/xe_gt.c                  |  13 ++
> drivers/gpu/drm/xe/xe_gt.h                  |   2 +
> drivers/gpu/drm/xe/xe_guc.c                 |   7 +
> drivers/gpu/drm/xe/xe_guc_engine_busyness.c | 153 ++++++++++++++++++++
> drivers/gpu/drm/xe/xe_guc_engine_busyness.h |  17 +++
> drivers/gpu/drm/xe/xe_guc_fwif.h            |  15 ++
> drivers/gpu/drm/xe/xe_guc_types.h           |   6 +
> 9 files changed, 215 insertions(+)
> create mode 100644 drivers/gpu/drm/xe/xe_guc_engine_busyness.c
> create mode 100644 drivers/gpu/drm/xe/xe_guc_engine_busyness.h
>
>diff --git a/drivers/gpu/drm/xe/Makefile b/drivers/gpu/drm/xe/Makefile
>index 86691f3b9077..7418e6a07bc8 100644
>--- a/drivers/gpu/drm/xe/Makefile
>+++ b/drivers/gpu/drm/xe/Makefile
>@@ -83,6 +83,7 @@ xe-y += xe_bb.o \
> 	xe_guc_ads.o \
> 	xe_guc_ct.o \
> 	xe_guc_debugfs.o \
>+	xe_guc_engine_busyness.o \
> 	xe_guc_hwconfig.o \
> 	xe_guc_log.o \
> 	xe_guc_pc.o \
>diff --git a/drivers/gpu/drm/xe/abi/guc_actions_abi.h b/drivers/gpu/drm/xe/abi/guc_actions_abi.h
>index 3062e0e0d467..d87681ca89bc 100644
>--- a/drivers/gpu/drm/xe/abi/guc_actions_abi.h
>+++ b/drivers/gpu/drm/xe/abi/guc_actions_abi.h
>@@ -139,6 +139,7 @@ enum xe_guc_action {
> 	XE_GUC_ACTION_REGISTER_CONTEXT_MULTI_LRC = 0x4601,
> 	XE_GUC_ACTION_CLIENT_SOFT_RESET = 0x5507,
> 	XE_GUC_ACTION_SET_ENG_UTIL_BUFF = 0x550A,
>+	XE_GUC_ACTION_SET_DEVICE_ENGINE_UTILIZATION = 0x550C,
> 	XE_GUC_ACTION_NOTIFY_MEMORY_CAT_ERROR = 0x6000,
> 	XE_GUC_ACTION_REPORT_PAGE_FAULT_REQ_DESC = 0x6002,
> 	XE_GUC_ACTION_PAGE_FAULT_RES_DESC = 0x6003,
>diff --git a/drivers/gpu/drm/xe/xe_gt.c b/drivers/gpu/drm/xe/xe_gt.c
>index 154d6c7072b9..3d735b66f60d 100644
>--- a/drivers/gpu/drm/xe/xe_gt.c
>+++ b/drivers/gpu/drm/xe/xe_gt.c
>@@ -31,6 +31,7 @@
> #include "xe_gt_sysfs.h"
> #include "xe_gt_tlb_invalidation.h"
> #include "xe_gt_topology.h"
>+#include "xe_guc_engine_busyness.h"
> #include "xe_guc_exec_queue_types.h"
> #include "xe_guc_pc.h"
> #include "xe_hw_fence.h"
>@@ -783,3 +784,15 @@ struct xe_hw_engine *xe_gt_any_hw_engine_by_reset_domain(struct xe_gt *gt,
>
> 	return NULL;
> }
>+
>+/**
>+ * xe_gt_engine_busy_ticks - Return current accumulated engine busyness ticks
>+ * @gt: GT structure
>+ * @hwe: Xe HW engine to report on
>+ *
>+ * Returns accumulated ticks @hwe was busy since engine stats were enabled.
>+ */
>+u64 xe_gt_engine_busy_ticks(struct xe_gt *gt, struct xe_hw_engine *hwe)
>+{
>+	return xe_guc_engine_busyness_ticks(&gt->uc.guc, hwe);
>+}
>diff --git a/drivers/gpu/drm/xe/xe_gt.h b/drivers/gpu/drm/xe/xe_gt.h
>index a818cc9c8fd0..2e3cd7031287 100644
>--- a/drivers/gpu/drm/xe/xe_gt.h
>+++ b/drivers/gpu/drm/xe/xe_gt.h
>@@ -42,6 +42,8 @@ int xe_gt_resume(struct xe_gt *gt);
> void xe_gt_reset_async(struct xe_gt *gt);
> void xe_gt_sanitize(struct xe_gt *gt);
>
>+u64 xe_gt_engine_busy_ticks(struct xe_gt *gt, struct xe_hw_engine *hwe);
>+
> /**
>  * xe_gt_any_hw_engine_by_reset_domain - scan the list of engines and return the
>  * first that matches the same reset domain as @class
>diff --git a/drivers/gpu/drm/xe/xe_guc.c b/drivers/gpu/drm/xe/xe_guc.c
>index 482cb0df9f15..6116aaea936f 100644
>--- a/drivers/gpu/drm/xe/xe_guc.c
>+++ b/drivers/gpu/drm/xe/xe_guc.c
>@@ -18,6 +18,7 @@
> #include "xe_gt.h"
> #include "xe_guc_ads.h"
> #include "xe_guc_ct.h"
>+#include "xe_guc_engine_busyness.h"
> #include "xe_guc_hwconfig.h"
> #include "xe_guc_log.h"
> #include "xe_guc_pc.h"
>@@ -306,9 +307,15 @@ int xe_guc_init_post_hwconfig(struct xe_guc *guc)
>
> int xe_guc_post_load_init(struct xe_guc *guc)
> {
>+	int err;
>+
> 	xe_guc_ads_populate_post_load(&guc->ads);
> 	guc->submission_state.enabled = true;
>
>+	err = xe_guc_engine_busyness_init(guc);
>+	if (err)
>+		return err;
>+
> 	return 0;
> }
>
>diff --git a/drivers/gpu/drm/xe/xe_guc_engine_busyness.c b/drivers/gpu/drm/xe/xe_guc_engine_busyness.c
>new file mode 100644
>index 000000000000..287429e31e6c
>--- /dev/null
>+++ b/drivers/gpu/drm/xe/xe_guc_engine_busyness.c
>@@ -0,0 +1,153 @@
>+// SPDX-License-Identifier: MIT
>+/*
>+ * Copyright © 2023 Intel Corporation
>+ */
>+#include "xe_guc_engine_busyness.h"
>+
>+#include <drm/drm_managed.h>
>+
>+#include "abi/guc_actions_abi.h"
>+#include "xe_bo.h"
>+#include "xe_guc.h"
>+#include "xe_guc_ct.h"
>+
>+/**
>+ * DOC: Xe GuC Engine Busyness
>+ *
>+ * GuC >= 70.11.1 maintains busyness counters in a shared memory buffer for each
>+ * engine on a continuous basis. The counters are all 64 bits and count in clock
>+ * ticks. The values are updated on context switch events and periodicaly on a
>+ * timer internal to GuC. The update rate is guaranteed to be at least 2Hz (but with
>+ * a caveat that is not real time, best effort only).
>+ *
>+ * engine busyness ticks (ticks_engine) : clock ticks for which engine was active
>+ */
>+
>+static void guc_engine_busyness_usage_map(struct xe_guc *guc,
>+					  struct xe_hw_engine *hwe,
>+					  struct iosys_map *engine_map)

indent slightly off

>+{
>+	struct iosys_map *map;
>+	size_t offset;
>+	u32 instance;
>+	u8 guc_class;
>+
>+	guc_class = xe_engine_class_to_guc_class(hwe->class);
>+	instance = hwe->logical_instance;
>+
>+	map = &guc->busy.bo->vmap;
>+
>+	offset = offsetof(struct guc_engine_observation_data,
>+			  engine_data[guc_class][instance]);
>+
>+	*engine_map = IOSYS_MAP_INIT_OFFSET(map, offset);
>+}
>+
>+static void guc_engine_busyness_get_usage(struct xe_guc *guc,
>+					  struct xe_hw_engine *hwe,
>+					  u64 *_ticks_engine)

I would swap the _ between the local ticks_engine and the one passed to 
the function or better just use a different name for the local variable.

>+{
>+	struct iosys_map engine_map;
>+	u64 ticks_engine = 0;
>+	int i = 0;
>+
>+	guc_engine_busyness_usage_map(guc, hwe, &engine_map);
>+
>+#define read_engine_usage(map_, field_) \
>+	iosys_map_rd_field(map_, 0, struct guc_engine_data, field_)
>+
>+	do {
>+		ticks_engine = read_engine_usage(&engine_map, total_execution_ticks);
>+
>+		if (read_engine_usage(&engine_map, total_execution_ticks) == ticks_engine)
>+			break;
>+	} while (++i < 6);
>+
>+#undef read_engine_usage
>+
>+	if (_ticks_engine)
>+		*_ticks_engine = ticks_engine;
>+}
>+
>+static void guc_engine_busyness_enable_stats(struct xe_guc *guc)
>+{
>+	u32 ggtt_addr = xe_bo_ggtt_addr(guc->busy.bo);
>+	u32 action[] = {
>+		XE_GUC_ACTION_SET_DEVICE_ENGINE_UTILIZATION,
>+		ggtt_addr,
>+		0,
>+	};
>+	struct xe_device *xe = guc_to_xe(guc);
>+	int ret;
>+
>+	ret = xe_guc_ct_send(&guc->ct, action, ARRAY_SIZE(action), 0, 0);
>+	if (ret)
>+		drm_err(&xe->drm, "Failed to enable usage stats %pe", ERR_PTR(ret));
>+}
>+
>+static void guc_engine_busyness_fini(struct drm_device *drm, void *arg)
>+{
>+	struct xe_guc *guc = arg;
>+
>+	xe_bo_unpin_map_no_vm(guc->busy.bo);
>+}
>+
>+/*
>+ * xe_guc_engine_busyness_ticks - Gets current accumulated
>+ *				  engine busyness ticks
>+ * @guc: The GuC object
>+ * @hwe: Xe HW Engine
>+ *
>+ * Returns current acculumated ticks @hwe was busy when engine stats are enabled.
>+ */
>+u64 xe_guc_engine_busyness_ticks(struct xe_guc *guc, struct xe_hw_engine *hwe)
>+{
>+	u64 ticks_engine;
>+
>+	guc_engine_busyness_get_usage(guc, hwe, &ticks_engine);
>+
>+	return ticks_engine;
>+}
>+
>+/*
>+ * xe_guc_engine_busyness_init - Initializes the GuC Engine Busyness
>+ * @guc: The GuC object
>+ *
>+ * Initialize GuC engine busyness, only called once during driver load
>+ * Supported only on GuC >= 70.11.1
>+ *
>+ * Return: 0 on success, negative error code on error.
>+ */
>+int xe_guc_engine_busyness_init(struct xe_guc *guc)
>+{
>+	struct xe_device *xe = guc_to_xe(guc);
>+	struct xe_gt *gt = guc_to_gt(guc);
>+	struct xe_tile *tile = gt_to_tile(gt);
>+	struct xe_bo *bo;
>+	u32 size;
>+	int err;
>+
>+	/* Initialization already done */
>+	if (guc->busy.bo)
>+		return 0;
>+
>+	size = PAGE_ALIGN(sizeof(struct guc_engine_observation_data));
>+
>+	bo = xe_bo_create_pin_map(xe, tile, NULL, size,
>+				  ttm_bo_type_kernel,
>+				  XE_BO_CREATE_VRAM_IF_DGFX(tile) |
>+				  XE_BO_CREATE_GGTT_BIT);
>+
>+	if (IS_ERR(bo))
>+		return PTR_ERR(bo);
>+
>+	guc->busy.bo = bo;
>+
>+	guc_engine_busyness_enable_stats(guc);
>+
>+	err = drmm_add_action_or_reset(&xe->drm, guc_engine_busyness_fini, guc);

Wondering if we need to store the busyness values prior to reset and 
restore them afterwards. Depends on what type of reset this is. Does 
this reset GuC as well?

>+	if (err)
>+		return err;
>+
>+	return 0;
>+}
>diff --git a/drivers/gpu/drm/xe/xe_guc_engine_busyness.h b/drivers/gpu/drm/xe/xe_guc_engine_busyness.h
>new file mode 100644
>index 000000000000..d70f06209896
>--- /dev/null
>+++ b/drivers/gpu/drm/xe/xe_guc_engine_busyness.h
>@@ -0,0 +1,17 @@
>+/* SPDX-License-Identifier: MIT */
>+/*
>+ * Copyright © 2023 Intel Corporation
>+ */
>+
>+#ifndef _XE_GUC_ENGINE_BUSYNESS_H_
>+#define _XE_GUC_ENGINE_BUSYNESS_H_
>+
>+#include <linux/types.h>
>+
>+struct xe_hw_engine;
>+struct xe_guc;
>+
>+int xe_guc_engine_busyness_init(struct xe_guc *guc);
>+u64 xe_guc_engine_busyness_ticks(struct xe_guc *guc, struct xe_hw_engine *hwe);
>+
>+#endif
>diff --git a/drivers/gpu/drm/xe/xe_guc_fwif.h b/drivers/gpu/drm/xe/xe_guc_fwif.h
>index 4dd5a88a7826..c8ca5fe97614 100644
>--- a/drivers/gpu/drm/xe/xe_guc_fwif.h
>+++ b/drivers/gpu/drm/xe/xe_guc_fwif.h
>@@ -37,6 +37,7 @@
> #define GUC_COMPUTE_CLASS		4
> #define GUC_GSC_OTHER_CLASS		5
> #define GUC_LAST_ENGINE_CLASS		GUC_GSC_OTHER_CLASS
>+#define GUC_MAX_OAG_COUNTERS		8
> #define GUC_MAX_ENGINE_CLASSES		16
> #define GUC_MAX_INSTANCES_PER_CLASS	32
>
>@@ -222,6 +223,20 @@ struct guc_engine_usage {
> 	struct guc_engine_usage_record engines[GUC_MAX_ENGINE_CLASSES][GUC_MAX_INSTANCES_PER_CLASS];
> } __packed;
>
>+/* Engine busyness stats */
>+struct guc_engine_data {
>+	u64 total_execution_ticks;
>+	u64 reserved;
>+} __packed;
>+
>+struct guc_engine_observation_data {
>+	struct guc_engine_data engine_data[GUC_MAX_ENGINE_CLASSES][GUC_MAX_INSTANCES_PER_CLASS];
>+	u64 oag_busy_data[GUC_MAX_OAG_COUNTERS];
>+	u64 total_active_ticks;
>+	u64 gt_timestamp;
>+	u64 reserved1;
>+} __packed;
>+
> /* This action will be programmed in C1BC - SOFT_SCRATCH_15_REG */
> enum xe_guc_recv_message {
> 	XE_GUC_RECV_MSG_CRASH_DUMP_POSTED = BIT(1),
>diff --git a/drivers/gpu/drm/xe/xe_guc_types.h b/drivers/gpu/drm/xe/xe_guc_types.h
>index cd80802e8918..4e9602301aed 100644
>--- a/drivers/gpu/drm/xe/xe_guc_types.h
>+++ b/drivers/gpu/drm/xe/xe_guc_types.h
>@@ -70,6 +70,12 @@ struct xe_guc {
> 		u32 size;
> 	} hwconfig;
>
>+	/** @busy: Engine busyness */
>+	struct {
>+		/** @bo: GGTT buffer object of engine busyness that is shared with GuC */
>+		struct xe_bo *bo;
>+	} busy;
>+
> 	/**
> 	 * @notify_reg: Register which is written to notify GuC of H2G messages
> 	 */

Except for some minor comments above, this lgtm,

Reviewed-by: Umesh Nerlige Ramappa <umesh.nerlige.ramappa@intel.com>


>-- 2.40.0
>

  reply	other threads:[~2023-12-21  0:50 UTC|newest]

Thread overview: 31+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2023-12-07 12:57 [PATCH v2 0/8] Engine Busyness Riana Tauro
2023-12-07 12:53 ` ✓ CI.Patch_applied: success for Engine Busyness (rev2) Patchwork
2023-12-07 12:53 ` ✗ CI.checkpatch: warning " Patchwork
2023-12-07 12:54 ` ✓ CI.KUnit: success " Patchwork
2023-12-07 12:57 ` [PATCH v2 1/8] RFC drm/xe: Move user engine class mappings to functions Riana Tauro
2023-12-07 12:57 ` [PATCH v2 2/8] RFC drm/xe/guc: Add interface for engine busyness ticks Riana Tauro
2023-12-21  0:49   ` Umesh Nerlige Ramappa [this message]
2023-12-21  5:14     ` Riana Tauro
2023-12-07 12:57 ` [PATCH v2 3/8] RFC drm/xe/guc: Expose engine busyness only for supported GuC version Riana Tauro
2023-12-21  0:52   ` Umesh Nerlige Ramappa
2023-12-21  5:17     ` Riana Tauro
2023-12-07 12:57 ` [PATCH v2 4/8] RFC drm/xe/guc: Add PMU counter for total active ticks Riana Tauro
2023-12-07 12:57 ` [PATCH v2 5/8] RFC drm/xe/uapi: Add configs for Engine busyness Riana Tauro
2023-12-21  2:29   ` Umesh Nerlige Ramappa
2023-12-21  5:26     ` Riana Tauro
2023-12-07 12:58 ` [PATCH v2 6/8] RFC drm/xe/pmu: Add PMU counters for engine busy ticks Riana Tauro
2023-12-07 12:58 ` [PATCH v2 7/8] RFC drm/xe/guc: Dynamically enable/disable engine busyness stats Riana Tauro
2023-12-07 12:58 ` [PATCH v2 8/8] RFC drm/xe/guc: Handle runtime suspend issues for engine busyness Riana Tauro
2023-12-07 13:01 ` ✓ CI.Build: success for Engine Busyness (rev2) Patchwork
2023-12-07 13:02 ` ✓ CI.Hooks: " Patchwork
2023-12-07 13:03 ` ✓ CI.checksparse: " Patchwork
2023-12-07 13:39 ` ✗ CI.BAT: failure " Patchwork
2023-12-07 14:45 ` [PATCH v2 0/8] Engine Busyness Tvrtko Ursulin
2023-12-14  1:56   ` Umesh Nerlige Ramappa
2023-12-14  8:06     ` Tvrtko Ursulin
2023-12-20  5:36       ` Umesh Nerlige Ramappa
2023-12-20  9:00         ` Tvrtko Ursulin
2023-12-20 23:58           ` Umesh Nerlige Ramappa
2023-12-21  9:36             ` Tvrtko Ursulin
2023-12-21 13:17               ` Nerlige Ramappa, Umesh
2023-12-22  9:41                 ` Tvrtko Ursulin

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=ZYOLtyll4gC9RHyh@unerlige-ril \
    --to=umesh.nerlige.ramappa@intel.com \
    --cc=intel-xe@lists.freedesktop.org \
    --cc=riana.tauro@intel.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.