intel-xe.lists.freedesktop.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v3 0/5] Enable media OA
@ 2025-06-03 20:21 Ashutosh Dixit
  2025-06-03 20:21 ` [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units Ashutosh Dixit
                   ` (7 more replies)
  0 siblings, 8 replies; 24+ messages in thread
From: Ashutosh Dixit @ 2025-06-03 20:21 UTC (permalink / raw)
  To: intel-xe; +Cc: Umesh Nerlige Ramappa

We had previously enabled render and compute OA units. Enable media OA
units with this series.

v3: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
v2: Added Patch 5

Ashutosh Dixit (5):
  drm/xe/oa/uapi: Expose media OA units
  drm/xe/oa: Print hwe to OA unit mapping
  drm/xe/oa: Introduce stream->oa_unit
  drm/xe/oa: Assign hwe for OAM_SAG
  drm/xe/oa: Enable OAM latency measurement

 drivers/gpu/drm/xe/regs/xe_oa_regs.h |   3 +
 drivers/gpu/drm/xe/xe_oa.c           | 205 ++++++++++++++++++++-------
 drivers/gpu/drm/xe/xe_oa_types.h     |   6 +
 include/uapi/drm/xe_drm.h            |   3 +
 4 files changed, 163 insertions(+), 54 deletions(-)

-- 
2.48.1


^ permalink raw reply	[flat|nested] 24+ messages in thread

* [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units
  2025-06-03 20:21 [PATCH v3 0/5] Enable media OA Ashutosh Dixit
@ 2025-06-03 20:21 ` Ashutosh Dixit
  2025-06-04 23:42   ` Umesh Nerlige Ramappa
  2025-06-03 20:21 ` [PATCH 2/5] drm/xe/oa: Print hwe to OA unit mapping Ashutosh Dixit
                   ` (6 subsequent siblings)
  7 siblings, 1 reply; 24+ messages in thread
From: Ashutosh Dixit @ 2025-06-03 20:21 UTC (permalink / raw)
  To: intel-xe; +Cc: Umesh Nerlige Ramappa

On Xe2+ platforms, media engines are attached to "SCMI" OA media (OAM)
units. One or more SCMI OAM units might be present on a platform. In
addition there is another OAM unit for global events, called
OAM-SAG. Performance metrics for media workloads can be obtained from these
OAM units, similar to OAG.

Expose these OAM units for userspace to use. OAM-SAG is exposed as an OA
unit without any attached engines.

Bspec: 70819, 67103, 63844, 72572, 74476, 61284

v2: Fix xe_gt_WARN_ON in __hwe_oam_unit for < 12.7 platforms
v3: Return XE_OA_UNIT_INVALID for < 12.7 to indicate no OAM units
v4: Move xe_oa_print_oa_units() to separate patch
v5: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG

Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
---
 drivers/gpu/drm/xe/xe_oa.c | 68 ++++++++++++++++++++++++++++----------
 include/uapi/drm/xe_drm.h  |  3 ++
 2 files changed, 54 insertions(+), 17 deletions(-)

diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
index fb842fa0552e5..0de0d5a18df74 100644
--- a/drivers/gpu/drm/xe/xe_oa.c
+++ b/drivers/gpu/drm/xe/xe_oa.c
@@ -43,6 +43,12 @@
 #define DEFAULT_POLL_PERIOD_NS (NSEC_PER_SEC / DEFAULT_POLL_FREQUENCY_HZ)
 #define XE_OA_UNIT_INVALID U32_MAX
 
+enum xe_oam_unit_type {
+	XE_OAM_UNIT_SAG,
+	XE_OAM_UNIT_SCMI_0,
+	XE_OAM_UNIT_SCMI_1,
+};
+
 enum xe_oa_submit_deps {
 	XE_OA_SUBMIT_NO_DEPS,
 	XE_OA_SUBMIT_ADD_DEPS,
@@ -1881,6 +1887,7 @@ static bool engine_supports_oa_format(const struct xe_hw_engine *hwe, int type)
 		return type == DRM_XE_OA_FMT_TYPE_OAG || type == DRM_XE_OA_FMT_TYPE_OAR ||
 			type == DRM_XE_OA_FMT_TYPE_OAC || type == DRM_XE_OA_FMT_TYPE_PEC;
 	case DRM_XE_OA_UNIT_TYPE_OAM:
+	case DRM_XE_OA_UNIT_TYPE_OAM_SAG:
 		return type == DRM_XE_OA_FMT_TYPE_OAM || type == DRM_XE_OA_FMT_TYPE_OAM_MPEC;
 	default:
 		return false;
@@ -2448,20 +2455,38 @@ int xe_oa_register(struct xe_device *xe)
 
 static u32 num_oa_units_per_gt(struct xe_gt *gt)
 {
-	return 1;
+	if (!xe_gt_is_media_type(gt) || GRAPHICS_VER(gt_to_xe(gt)) < 20)
+		return 1;
+	else if (!IS_DGFX(gt_to_xe(gt)))
+		return XE_OAM_UNIT_SCMI_0 + 1; /* SAG + SCMI_0 */
+	else
+		return XE_OAM_UNIT_SCMI_1 + 1; /* SAG + SCMI_0 + SCMI_1 */
 }
 
 static u32 __hwe_oam_unit(struct xe_hw_engine *hwe)
 {
-	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) >= 1270) {
-		/*
-		 * There's 1 SAMEDIA gt and 1 OAM per SAMEDIA gt. All media slices
-		 * within the gt use the same OAM. All MTL/LNL SKUs list 1 SA MEDIA
-		 */
-		xe_gt_WARN_ON(hwe->gt, hwe->gt->info.type != XE_GT_TYPE_MEDIA);
+	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) < 1270)
+		return XE_OA_UNIT_INVALID;
 
+	xe_gt_WARN_ON(hwe->gt, !xe_gt_is_media_type(hwe->gt));
+
+	if (GRAPHICS_VER(gt_to_xe(hwe->gt)) < 20)
 		return 0;
-	}
+	/*
+	 * XE_OAM_UNIT_SAG has only GSCCS attached to it, but only on some platforms. Also
+	 * GSCCS cannot be used to submit batches to program the OAM unit. Therefore we don't
+	 * assign an OA unit to GSCCS. This means that XE_OAM_UNIT_SAG is exposed as an OA
+	 * unit without attached engines. Fused off engines can also result in oa_unit's with
+	 * num_engines == 0. OA streams can be opened on all OA units.
+	 */
+	else if (hwe->engine_id == XE_HW_ENGINE_GSCCS0)
+		return XE_OA_UNIT_INVALID;
+	else if (!IS_DGFX(gt_to_xe(hwe->gt)))
+		return XE_OAM_UNIT_SCMI_0;
+	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_DECODE)
+		return (hwe->instance / 2 & 0x1) + 1;
+	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_ENHANCE)
+		return (hwe->instance & 0x1) + 1;
 
 	return XE_OA_UNIT_INVALID;
 }
@@ -2475,6 +2500,7 @@ static u32 __hwe_oa_unit(struct xe_hw_engine *hwe)
 
 	case XE_ENGINE_CLASS_VIDEO_DECODE:
 	case XE_ENGINE_CLASS_VIDEO_ENHANCE:
+	case XE_ENGINE_CLASS_OTHER:
 		return __hwe_oam_unit(hwe);
 
 	default:
@@ -2514,18 +2540,25 @@ static struct xe_oa_regs __oag_regs(void)
 
 static void __xe_oa_init_oa_units(struct xe_gt *gt)
 {
-	const u32 mtl_oa_base[] = { 0x13000 };
+	/* Actual address is MEDIA_GT_GSI_OFFSET + oam_base_addr[i] */
+	const u32 oam_base_addr[] = {
+		[XE_OAM_UNIT_SAG]    = 0x13000,
+		[XE_OAM_UNIT_SCMI_0] = 0x14000,
+		[XE_OAM_UNIT_SCMI_1] = 0x14800,
+	};
 	int i, num_units = gt->oa.num_oa_units;
 
 	for (i = 0; i < num_units; i++) {
 		struct xe_oa_unit *u = &gt->oa.oa_unit[i];
 
-		if (gt->info.type != XE_GT_TYPE_MEDIA) {
+		if (!xe_gt_is_media_type(gt)) {
 			u->regs = __oag_regs();
 			u->type = DRM_XE_OA_UNIT_TYPE_OAG;
-		} else if (GRAPHICS_VERx100(gt_to_xe(gt)) >= 1270) {
-			u->regs = __oam_regs(mtl_oa_base[i]);
-			u->type = DRM_XE_OA_UNIT_TYPE_OAM;
+		} else {
+			xe_gt_assert(gt, GRAPHICS_VERx100(gt_to_xe(gt)) >= 1270);
+			u->regs = __oam_regs(oam_base_addr[i]);
+			u->type = i == XE_OAM_UNIT_SAG && GRAPHICS_VER(gt_to_xe(gt)) >= 20 ?
+				DRM_XE_OA_UNIT_TYPE_OAM_SAG : DRM_XE_OA_UNIT_TYPE_OAM;
 		}
 
 		xe_mmio_write32(&gt->mmio, u->regs.oa_ctrl, 0);
@@ -2560,10 +2593,6 @@ static int xe_oa_init_gt(struct xe_gt *gt)
 		}
 	}
 
-	/*
-	 * Fused off engines can result in oa_unit's with num_engines == 0. These units
-	 * will appear in OA unit query, but no OA streams can be opened on them.
-	 */
 	gt->oa.num_oa_units = num_oa_units;
 	gt->oa.oa_unit = u;
 
@@ -2579,6 +2608,11 @@ static int xe_oa_init_oa_units(struct xe_oa *oa)
 	struct xe_gt *gt;
 	int i, ret;
 
+	/* Needed for OAM implementation here */
+	BUILD_BUG_ON(XE_OAM_UNIT_SAG != 0);
+	BUILD_BUG_ON(XE_OAM_UNIT_SCMI_0 != 1);
+	BUILD_BUG_ON(XE_OAM_UNIT_SCMI_1 != 2);
+
 	for_each_gt(gt, oa->xe, i) {
 		ret = xe_oa_init_gt(gt);
 		if (ret)
diff --git a/include/uapi/drm/xe_drm.h b/include/uapi/drm/xe_drm.h
index 6a702ba7817c3..5460ba1e4cc37 100644
--- a/include/uapi/drm/xe_drm.h
+++ b/include/uapi/drm/xe_drm.h
@@ -1617,6 +1617,9 @@ enum drm_xe_oa_unit_type {
 
 	/** @DRM_XE_OA_UNIT_TYPE_OAM: OAM OA unit */
 	DRM_XE_OA_UNIT_TYPE_OAM,
+
+	/** @DRM_XE_OA_UNIT_TYPE_OAM_SAG: OAM_SAG OA unit */
+	DRM_XE_OA_UNIT_TYPE_OAM_SAG,
 };
 
 /**
-- 
2.48.1


^ permalink raw reply related	[flat|nested] 24+ messages in thread

* [PATCH 2/5] drm/xe/oa: Print hwe to OA unit mapping
  2025-06-03 20:21 [PATCH v3 0/5] Enable media OA Ashutosh Dixit
  2025-06-03 20:21 ` [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units Ashutosh Dixit
@ 2025-06-03 20:21 ` Ashutosh Dixit
  2025-06-04 23:49   ` Umesh Nerlige Ramappa
  2025-06-03 20:21 ` [PATCH 3/5] drm/xe/oa: Introduce stream->oa_unit Ashutosh Dixit
                   ` (5 subsequent siblings)
  7 siblings, 1 reply; 24+ messages in thread
From: Ashutosh Dixit @ 2025-06-03 20:21 UTC (permalink / raw)
  To: intel-xe; +Cc: Umesh Nerlige Ramappa

Print hwe to OA unit mapping to dmesg, to help debug for current and new
platforms.

Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
---
 drivers/gpu/drm/xe/xe_oa.c | 27 +++++++++++++++++++++++++++
 1 file changed, 27 insertions(+)

diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
index 0de0d5a18df74..94faa4ed2012f 100644
--- a/drivers/gpu/drm/xe/xe_oa.c
+++ b/drivers/gpu/drm/xe/xe_oa.c
@@ -2603,6 +2603,31 @@ static int xe_oa_init_gt(struct xe_gt *gt)
 	return 0;
 }
 
+static void xe_oa_print_oa_units(struct xe_oa *oa)
+{
+	enum xe_hw_engine_id hwe_id;
+	struct xe_hw_engine *hwe;
+	struct xe_oa_unit *u;
+	struct xe_gt *gt;
+	int gt_id, i, n;
+	char buf[256];
+
+	for_each_gt(gt, oa->xe, gt_id) {
+		for (i = 0; i < gt->oa.num_oa_units; i++) {
+			u = &gt->oa.oa_unit[i];
+			buf[0] = '\0';
+			n = 0;
+
+			for_each_hw_engine(hwe, gt, hwe_id)
+				if (xe_oa_unit_id(hwe) == u->oa_unit_id)
+					n += scnprintf(buf + n, sizeof(buf) - n, "%s ", hwe->name);
+
+			xe_gt_dbg(gt, "oa_unit %d, type %d, Engines: %s\n",
+				  u->oa_unit_id, u->type, buf);
+		}
+	}
+}
+
 static int xe_oa_init_oa_units(struct xe_oa *oa)
 {
 	struct xe_gt *gt;
@@ -2619,6 +2644,8 @@ static int xe_oa_init_oa_units(struct xe_oa *oa)
 			return ret;
 	}
 
+	xe_oa_print_oa_units(oa);
+
 	return 0;
 }
 
-- 
2.48.1


^ permalink raw reply related	[flat|nested] 24+ messages in thread

* [PATCH 3/5] drm/xe/oa: Introduce stream->oa_unit
  2025-06-03 20:21 [PATCH v3 0/5] Enable media OA Ashutosh Dixit
  2025-06-03 20:21 ` [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units Ashutosh Dixit
  2025-06-03 20:21 ` [PATCH 2/5] drm/xe/oa: Print hwe to OA unit mapping Ashutosh Dixit
@ 2025-06-03 20:21 ` Ashutosh Dixit
  2025-06-04 23:54   ` Umesh Nerlige Ramappa
  2025-06-03 20:21 ` [PATCH 4/5] drm/xe/oa: Assign hwe for OAM_SAG Ashutosh Dixit
                   ` (4 subsequent siblings)
  7 siblings, 1 reply; 24+ messages in thread
From: Ashutosh Dixit @ 2025-06-03 20:21 UTC (permalink / raw)
  To: intel-xe; +Cc: Umesh Nerlige Ramappa

Previously, the oa_unit associated with an OA stream was derived from hwe
associated with the stream (stream->hwe->oa_unit). This breaks with OAM_SAG
since OAM_SAG does not have any attached hardware engines. Resolve this by
introducing stream->oa_unit and stop depending on stream->hwe.

Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
---
 drivers/gpu/drm/xe/xe_oa.c       | 51 +++++++++++++++++++++-----------
 drivers/gpu/drm/xe/xe_oa_types.h |  3 ++
 2 files changed, 37 insertions(+), 17 deletions(-)

diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
index 94faa4ed2012f..4d6d9f0189a83 100644
--- a/drivers/gpu/drm/xe/xe_oa.c
+++ b/drivers/gpu/drm/xe/xe_oa.c
@@ -83,7 +83,7 @@ struct xe_oa_config {
 
 struct xe_oa_open_param {
 	struct xe_file *xef;
-	u32 oa_unit_id;
+	struct xe_oa_unit *oa_unit;
 	bool sample;
 	u32 metric_set;
 	enum xe_oa_format_name oa_format;
@@ -200,7 +200,7 @@ static void free_oa_config_bo(struct xe_oa_config_bo *oa_bo, struct dma_fence *l
 
 static const struct xe_oa_regs *__oa_regs(struct xe_oa_stream *stream)
 {
-	return &stream->hwe->oa_unit->regs;
+	return &stream->oa_unit->regs;
 }
 
 static u32 xe_oa_hw_tail_read(struct xe_oa_stream *stream)
@@ -460,7 +460,7 @@ static u32 __oa_ccs_select(struct xe_oa_stream *stream)
 
 static u32 __oactrl_used_bits(struct xe_oa_stream *stream)
 {
-	return stream->hwe->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG ?
+	return stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG ?
 		OAG_OACONTROL_USED_BITS : OAM_OACONTROL_USED_BITS;
 }
 
@@ -481,7 +481,7 @@ static void xe_oa_enable(struct xe_oa_stream *stream)
 		__oa_ccs_select(stream) | OAG_OACONTROL_OA_COUNTER_ENABLE;
 
 	if (GRAPHICS_VER(stream->oa->xe) >= 20 &&
-	    stream->hwe->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG)
+	    stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG)
 		val |= OAG_OACONTROL_OA_PES_DISAG_EN;
 
 	xe_mmio_rmw32(&stream->gt->mmio, regs->oa_ctrl, __oactrl_used_bits(stream), val);
@@ -848,7 +848,7 @@ static void xe_oa_disable_metric_set(struct xe_oa_stream *stream)
 
 static void xe_oa_stream_destroy(struct xe_oa_stream *stream)
 {
-	struct xe_oa_unit *u = stream->hwe->oa_unit;
+	struct xe_oa_unit *u = stream->oa_unit;
 	struct xe_gt *gt = stream->hwe->gt;
 
 	if (WARN_ON(stream != u->exclusive_stream))
@@ -1145,14 +1145,31 @@ static int decode_oa_format(struct xe_oa *oa, u64 fmt, enum xe_oa_format_name *n
 	return -EINVAL;
 }
 
+static struct xe_oa_unit *xe_oa_lookup_oa_unit(struct xe_oa *oa, u32 oa_unit_id)
+{
+	struct xe_gt *gt;
+	int gt_id, i;
+
+	for_each_gt(gt, oa->xe, gt_id) {
+		for (i = 0; i < gt->oa.num_oa_units; i++) {
+			struct xe_oa_unit *u = &gt->oa.oa_unit[i];
+
+			if (u->oa_unit_id == oa_unit_id)
+				return u;
+		}
+	}
+
+	return NULL;
+}
+
 static int xe_oa_set_prop_oa_unit_id(struct xe_oa *oa, u64 value,
 				     struct xe_oa_open_param *param)
 {
-	if (value >= oa->oa_unit_ids) {
+	param->oa_unit = xe_oa_lookup_oa_unit(oa, value);
+	if (!param->oa_unit) {
 		drm_dbg(&oa->xe->drm, "OA unit ID out of range %lld\n", value);
 		return -EINVAL;
 	}
-	param->oa_unit_id = value;
 	return 0;
 }
 
@@ -1683,13 +1700,13 @@ static const struct file_operations xe_oa_fops = {
 static int xe_oa_stream_init(struct xe_oa_stream *stream,
 			     struct xe_oa_open_param *param)
 {
-	struct xe_oa_unit *u = param->hwe->oa_unit;
 	struct xe_gt *gt = param->hwe->gt;
 	unsigned int fw_ref;
 	int ret;
 
 	stream->exec_q = param->exec_q;
 	stream->poll_period_ns = DEFAULT_POLL_PERIOD_NS;
+	stream->oa_unit = param->oa_unit;
 	stream->hwe = param->hwe;
 	stream->gt = stream->hwe->gt;
 	stream->oa_buffer.format = &stream->oa->oa_formats[param->oa_format];
@@ -1710,7 +1727,7 @@ static int xe_oa_stream_init(struct xe_oa_stream *stream,
 	 * buffer whose size, circ_size, is a multiple of the report size
 	 */
 	if (GRAPHICS_VER(stream->oa->xe) >= 20 &&
-	    stream->hwe->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG && stream->sample)
+	    stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG && stream->sample)
 		stream->oa_buffer.circ_size =
 			param->oa_buffer_size -
 			param->oa_buffer_size % stream->oa_buffer.format->size;
@@ -1768,7 +1785,7 @@ static int xe_oa_stream_init(struct xe_oa_stream *stream,
 	drm_dbg(&stream->oa->xe->drm, "opening stream oa config uuid=%s\n",
 		stream->oa_config->uuid);
 
-	WRITE_ONCE(u->exclusive_stream, stream);
+	WRITE_ONCE(stream->oa_unit->exclusive_stream, stream);
 
 	hrtimer_setup(&stream->poll_check_timer, xe_oa_poll_check_timer_cb, CLOCK_MONOTONIC,
 		      HRTIMER_MODE_REL);
@@ -1804,7 +1821,7 @@ static int xe_oa_stream_open_ioctl_locked(struct xe_oa *oa,
 	int ret;
 
 	/* We currently only allow exclusive access */
-	if (param->hwe->oa_unit->exclusive_stream) {
+	if (param->oa_unit->exclusive_stream) {
 		drm_dbg(&oa->xe->drm, "OA unit already in use\n");
 		ret = -EBUSY;
 		goto exit;
@@ -1880,9 +1897,9 @@ static u64 oa_exponent_to_ns(struct xe_gt *gt, int exponent)
 	return div_u64(nom + den - 1, den);
 }
 
-static bool engine_supports_oa_format(const struct xe_hw_engine *hwe, int type)
+static bool oa_unit_supports_oa_format(struct xe_oa_open_param *param, int type)
 {
-	switch (hwe->oa_unit->type) {
+	switch (param->oa_unit->type) {
 	case DRM_XE_OA_UNIT_TYPE_OAG:
 		return type == DRM_XE_OA_FMT_TYPE_OAG || type == DRM_XE_OA_FMT_TYPE_OAR ||
 			type == DRM_XE_OA_FMT_TYPE_OAC || type == DRM_XE_OA_FMT_TYPE_PEC;
@@ -1922,7 +1939,7 @@ static int xe_oa_assign_hwe(struct xe_oa *oa, struct xe_oa_open_param *param)
 		/* Else just get the first hwe attached to the oa unit */
 		for_each_gt(gt, oa->xe, i) {
 			for_each_hw_engine(hwe, gt, id) {
-				if (xe_oa_unit_id(hwe) == param->oa_unit_id) {
+				if (hwe->oa_unit == param->oa_unit) {
 					param->hwe = hwe;
 					goto out;
 				}
@@ -1930,10 +1947,10 @@ static int xe_oa_assign_hwe(struct xe_oa *oa, struct xe_oa_open_param *param)
 		}
 	}
 out:
-	if (!param->hwe || xe_oa_unit_id(param->hwe) != param->oa_unit_id) {
+	if (!param->hwe || param->hwe->oa_unit != param->oa_unit) {
 		drm_dbg(&oa->xe->drm, "Unable to find hwe (%d, %d) for OA unit ID %d\n",
 			param->exec_q ? param->exec_q->class : -1,
-			param->engine_instance, param->oa_unit_id);
+			param->engine_instance, param->oa_unit->oa_unit_id);
 		ret = -EINVAL;
 	}
 
@@ -2014,7 +2031,7 @@ int xe_oa_stream_open_ioctl(struct drm_device *dev, u64 data, struct drm_file *f
 
 	f = &oa->oa_formats[param.oa_format];
 	if (!param.oa_format || !f->size ||
-	    !engine_supports_oa_format(param.hwe, f->type)) {
+	    !oa_unit_supports_oa_format(&param, f->type)) {
 		drm_dbg(&oa->xe->drm, "Invalid OA format %d type %d size %d for class %d\n",
 			param.oa_format, f->type, f->size, param.hwe->class);
 		ret = -EINVAL;
diff --git a/drivers/gpu/drm/xe/xe_oa_types.h b/drivers/gpu/drm/xe/xe_oa_types.h
index 52e33c37d5ee8..a01c85931e2a5 100644
--- a/drivers/gpu/drm/xe/xe_oa_types.h
+++ b/drivers/gpu/drm/xe/xe_oa_types.h
@@ -182,6 +182,9 @@ struct xe_oa_stream {
 	/** @gt: gt associated with the oa stream */
 	struct xe_gt *gt;
 
+	/** @oa_unit: oa unit for this stream */
+	struct xe_oa_unit *oa_unit;
+
 	/** @hwe: hardware engine associated with this oa stream */
 	struct xe_hw_engine *hwe;
 
-- 
2.48.1


^ permalink raw reply related	[flat|nested] 24+ messages in thread

* [PATCH 4/5] drm/xe/oa: Assign hwe for OAM_SAG
  2025-06-03 20:21 [PATCH v3 0/5] Enable media OA Ashutosh Dixit
                   ` (2 preceding siblings ...)
  2025-06-03 20:21 ` [PATCH 3/5] drm/xe/oa: Introduce stream->oa_unit Ashutosh Dixit
@ 2025-06-03 20:21 ` Ashutosh Dixit
  2025-06-05  0:14   ` Umesh Nerlige Ramappa
  2025-06-03 20:21 ` [PATCH 5/5] drm/xe/oa: Enable OAM latency measurement Ashutosh Dixit
                   ` (3 subsequent siblings)
  7 siblings, 1 reply; 24+ messages in thread
From: Ashutosh Dixit @ 2025-06-03 20:21 UTC (permalink / raw)
  To: intel-xe; +Cc: Umesh Nerlige Ramappa

Because OAM_SAG doesn't have an attached hwe, assign another hwe belonging
to the same gt (and different OAM unit) to OAM_SAG. A hwe is needed for
batch submissions to program OA HW.

Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
---
 drivers/gpu/drm/xe/xe_oa.c       | 54 +++++++++++++++++++-------------
 drivers/gpu/drm/xe/xe_oa_types.h |  3 ++
 2 files changed, 35 insertions(+), 22 deletions(-)

diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
index 4d6d9f0189a83..35157424010bb 100644
--- a/drivers/gpu/drm/xe/xe_oa.c
+++ b/drivers/gpu/drm/xe/xe_oa.c
@@ -1923,37 +1923,45 @@ u16 xe_oa_unit_id(struct xe_hw_engine *hwe)
 		hwe->oa_unit->oa_unit_id : U16_MAX;
 }
 
+/* A hwe must be assigned to stream/oa_unit for batch submissions */
 static int xe_oa_assign_hwe(struct xe_oa *oa, struct xe_oa_open_param *param)
 {
-	struct xe_gt *gt;
-	int i, ret = 0;
+	struct xe_hw_engine *hwe;
+	enum xe_hw_engine_id id;
+	int ret = 0;
+
+	/* If not provided, OA unit defaults to OA unit 0 as per uapi */
+	if (!param->oa_unit)
+		param->oa_unit = &xe_device_get_gt(oa->xe, 0)->oa.oa_unit[0];
 
+	/* When we have an exec_q, get hwe from the exec_q */
 	if (param->exec_q) {
-		/* When we have an exec_q, get hwe from the exec_q */
 		param->hwe = xe_gt_hw_engine(param->exec_q->gt, param->exec_q->class,
 					     param->engine_instance, true);
-	} else {
-		struct xe_hw_engine *hwe;
-		enum xe_hw_engine_id id;
-
-		/* Else just get the first hwe attached to the oa unit */
-		for_each_gt(gt, oa->xe, i) {
-			for_each_hw_engine(hwe, gt, id) {
-				if (hwe->oa_unit == param->oa_unit) {
-					param->hwe = hwe;
-					goto out;
-				}
-			}
-		}
+		if (!param->hwe || param->hwe->oa_unit != param->oa_unit)
+			goto err;
+		goto out;
 	}
-out:
-	if (!param->hwe || param->hwe->oa_unit != param->oa_unit) {
-		drm_dbg(&oa->xe->drm, "Unable to find hwe (%d, %d) for OA unit ID %d\n",
-			param->exec_q ? param->exec_q->class : -1,
-			param->engine_instance, param->oa_unit->oa_unit_id);
-		ret = -EINVAL;
+
+	/* Else just get the first hwe attached to the oa unit */
+	for_each_hw_engine(hwe, param->oa_unit->gt, id) {
+		if (hwe->oa_unit == param->oa_unit) {
+			param->hwe = hwe;
+			goto out;
+		}
 	}
 
+	/* If we still didn't find a hwe, just get one from the same gt */
+	for_each_hw_engine(hwe, param->oa_unit->gt, id) {
+		param->hwe = hwe;
+		goto out;
+	}
+err:
+	drm_dbg(&oa->xe->drm, "Unable to find hwe (%d, %d) for OA unit ID %d\n",
+		param->exec_q ? param->exec_q->class : -1,
+		param->engine_instance, param->oa_unit->oa_unit_id);
+	ret = -EINVAL;
+out:
 	return ret;
 }
 
@@ -2578,6 +2586,8 @@ static void __xe_oa_init_oa_units(struct xe_gt *gt)
 				DRM_XE_OA_UNIT_TYPE_OAM_SAG : DRM_XE_OA_UNIT_TYPE_OAM;
 		}
 
+		u->gt = gt;
+
 		xe_mmio_write32(&gt->mmio, u->regs.oa_ctrl, 0);
 
 		/* Ensure MMIO trigger remains disabled till there is a stream */
diff --git a/drivers/gpu/drm/xe/xe_oa_types.h b/drivers/gpu/drm/xe/xe_oa_types.h
index a01c85931e2a5..2628f78c4e8dc 100644
--- a/drivers/gpu/drm/xe/xe_oa_types.h
+++ b/drivers/gpu/drm/xe/xe_oa_types.h
@@ -95,6 +95,9 @@ struct xe_oa_unit {
 	/** @oa_unit_id: identifier for the OA unit */
 	u16 oa_unit_id;
 
+	/** @gt: gt associated with the OA unit */
+	struct xe_gt *gt;
+
 	/** @type: Type of OA unit - OAM, OAG etc. */
 	enum drm_xe_oa_unit_type type;
 
-- 
2.48.1


^ permalink raw reply related	[flat|nested] 24+ messages in thread

* [PATCH 5/5] drm/xe/oa: Enable OAM latency measurement
  2025-06-03 20:21 [PATCH v3 0/5] Enable media OA Ashutosh Dixit
                   ` (3 preceding siblings ...)
  2025-06-03 20:21 ` [PATCH 4/5] drm/xe/oa: Assign hwe for OAM_SAG Ashutosh Dixit
@ 2025-06-03 20:21 ` Ashutosh Dixit
  2025-06-05 16:25   ` Umesh Nerlige Ramappa
  2025-06-03 20:26 ` ✓ CI.Patch_applied: success for Enable media OA Patchwork
                   ` (2 subsequent siblings)
  7 siblings, 1 reply; 24+ messages in thread
From: Ashutosh Dixit @ 2025-06-03 20:21 UTC (permalink / raw)
  To: intel-xe; +Cc: Umesh Nerlige Ramappa

Enable OAM latency measurement for Xe3+ platforms.

Bspec: 58840

v2: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG

Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
---
 drivers/gpu/drm/xe/regs/xe_oa_regs.h |  3 +++
 drivers/gpu/drm/xe/xe_oa.c           | 11 ++++++++++-
 2 files changed, 13 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/xe/regs/xe_oa_regs.h b/drivers/gpu/drm/xe/regs/xe_oa_regs.h
index a79ad2da070c2..e693a50706f84 100644
--- a/drivers/gpu/drm/xe/regs/xe_oa_regs.h
+++ b/drivers/gpu/drm/xe/regs/xe_oa_regs.h
@@ -97,4 +97,7 @@
 #define OAM_STATUS(base)			XE_REG((base) + OAM_STATUS_OFFSET)
 #define OAM_MMIO_TRG(base)			XE_REG((base) + OAM_MMIO_TRG_OFFSET)
 
+#define OAM_COMPRESSION_T3_CONTROL		XE_REG(0x1c2e00)
+#define  OAM_LAT_MEASURE_ENABLE			REG_BIT(4)
+
 #endif
diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
index 35157424010bb..5aa68bd63b00d 100644
--- a/drivers/gpu/drm/xe/xe_oa.c
+++ b/drivers/gpu/drm/xe/xe_oa.c
@@ -844,6 +844,11 @@ static void xe_oa_disable_metric_set(struct xe_oa_stream *stream)
 
 	/* Reset PMON Enable to save power. */
 	xe_mmio_rmw32(mmio, XELPMP_SQCNT1, sqcnt1, 0);
+
+	if ((stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAM ||
+	     stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAM_SAG) &&
+	    GRAPHICS_VER(stream->oa->xe) >= 30)
+		xe_mmio_rmw32(mmio, OAM_COMPRESSION_T3_CONTROL, OAM_LAT_MEASURE_ENABLE, 0);
 }
 
 static void xe_oa_stream_destroy(struct xe_oa_stream *stream)
@@ -1111,9 +1116,13 @@ static int xe_oa_enable_metric_set(struct xe_oa_stream *stream)
 	 */
 	sqcnt1 = SQCNT1_PMON_ENABLE |
 		 (HAS_OA_BPC_REPORTING(stream->oa->xe) ? SQCNT1_OABPC : 0);
-
 	xe_mmio_rmw32(mmio, XELPMP_SQCNT1, 0, sqcnt1);
 
+	if ((stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAM ||
+	     stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAM_SAG) &&
+	    GRAPHICS_VER(stream->oa->xe) >= 30)
+		xe_mmio_rmw32(mmio, OAM_COMPRESSION_T3_CONTROL, 0, OAM_LAT_MEASURE_ENABLE);
+
 	/* Configure OAR/OAC */
 	if (stream->exec_q) {
 		ret = xe_oa_configure_oa_context(stream, true);
-- 
2.48.1


^ permalink raw reply related	[flat|nested] 24+ messages in thread

* ✓ CI.Patch_applied: success for Enable media OA
  2025-06-03 20:21 [PATCH v3 0/5] Enable media OA Ashutosh Dixit
                   ` (4 preceding siblings ...)
  2025-06-03 20:21 ` [PATCH 5/5] drm/xe/oa: Enable OAM latency measurement Ashutosh Dixit
@ 2025-06-03 20:26 ` Patchwork
  2025-06-03 20:26 ` ✓ CI.checkpatch: " Patchwork
  2025-06-03 20:27 ` ✗ CI.KUnit: failure " Patchwork
  7 siblings, 0 replies; 24+ messages in thread
From: Patchwork @ 2025-06-03 20:26 UTC (permalink / raw)
  To: Ashutosh Dixit; +Cc: intel-xe

== Series Details ==

Series: Enable media OA
URL   : https://patchwork.freedesktop.org/series/149806/
State : success

== Summary ==

=== Applying kernel patches on branch 'drm-tip' with base: ===
Base commit: ba486e3b10ce drm-tip: 2025y-06m-03d-16h-48m-17s UTC integration manifest
=== git am output follows ===
Applying: drm/xe/oa/uapi: Expose media OA units
Applying: drm/xe/oa: Print hwe to OA unit mapping
Applying: drm/xe/oa: Introduce stream->oa_unit
Applying: drm/xe/oa: Assign hwe for OAM_SAG
Applying: drm/xe/oa: Enable OAM latency measurement



^ permalink raw reply	[flat|nested] 24+ messages in thread

* ✓ CI.checkpatch: success for Enable media OA
  2025-06-03 20:21 [PATCH v3 0/5] Enable media OA Ashutosh Dixit
                   ` (5 preceding siblings ...)
  2025-06-03 20:26 ` ✓ CI.Patch_applied: success for Enable media OA Patchwork
@ 2025-06-03 20:26 ` Patchwork
  2025-06-03 20:27 ` ✗ CI.KUnit: failure " Patchwork
  7 siblings, 0 replies; 24+ messages in thread
From: Patchwork @ 2025-06-03 20:26 UTC (permalink / raw)
  To: Ashutosh Dixit; +Cc: intel-xe

== Series Details ==

Series: Enable media OA
URL   : https://patchwork.freedesktop.org/series/149806/
State : success

== Summary ==

+ KERNEL=/kernel
+ git clone https://gitlab.freedesktop.org/drm/maintainer-tools mt
Cloning into 'mt'...
warning: redirecting to https://gitlab.freedesktop.org/drm/maintainer-tools.git/
+ git -C mt rev-list -n1 origin/master
202708c00696422fd217223bb679a353a5936e23
+ cd /kernel
+ git config --global --add safe.directory /kernel
+ git log -n1
commit 6664f65d30a33982bd2e9435dc3c79ce2b1e9b64
Author: Ashutosh Dixit <ashutosh.dixit@intel.com>
Date:   Tue Jun 3 13:21:33 2025 -0700

    drm/xe/oa: Enable OAM latency measurement
    
    Enable OAM latency measurement for Xe3+ platforms.
    
    Bspec: 58840
    
    v2: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
    
    Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
+ /mt/dim checkpatch ba486e3b10ce5b4ee4d1ffc58aa4cc3b669c02a3 drm-intel
4c6f15bf5871 drm/xe/oa/uapi: Expose media OA units
373452cb87d1 drm/xe/oa: Print hwe to OA unit mapping
6fdad47337fc drm/xe/oa: Introduce stream->oa_unit
afc96b9e539c drm/xe/oa: Assign hwe for OAM_SAG
6664f65d30a3 drm/xe/oa: Enable OAM latency measurement



^ permalink raw reply	[flat|nested] 24+ messages in thread

* ✗ CI.KUnit: failure for Enable media OA
  2025-06-03 20:21 [PATCH v3 0/5] Enable media OA Ashutosh Dixit
                   ` (6 preceding siblings ...)
  2025-06-03 20:26 ` ✓ CI.checkpatch: " Patchwork
@ 2025-06-03 20:27 ` Patchwork
  7 siblings, 0 replies; 24+ messages in thread
From: Patchwork @ 2025-06-03 20:27 UTC (permalink / raw)
  To: Ashutosh Dixit; +Cc: intel-xe

== Series Details ==

Series: Enable media OA
URL   : https://patchwork.freedesktop.org/series/149806/
State : failure

== Summary ==

+ trap cleanup EXIT
+ /kernel/tools/testing/kunit/kunit.py run --kunitconfig /kernel/drivers/gpu/drm/xe/.kunitconfig
[20:26:54] Configuring KUnit Kernel ...
Generating .config ...
Populating config with:
$ make ARCH=um O=.kunit olddefconfig
[20:26:58] Building KUnit Kernel ...
Populating config with:
$ make ARCH=um O=.kunit olddefconfig
Building with:
$ make all compile_commands.json scripts_gdb ARCH=um O=.kunit --jobs=48
[20:27:25] Starting KUnit Kernel (1/1)...
[20:27:25] ============================================================
Running tests with:
$ .kunit/linux kunit.enable=1 mem=1G console=tty kunit_shutdown=halt
[20:27:25] ================== guc_buf (11 subtests) ===================
[20:27:25] [PASSED] test_smallest
[20:27:25] [PASSED] test_largest
[20:27:25] [PASSED] test_granular
[20:27:25] [PASSED] test_unique
[20:27:25] [PASSED] test_overlap
[20:27:25] [PASSED] test_reusable
[20:27:25] [PASSED] test_too_big
[20:27:25] [PASSED] test_flush
[20:27:25] [PASSED] test_lookup
[20:27:25] [PASSED] test_data
[20:27:25] [PASSED] test_class
[20:27:25] ===================== [PASSED] guc_buf =====================
[20:27:25] =================== guc_dbm (7 subtests) ===================
[20:27:25] [PASSED] test_empty
[20:27:25] [PASSED] test_default
[20:27:25] ======================== test_size  ========================
[20:27:25] [PASSED] 4
[20:27:25] [PASSED] 8
[20:27:25] [PASSED] 32
[20:27:25] [PASSED] 256
[20:27:25] ==================== [PASSED] test_size ====================
[20:27:25] ======================= test_reuse  ========================
[20:27:25] [PASSED] 4
[20:27:25] [PASSED] 8
[20:27:25] [PASSED] 32
[20:27:25] [PASSED] 256
[20:27:25] =================== [PASSED] test_reuse ====================
[20:27:25] =================== test_range_overlap  ====================
[20:27:25] [PASSED] 4
[20:27:25] [PASSED] 8
[20:27:25] [PASSED] 32
[20:27:25] [PASSED] 256
[20:27:25] =============== [PASSED] test_range_overlap ================
[20:27:25] =================== test_range_compact  ====================
[20:27:25] [PASSED] 4
[20:27:25] [PASSED] 8
[20:27:25] [PASSED] 32
[20:27:25] [PASSED] 256
[20:27:25] =============== [PASSED] test_range_compact ================
[20:27:25] ==================== test_range_spare  =====================
[20:27:25] [PASSED] 4
[20:27:25] [PASSED] 8
[20:27:25] [PASSED] 32
[20:27:25] [PASSED] 256
[20:27:25] ================ [PASSED] test_range_spare =================
[20:27:25] ===================== [PASSED] guc_dbm =====================
[20:27:25] =================== guc_idm (6 subtests) ===================
[20:27:25] [PASSED] bad_init
[20:27:25] [PASSED] no_init
[20:27:25] [PASSED] init_fini
[20:27:25] [PASSED] check_used
[20:27:25] [PASSED] check_quota
[20:27:25] [PASSED] check_all
[20:27:25] ===================== [PASSED] guc_idm =====================
[20:27:25] ================== no_relay (3 subtests) ===================
[20:27:25] [PASSED] xe_drops_guc2pf_if_not_ready
[20:27:25] [PASSED] xe_drops_guc2vf_if_not_ready
[20:27:25] [PASSED] xe_rejects_send_if_not_ready
[20:27:25] ==================== [PASSED] no_relay =====================
[20:27:25] ================== pf_relay (14 subtests) ==================
[20:27:25] [PASSED] pf_rejects_guc2pf_too_short
[20:27:25] [PASSED] pf_rejects_guc2pf_too_long
[20:27:25] [PASSED] pf_rejects_guc2pf_no_payload
[20:27:25] [PASSED] pf_fails_no_payload
[20:27:25] [PASSED] pf_fails_bad_origin
[20:27:25] [PASSED] pf_fails_bad_type
[20:27:25] [PASSED] pf_txn_reports_error
[20:27:25] [PASSED] pf_txn_sends_pf2guc
[20:27:25] [PASSED] pf_sends_pf2guc
[20:27:25] [SKIPPED] pf_loopback_nop
[20:27:25] [SKIPPED] pf_loopback_echo
[20:27:25] [SKIPPED] pf_loopback_fail
[20:27:25] [SKIPPED] pf_loopback_busy
[20:27:25] [SKIPPED] pf_loopback_retry
[20:27:25] ==================== [PASSED] pf_relay =====================
[20:27:25] ================== vf_relay (3 subtests) ===================
[20:27:25] [PASSED] vf_rejects_guc2vf_too_short
[20:27:25] [PASSED] vf_rejects_guc2vf_too_long
[20:27:25] [PASSED] vf_rejects_guc2vf_no_payload
[20:27:25] ==================== [PASSED] vf_relay =====================
[20:27:25] ================= pf_service (11 subtests) =================
[20:27:25] [PASSED] pf_negotiate_any
[20:27:25] [PASSED] pf_negotiate_base_match
[20:27:25] [PASSED] pf_negotiate_base_newer
[20:27:25] [PASSED] pf_negotiate_base_next
[20:27:25] [SKIPPED] pf_negotiate_base_older
[20:27:25] [PASSED] pf_negotiate_base_prev
[20:27:25] [PASSED] pf_negotiate_latest_match
[20:27:25] [PASSED] pf_negotiate_latest_newer
[20:27:25] [PASSED] pf_negotiate_latest_next
[20:27:25] [SKIPPED] pf_negotiate_latest_older
[20:27:25] [SKIPPED] pf_negotiate_latest_prev
[20:27:25] =================== [PASSED] pf_service ====================
[20:27:25] ===================== lmtt (1 subtest) =====================
[20:27:25] ======================== test_ops  =========================
[20:27:25] [PASSED] 2-level
[20:27:25] [PASSED] multi-level
[20:27:25] ==================== [PASSED] test_ops =====================
[20:27:25] ====================== [PASSED] lmtt =======================
[20:27:25] =================== xe_mocs (2 subtests) ===================
[20:27:25] ================ xe_live_mocs_kernel_kunit  ================
[20:27:25] =========== [SKIPPED] xe_live_mocs_kernel_kunit ============
[20:27:25] ================ xe_live_mocs_reset_kunit  =================
[20:27:25] ============ [SKIPPED] xe_live_mocs_reset_kunit ============
[20:27:25] ==================== [SKIPPED] xe_mocs =====================
[20:27:25] ================= xe_migrate (2 subtests) ==================
[20:27:25] ================= xe_migrate_sanity_kunit  =================
[20:27:25] ============ [SKIPPED] xe_migrate_sanity_kunit =============
[20:27:25] ================== xe_validate_ccs_kunit  ==================
[20:27:25] ============= [SKIPPED] xe_validate_ccs_kunit ==============
[20:27:25] =================== [SKIPPED] xe_migrate ===================
[20:27:25] ================== xe_dma_buf (1 subtest) ==================
[20:27:25] ==================== xe_dma_buf_kunit  =====================
[20:27:25] ================ [SKIPPED] xe_dma_buf_kunit ================
[20:27:25] =================== [SKIPPED] xe_dma_buf ===================
[20:27:25] ================= xe_bo_shrink (1 subtest) =================
[20:27:25] =================== xe_bo_shrink_kunit  ====================
[20:27:25] =============== [SKIPPED] xe_bo_shrink_kunit ===============
[20:27:25] ================== [SKIPPED] xe_bo_shrink ==================
[20:27:25] ==================== xe_bo (2 subtests) ====================
[20:27:25] ================== xe_ccs_migrate_kunit  ===================
[20:27:25] ============== [SKIPPED] xe_ccs_migrate_kunit ==============
[20:27:25] ==================== xe_bo_evict_kunit  ====================
[20:27:25] =============== [SKIPPED] xe_bo_evict_kunit ================
[20:27:25] ===================== [SKIPPED] xe_bo ======================
[20:27:25] ==================== args (11 subtests) ====================
[20:27:25] [PASSED] count_args_test
[20:27:25] [PASSED] call_args_example
[20:27:25] [PASSED] call_args_test
[20:27:25] [PASSED] drop_first_arg_example
[20:27:25] [PASSED] drop_first_arg_test
[20:27:25] [PASSED] first_arg_example
[20:27:25] [PASSED] first_arg_test
[20:27:25] [PASSED] last_arg_example
[20:27:25] [PASSED] last_arg_test
[20:27:25] [PASSED] pick_arg_example
[20:27:25] [PASSED] sep_comma_example
[20:27:25] ====================== [PASSED] args =======================
[20:27:25] =================== xe_pci (2 subtests) ====================
[20:27:25] [PASSED] xe_gmdid_graphics_ip
[20:27:25] [PASSED] xe_gmdid_media_ip
[20:27:25] ===================== [PASSED] xe_pci ======================
[20:27:25] =================== xe_rtp (2 subtests) ====================
[20:27:25] =============== xe_rtp_process_to_sr_tests  ================
[20:27:25] [PASSED] coalesce-same-reg
[20:27:25] [PASSED] no-match-no-add
[20:27:25] [PASSED] match-or
[20:27:25] [PASSED] match-or-xfail
[20:27:25] [PASSED] no-match-no-add-multiple-rules
[20:27:25] [PASSED] two-regs-two-entries
[20:27:25] [PASSED] clr-one-set-other
[20:27:25] [PASSED] set-field
[20:27:25] [PASSED] conflict-duplicate
[20:27:25] [PASSED] conflict-not-disjoint
stty: 'standard input': Inappropriate ioctl for device
[20:27:25] [PASSED] conflict-reg-type
[20:27:25] =========== [PASSED] xe_rtp_process_to_sr_tests ============
[20:27:25] ================== xe_rtp_process_tests  ===================
[20:27:25] [PASSED] active1
[20:27:25] [PASSED] active2
[20:27:25] [PASSED] active-inactive
[20:27:25] [PASSED] inactive-active
[20:27:25] [PASSED] inactive-1st_or_active-inactive
[20:27:25] [PASSED] inactive-2nd_or_active-inactive
[20:27:25] [PASSED] inactive-last_or_active-inactive
[20:27:25] [PASSED] inactive-no_or_active-inactive
[20:27:25] ============== [PASSED] xe_rtp_process_tests ===============
[20:27:25] ===================== [PASSED] xe_rtp ======================
[20:27:25] ==================== xe_wa (1 subtest) =====================
[20:27:25] ======================== xe_wa_gt  =========================
[20:27:25] [PASSED] TIGERLAKE (B0)
[20:27:25] [PASSED] DG1 (A0)
[20:27:25] [PASSED] DG1 (B0)
[20:27:25] [PASSED] ALDERLAKE_S (A0)
[20:27:25] [PASSED] ALDERLAKE_S (B0)
[20:27:25] [PASSED] ALDERLAKE_S (C0)
[20:27:25] [PASSED] ALDERLAKE_S (D0)
[20:27:25] [PASSED] ALDERLAKE_P (A0)
[20:27:25] [PASSED] ALDERLAKE_P (B0)
[20:27:25] [PASSED] ALDERLAKE_P (C0)
[20:27:25] [PASSED] ALDERLAKE_S_RPLS (D0)
[20:27:25] [PASSED] ALDERLAKE_P_RPLU (E0)
[20:27:25] [PASSED] DG2_G10 (C0)
[20:27:25] [PASSED] DG2_G11 (B1)
[20:27:25] [PASSED] DG2_G12 (A1)
[20:27:25] [PASSED] METEORLAKE (g:A0, m:A0)
[20:27:25] [PASSED] METEORLAKE (g:A0, m:A0)
[20:27:25] [PASSED] METEORLAKE (g:A0, m:A0)
[20:27:25] [PASSED] LUNARLAKE (g:A0, m:A0)
[20:27:25] [PASSED] LUNARLAKE (g:B0, m:A0)
[20:27:25] [PASSED] BATTLEMAGE (g:A0, m:A1)
[20:27:25] ==================== [PASSED] xe_wa_gt =====================
[20:27:25] ====================== [PASSED] xe_wa ======================
[20:27:25] ============================================================
[20:27:25] Testing complete. Ran 133 tests: passed: 117, skipped: 16
[20:27:25] Elapsed time: 31.022s total, 4.144s configuring, 26.561s building, 0.297s running

+ /kernel/tools/testing/kunit/kunit.py run --kunitconfig /kernel/drivers/gpu/drm/tests/.kunitconfig
[20:27:25] Configuring KUnit Kernel ...
Regenerating .config ...
Populating config with:
$ make ARCH=um O=.kunit olddefconfig
[20:27:27] Building KUnit Kernel ...
Populating config with:
$ make ARCH=um O=.kunit olddefconfig
Building with:
$ make all compile_commands.json scripts_gdb ARCH=um O=.kunit --jobs=48
[20:27:48] Starting KUnit Kernel (1/1)...
[20:27:48] ============================================================
Running tests with:
$ .kunit/linux kunit.enable=1 mem=1G console=tty kunit_shutdown=halt
[20:27:48] == drm_test_atomic_get_connector_for_encoder (1 subtest) ===
[20:27:48] [PASSED] drm_test_drm_atomic_get_connector_for_encoder
[20:27:48] ==== [PASSED] drm_test_atomic_get_connector_for_encoder ====
[20:27:48] =========== drm_validate_clone_mode (2 subtests) ===========
[20:27:48] ============== drm_test_check_in_clone_mode  ===============
[20:27:48] [PASSED] in_clone_mode
[20:27:48] [PASSED] not_in_clone_mode
[20:27:48] ========== [PASSED] drm_test_check_in_clone_mode ===========
[20:27:48] =============== drm_test_check_valid_clones  ===============
[20:27:48] [PASSED] not_in_clone_mode
[20:27:48] [PASSED] valid_clone
[20:27:48] [PASSED] invalid_clone
[20:27:48] =========== [PASSED] drm_test_check_valid_clones ===========
[20:27:48] ============= [PASSED] drm_validate_clone_mode =============
[20:27:48] ============= drm_validate_modeset (1 subtest) =============
[20:27:48] [PASSED] drm_test_check_connector_changed_modeset
[20:27:48] ============== [PASSED] drm_validate_modeset ===============
[20:27:48] ====== drm_test_bridge_get_current_state (2 subtests) ======
[20:27:48] [PASSED] drm_test_drm_bridge_get_current_state_atomic
[20:27:48] [PASSED] drm_test_drm_bridge_get_current_state_legacy
[20:27:48] ======== [PASSED] drm_test_bridge_get_current_state ========
[20:27:48] ====== drm_test_bridge_helper_reset_crtc (3 subtests) ======
[20:27:48] [PASSED] drm_test_drm_bridge_helper_reset_crtc_atomic
[20:27:48] [PASSED] drm_test_drm_bridge_helper_reset_crtc_atomic_disabled
[20:27:48] [PASSED] drm_test_drm_bridge_helper_reset_crtc_legacy
[20:27:48] ======== [PASSED] drm_test_bridge_helper_reset_crtc ========
[20:27:48] ================== drm_buddy (7 subtests) ==================
[20:27:48] [PASSED] drm_test_buddy_alloc_limit
[20:27:48] [PASSED] drm_test_buddy_alloc_optimistic
[20:27:48] [PASSED] drm_test_buddy_alloc_pessimistic
[20:27:48] [PASSED] drm_test_buddy_alloc_pathological
[20:27:48] [PASSED] drm_test_buddy_alloc_contiguous
[20:27:48] [PASSED] drm_test_buddy_alloc_clear
[20:27:48] [PASSED] drm_test_buddy_alloc_range_bias
[20:27:48] ==================== [PASSED] drm_buddy ====================
[20:27:48] ============= drm_cmdline_parser (40 subtests) =============
[20:27:48] [PASSED] drm_test_cmdline_force_d_only
[20:27:48] [PASSED] drm_test_cmdline_force_D_only_dvi
[20:27:48] [PASSED] drm_test_cmdline_force_D_only_hdmi
[20:27:48] [PASSED] drm_test_cmdline_force_D_only_not_digital
[20:27:48] [PASSED] drm_test_cmdline_force_e_only
[20:27:48] [PASSED] drm_test_cmdline_res
[20:27:48] [PASSED] drm_test_cmdline_res_vesa
[20:27:48] [PASSED] drm_test_cmdline_res_vesa_rblank
[20:27:48] [PASSED] drm_test_cmdline_res_rblank
[20:27:48] [PASSED] drm_test_cmdline_res_bpp
[20:27:48] [PASSED] drm_test_cmdline_res_refresh
[20:27:48] [PASSED] drm_test_cmdline_res_bpp_refresh
[20:27:48] [PASSED] drm_test_cmdline_res_bpp_refresh_interlaced
[20:27:48] [PASSED] drm_test_cmdline_res_bpp_refresh_margins
[20:27:48] [PASSED] drm_test_cmdline_res_bpp_refresh_force_off
[20:27:48] [PASSED] drm_test_cmdline_res_bpp_refresh_force_on
[20:27:48] [PASSED] drm_test_cmdline_res_bpp_refresh_force_on_analog
[20:27:48] [PASSED] drm_test_cmdline_res_bpp_refresh_force_on_digital
[20:27:48] [PASSED] drm_test_cmdline_res_bpp_refresh_interlaced_margins_force_on
[20:27:48] [PASSED] drm_test_cmdline_res_margins_force_on
[20:27:48] [PASSED] drm_test_cmdline_res_vesa_margins
[20:27:48] [PASSED] drm_test_cmdline_name
[20:27:48] [PASSED] drm_test_cmdline_name_bpp
[20:27:48] [PASSED] drm_test_cmdline_name_option
[20:27:48] [PASSED] drm_test_cmdline_name_bpp_option
[20:27:48] [PASSED] drm_test_cmdline_rotate_0
[20:27:48] [PASSED] drm_test_cmdline_rotate_90
[20:27:48] [PASSED] drm_test_cmdline_rotate_180
[20:27:48] [PASSED] drm_test_cmdline_rotate_270
[20:27:48] [PASSED] drm_test_cmdline_hmirror
[20:27:48] [PASSED] drm_test_cmdline_vmirror
[20:27:48] [PASSED] drm_test_cmdline_margin_options
[20:27:48] [PASSED] drm_test_cmdline_multiple_options
[20:27:48] [PASSED] drm_test_cmdline_bpp_extra_and_option
[20:27:48] [PASSED] drm_test_cmdline_extra_and_option
[20:27:48] [PASSED] drm_test_cmdline_freestanding_options
[20:27:48] [PASSED] drm_test_cmdline_freestanding_force_e_and_options
[20:27:48] [PASSED] drm_test_cmdline_panel_orientation
[20:27:48] ================ drm_test_cmdline_invalid  =================
[20:27:48] [PASSED] margin_only
[20:27:48] [PASSED] interlace_only
[20:27:48] [PASSED] res_missing_x
[20:27:48] [PASSED] res_missing_y
[20:27:48] [PASSED] res_bad_y
[20:27:48] [PASSED] res_missing_y_bpp
[20:27:48] [PASSED] res_bad_bpp
[20:27:48] [PASSED] res_bad_refresh
[20:27:48] [PASSED] res_bpp_refresh_force_on_off
[20:27:48] [PASSED] res_invalid_mode
[20:27:48] [PASSED] res_bpp_wrong_place_mode
[20:27:48] [PASSED] name_bpp_refresh
[20:27:48] [PASSED] name_refresh
[20:27:48] [PASSED] name_refresh_wrong_mode
[20:27:48] [PASSED] name_refresh_invalid_mode
[20:27:48] [PASSED] rotate_multiple
[20:27:48] [PASSED] rotate_invalid_val
[20:27:48] [PASSED] rotate_truncated
[20:27:48] [PASSED] invalid_option
[20:27:48] [PASSED] invalid_tv_option
[20:27:48] [PASSED] truncated_tv_option
[20:27:48] ============ [PASSED] drm_test_cmdline_invalid =============
[20:27:48] =============== drm_test_cmdline_tv_options  ===============
[20:27:48] [PASSED] NTSC
[20:27:48] [PASSED] NTSC_443
[20:27:48] [PASSED] NTSC_J
[20:27:48] [PASSED] PAL
[20:27:48] [PASSED] PAL_M
[20:27:48] [PASSED] PAL_N
[20:27:48] [PASSED] SECAM
[20:27:48] [PASSED] MONO_525
[20:27:48] [PASSED] MONO_625
[20:27:48] =========== [PASSED] drm_test_cmdline_tv_options ===========
[20:27:48] =============== [PASSED] drm_cmdline_parser ================
[20:27:48] ========== drmm_connector_hdmi_init (20 subtests) ==========
[20:27:48] [PASSED] drm_test_connector_hdmi_init_valid
[20:27:48] [PASSED] drm_test_connector_hdmi_init_bpc_8
[20:27:48] [PASSED] drm_test_connector_hdmi_init_bpc_10
[20:27:48] [PASSED] drm_test_connector_hdmi_init_bpc_12
[20:27:48] [PASSED] drm_test_connector_hdmi_init_bpc_invalid
[20:27:48] [PASSED] drm_test_connector_hdmi_init_bpc_null
[20:27:48] [PASSED] drm_test_connector_hdmi_init_formats_empty
[20:27:48] [PASSED] drm_test_connector_hdmi_init_formats_no_rgb
[20:27:48] === drm_test_connector_hdmi_init_formats_yuv420_allowed  ===
[20:27:48] [PASSED] supported_formats=0x9 yuv420_allowed=1
[20:27:48] [PASSED] supported_formats=0x9 yuv420_allowed=0
[20:27:48] [PASSED] supported_formats=0x3 yuv420_allowed=1
[20:27:48] [PASSED] supported_formats=0x3 yuv420_allowed=0
[20:27:48] === [PASSED] drm_test_connector_hdmi_init_formats_yuv420_allowed ===
[20:27:48] [PASSED] drm_test_connector_hdmi_init_null_ddc
[20:27:48] [PASSED] drm_test_connector_hdmi_init_null_product
[20:27:48] [PASSED] drm_test_connector_hdmi_init_null_vendor
[20:27:48] [PASSED] drm_test_connector_hdmi_init_product_length_exact
[20:27:48] [PASSED] drm_test_connector_hdmi_init_product_length_too_long
[20:27:48] [PASSED] drm_test_connector_hdmi_init_product_valid
[20:27:48] [PASSED] drm_test_connector_hdmi_init_vendor_length_exact
[20:27:48] [PASSED] drm_test_connector_hdmi_init_vendor_length_too_long
[20:27:48] [PASSED] drm_test_connector_hdmi_init_vendor_valid
[20:27:48] ========= drm_test_connector_hdmi_init_type_valid  =========
[20:27:48] [PASSED] HDMI-A
[20:27:48] [PASSED] HDMI-B
[20:27:48] ===== [PASSED] drm_test_connector_hdmi_init_type_valid =====
[20:27:48] ======== drm_test_connector_hdmi_init_type_invalid  ========
[20:27:48] [PASSED] Unknown
[20:27:48] [PASSED] VGA
[20:27:48] [PASSED] DVI-I
[20:27:48] [PASSED] DVI-D
[20:27:48] [PASSED] DVI-A
[20:27:48] [PASSED] Composite
[20:27:48] [PASSED] SVIDEO
[20:27:48] [PASSED] LVDS
[20:27:48] [PASSED] Component
[20:27:48] [PASSED] DIN
[20:27:48] [PASSED] DP
[20:27:48] [PASSED] TV
[20:27:48] [PASSED] eDP
[20:27:48] [PASSED] Virtual
[20:27:48] [PASSED] DSI
[20:27:48] [PASSED] DPI
[20:27:48] [PASSED] Writeback
[20:27:48] [PASSED] SPI
[20:27:48] [PASSED] USB
[20:27:48] ==== [PASSED] drm_test_connector_hdmi_init_type_invalid ====
[20:27:48] ============ [PASSED] drmm_connector_hdmi_init =============
[20:27:48] ============= drmm_connector_init (3 subtests) =============
[20:27:48] [PASSED] drm_test_drmm_connector_init
[20:27:48] [PASSED] drm_test_drmm_connector_init_null_ddc
[20:27:48] ========= drm_test_drmm_connector_init_type_valid  =========
[20:27:48] [PASSED] Unknown
[20:27:48] [PASSED] VGA
[20:27:48] [PASSED] DVI-I
[20:27:48] [PASSED] DVI-D
[20:27:48] [PASSED] DVI-A
[20:27:48] [PASSED] Composite
[20:27:48] [PASSED] SVIDEO
[20:27:48] [PASSED] LVDS
[20:27:48] [PASSED] Component
[20:27:48] [PASSED] DIN
[20:27:48] [PASSED] DP
[20:27:48] [PASSED] HDMI-A
[20:27:48] [PASSED] HDMI-B
[20:27:48] [PASSED] TV
[20:27:48] [PASSED] eDP
[20:27:48] [PASSED] Virtual
[20:27:48] [PASSED] DSI
[20:27:48] [PASSED] DPI
[20:27:48] [PASSED] Writeback
[20:27:48] [PASSED] SPI
[20:27:48] [PASSED] USB
[20:27:48] ===== [PASSED] drm_test_drmm_connector_init_type_valid =====
[20:27:48] =============== [PASSED] drmm_connector_init ===============
[20:27:48] ========= drm_connector_dynamic_init (6 subtests) ==========
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_init
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_init_null_ddc
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_init_not_added
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_init_properties
[20:27:48] ===== drm_test_drm_connector_dynamic_init_type_valid  ======
[20:27:48] [PASSED] Unknown
[20:27:48] [PASSED] VGA
[20:27:48] [PASSED] DVI-I
[20:27:48] [PASSED] DVI-D
[20:27:48] [PASSED] DVI-A
[20:27:48] [PASSED] Composite
[20:27:48] [PASSED] SVIDEO
[20:27:48] [PASSED] LVDS
[20:27:48] [PASSED] Component
[20:27:48] [PASSED] DIN
[20:27:48] [PASSED] DP
[20:27:48] [PASSED] HDMI-A
[20:27:48] [PASSED] HDMI-B
[20:27:48] [PASSED] TV
[20:27:48] [PASSED] eDP
[20:27:48] [PASSED] Virtual
[20:27:48] [PASSED] DSI
[20:27:48] [PASSED] DPI
[20:27:48] [PASSED] Writeback
[20:27:48] [PASSED] SPI
[20:27:48] [PASSED] USB
[20:27:48] = [PASSED] drm_test_drm_connector_dynamic_init_type_valid ==
[20:27:48] ======== drm_test_drm_connector_dynamic_init_name  =========
[20:27:48] [PASSED] Unknown
[20:27:48] [PASSED] VGA
[20:27:48] [PASSED] DVI-I
[20:27:48] [PASSED] DVI-D
[20:27:48] [PASSED] DVI-A
[20:27:48] [PASSED] Composite
[20:27:48] [PASSED] SVIDEO
[20:27:48] [PASSED] LVDS
[20:27:48] [PASSED] Component
[20:27:48] [PASSED] DIN
[20:27:48] [PASSED] DP
[20:27:48] [PASSED] HDMI-A
[20:27:48] [PASSED] HDMI-B
[20:27:48] [PASSED] TV
[20:27:48] [PASSED] eDP
[20:27:48] [PASSED] Virtual
[20:27:48] [PASSED] DSI
[20:27:48] [PASSED] DPI
[20:27:48] [PASSED] Writeback
[20:27:48] [PASSED] SPI
[20:27:48] [PASSED] USB
[20:27:48] ==== [PASSED] drm_test_drm_connector_dynamic_init_name =====
[20:27:48] =========== [PASSED] drm_connector_dynamic_init ============
[20:27:48] ==== drm_connector_dynamic_register_early (4 subtests) =====
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_early_on_list
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_early_defer
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_early_no_init
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_early_no_mode_object
[20:27:48] ====== [PASSED] drm_connector_dynamic_register_early =======
[20:27:48] ======= drm_connector_dynamic_register (7 subtests) ========
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_on_list
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_no_defer
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_no_init
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_mode_object
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_sysfs
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_sysfs_name
[20:27:48] [PASSED] drm_test_drm_connector_dynamic_register_debugfs
[20:27:48] ========= [PASSED] drm_connector_dynamic_register ==========
[20:27:48] = drm_connector_attach_broadcast_rgb_property (2 subtests) =
[20:27:48] [PASSED] drm_test_drm_connector_attach_broadcast_rgb_property
[20:27:48] [PASSED] drm_test_drm_connector_attach_broadcast_rgb_property_hdmi_connector
[20:27:48] === [PASSED] drm_connector_attach_broadcast_rgb_property ===
[20:27:48] ========== drm_get_tv_mode_from_name (2 subtests) ==========
[20:27:48] ========== drm_test_get_tv_mode_from_name_valid  ===========
[20:27:48] [PASSED] NTSC
[20:27:48] [PASSED] NTSC-443
[20:27:48] [PASSED] NTSC-J
[20:27:48] [PASSED] PAL
[20:27:48] [PASSED] PAL-M
[20:27:48] [PASSED] PAL-N
[20:27:48] [PASSED] SECAM
[20:27:48] [PASSED] Mono
[20:27:48] ====== [PASSED] drm_test_get_tv_mode_from_name_valid =======
[20:27:48] [PASSED] drm_test_get_tv_mode_from_name_truncated
[20:27:48] ============ [PASSED] drm_get_tv_mode_from_name ============
[20:27:48] = drm_test_connector_hdmi_compute_mode_clock (12 subtests) =
[20:27:48] [PASSED] drm_test_drm_hdmi_compute_mode_clock_rgb
[20:27:48] [PASSED] drm_test_drm_hdmi_compute_mode_clock_rgb_10bpc
[20:27:48] [PASSED] drm_test_drm_hdmi_compute_mode_clock_rgb_10bpc_vic_1
[20:27:48] [PASSED] drm_test_drm_hdmi_compute_mode_clock_rgb_12bpc
[20:27:48] [PASSED] drm_test_drm_hdmi_compute_mode_clock_rgb_12bpc_vic_1
[20:27:48] [PASSED] drm_test_drm_hdmi_compute_mode_clock_rgb_double
[20:27:48] = drm_test_connector_hdmi_compute_mode_clock_yuv420_valid  =
[20:27:48] [PASSED] VIC 96
[20:27:48] [PASSED] VIC 97
[20:27:48] [PASSED] VIC 101
[20:27:48] [PASSED] VIC 102
[20:27:48] [PASSED] VIC 106
[20:27:48] [PASSED] VIC 107
[20:27:48] === [PASSED] drm_test_connector_hdmi_compute_mode_clock_yuv420_valid ===
[20:27:48] [PASSED] drm_test_connector_hdmi_compute_mode_clock_yuv420_10_bpc
[20:27:48] [PASSED] drm_test_connector_hdmi_compute_mode_clock_yuv420_12_bpc
[20:27:48] [PASSED] drm_test_connector_hdmi_compute_mode_clock_yuv422_8_bpc
[20:27:48] [PASSED] drm_test_connector_hdmi_compute_mode_clock_yuv422_10_bpc
[20:27:48] [PASSED] drm_test_connector_hdmi_compute_mode_clock_yuv422_12_bpc
[20:27:48] === [PASSED] drm_test_connector_hdmi_compute_mode_clock ====
[20:27:48] == drm_hdmi_connector_get_broadcast_rgb_name (2 subtests) ==
[20:27:48] === drm_test_drm_hdmi_connector_get_broadcast_rgb_name  ====
[20:27:48] [PASSED] Automatic
[20:27:48] [PASSED] Full
[20:27:48] [PASSED] Limited 16:235
[20:27:48] === [PASSED] drm_test_drm_hdmi_connector_get_broadcast_rgb_name ===
[20:27:48] [PASSED] drm_test_drm_hdmi_connector_get_broadcast_rgb_name_invalid
[20:27:48] ==== [PASSED] drm_hdmi_connector_get_broadcast_rgb_name ====
[20:27:48] == drm_hdmi_connector_get_output_format_name (2 subtests) ==
[20:27:48] === drm_test_drm_hdmi_connector_get_output_format_name  ====
[20:27:48] [PASSED] RGB
[20:27:48] [PASSED] YUV 4:2:0
[20:27:48] [PASSED] YUV 4:2:2
[20:27:48] [PASSED] YUV 4:4:4
[20:27:48] === [PASSED] drm_test_drm_hdmi_connector_get_output_format_name ===
[20:27:48] [PASSED] drm_test_drm_hdmi_connector_get_output_format_name_invalid
[20:27:48] ==== [PASSED] drm_hdmi_connector_get_output_format_name ====
[20:27:48] ============= drm_damage_helper (21 subtests) ==============
[20:27:48] [PASSED] drm_test_damage_iter_no_damage
[20:27:48] [PASSED] drm_test_damage_iter_no_damage_fractional_src
[20:27:48] [PASSED] drm_test_damage_iter_no_damage_src_moved
[20:27:48] [PASSED] drm_test_damage_iter_no_damage_fractional_src_moved
[20:27:48] [PASSED] drm_test_damage_iter_no_damage_not_visible
[20:27:48] [PASSED] drm_test_damage_iter_no_damage_no_crtc
[20:27:48] [PASSED] drm_test_damage_iter_no_damage_no_fb
[20:27:48] [PASSED] drm_test_damage_iter_simple_damage
[20:27:48] [PASSED] drm_test_damage_iter_single_damage
[20:27:48] [PASSED] drm_test_damage_iter_single_damage_intersect_src
[20:27:48] [PASSED] drm_test_damage_iter_single_damage_outside_src
[20:27:48] [PASSED] drm_test_damage_iter_single_damage_fractional_src
[20:27:48] [PASSED] drm_test_damage_iter_single_damage_intersect_fractional_src
[20:27:48] [PASSED] drm_test_damage_iter_single_damage_outside_fractional_src
[20:27:48] [PASSED] drm_test_damage_iter_single_damage_src_moved
[20:27:48] [PASSED] drm_test_damage_iter_single_damage_fractional_src_moved
[20:27:48] [PASSED] drm_test_damage_iter_damage
[20:27:48] [PASSED] drm_test_damage_iter_damage_one_intersect
[20:27:48] [PASSED] drm_test_damage_iter_damage_one_outside
[20:27:48] [PASSED] drm_test_damage_iter_damage_src_moved
[20:27:48] [PASSED] drm_test_damage_iter_damage_not_visible
[20:27:48] ================ [PASSED] drm_damage_helper ================
[20:27:48] ============== drm_dp_mst_helper (3 subtests) ==============
[20:27:48] ============== drm_test_dp_mst_calc_pbn_mode  ==============
[20:27:48] [PASSED] Clock 154000 BPP 30 DSC disabled
[20:27:48] [PASSED] Clock 234000 BPP 30 DSC disabled
[20:27:48] [PASSED] Clock 297000 BPP 24 DSC disabled
[20:27:48] [PASSED] Clock 332880 BPP 24 DSC enabled
[20:27:48] [PASSED] Clock 324540 BPP 24 DSC enabled
[20:27:48] ========== [PASSED] drm_test_dp_mst_calc_pbn_mode ==========
[20:27:48] ============== drm_test_dp_mst_calc_pbn_div  ===============
[20:27:48] [PASSED] Link rate 2000000 lane count 4
[20:27:48] [PASSED] Link rate 2000000 lane count 2
[20:27:48] [PASSED] Link rate 2000000 lane count 1
[20:27:48] [PASSED] Link rate 1350000 lane count 4
[20:27:48] [PASSED] Link rate 1350000 lane count 2
[20:27:48] [PASSED] Link rate 1350000 lane count 1
[20:27:48] [PASSED] Link rate 1000000 lane count 4
[20:27:48] [PASSED] Link rate 1000000 lane count 2
[20:27:48] [PASSED] Link rate 1000000 lane count 1
[20:27:48] [PASSED] Link rate 810000 lane count 4
[20:27:48] [PASSED] Link rate 810000 lane count 2
[20:27:48] [PASSED] Link rate 810000 lane count 1
[20:27:48] [PASSED] Link rate 540000 lane count 4
[20:27:48] [PASSED] Link rate 540000 lane count 2
[20:27:48] [PASSED] Link rate 540000 lane count 1
[20:27:48] [PASSED] Link rate 270000 lane count 4
[20:27:48] [PASSED] Link rate 270000 lane count 2
[20:27:48] [PASSED] Link rate 270000 lane count 1
[20:27:48] [PASSED] Link rate 162000 lane count 4
[20:27:48] [PASSED] Link rate 162000 lane count 2
[20:27:48] [PASSED] Link rate 162000 lane count 1
[20:27:48] ========== [PASSED] drm_test_dp_mst_calc_pbn_div ===========
[20:27:48] ========= drm_test_dp_mst_sideband_msg_req_decode  =========
[20:27:48] [PASSED] DP_ENUM_PATH_RESOURCES with port number
[20:27:48] [PASSED] DP_POWER_UP_PHY with port number
[20:27:48] [PASSED] DP_POWER_DOWN_PHY with port number
[20:27:48] [PASSED] DP_ALLOCATE_PAYLOAD with SDP stream sinks
[20:27:48] [PASSED] DP_ALLOCATE_PAYLOAD with port number
[20:27:48] [PASSED] DP_ALLOCATE_PAYLOAD with VCPI
[20:27:48] [PASSED] DP_ALLOCATE_PAYLOAD with PBN
[20:27:48] [PASSED] DP_QUERY_PAYLOAD with port number
[20:27:48] [PASSED] DP_QUERY_PAYLOAD with VCPI
[20:27:48] [PASSED] DP_REMOTE_DPCD_READ with port number
[20:27:48] [PASSED] DP_REMOTE_DPCD_READ with DPCD address
[20:27:48] [PASSED] DP_REMOTE_DPCD_READ with max number of bytes
[20:27:48] [PASSED] DP_REMOTE_DPCD_WRITE with port number
[20:27:48] [PASSED] DP_REMOTE_DPCD_WRITE with DPCD address
[20:27:48] [PASSED] DP_REMOTE_DPCD_WRITE with data array
[20:27:48] [PASSED] DP_REMOTE_I2C_READ with port number
[20:27:48] [PASSED] DP_REMOTE_I2C_READ with I2C device ID
[20:27:48] [PASSED] DP_REMOTE_I2C_READ with transactions array
[20:27:48] [PASSED] DP_REMOTE_I2C_WRITE with port number
[20:27:48] [PASSED] DP_REMOTE_I2C_WRITE with I2C device ID
[20:27:48] [PASSED] DP_REMOTE_I2C_WRITE with data array
[20:27:48] [PASSED] DP_QUERY_STREAM_ENC_STATUS with stream ID
[20:27:48] [PASSED] DP_QUERY_STREAM_ENC_STATUS with client ID
[20:27:48] [PASSED] DP_QUERY_STREAM_ENC_STATUS with stream event
[20:27:48] [PASSED] DP_QUERY_STREAM_ENC_STATUS with valid stream event
[20:27:48] [PASSED] DP_QUERY_STREAM_ENC_STATUS with stream behavior
[20:27:48] [PASSED] DP_QUERY_STREAM_ENC_STATUS with a valid stream behavior
[20:27:48] ===== [PASSED] drm_test_dp_mst_sideband_msg_req_decode =====
[20:27:48] ================ [PASSED] drm_dp_mst_helper ================
[20:27:48] ================== drm_exec (7 subtests) ===================
[20:27:48] [PASSED] sanitycheck
[20:27:48] [PASSED] test_lock
[20:27:48] [PASSED] test_lock_unlock
[20:27:48] [PASSED] test_duplicates
[20:27:48] [PASSED] test_prepare
[20:27:48] [PASSED] test_prepare_array
[20:27:48] [PASSED] test_multiple_loops
[20:27:48] ==================== [PASSED] drm_exec =====================
[20:27:48] =========== drm_format_helper_test (18 subtests) ===========
[20:27:48] ============== drm_test_fb_xrgb8888_to_gray8  ==============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ========== [PASSED] drm_test_fb_xrgb8888_to_gray8 ==========
[20:27:48] ============= drm_test_fb_xrgb8888_to_rgb332  ==============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ========= [PASSED] drm_test_fb_xrgb8888_to_rgb332 ==========
[20:27:48] ============= drm_test_fb_xrgb8888_to_rgb565  ==============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ========= [PASSED] drm_test_fb_xrgb8888_to_rgb565 ==========
[20:27:48] ============ drm_test_fb_xrgb8888_to_xrgb1555  =============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ======== [PASSED] drm_test_fb_xrgb8888_to_xrgb1555 =========
[20:27:48] ============ drm_test_fb_xrgb8888_to_argb1555  =============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ======== [PASSED] drm_test_fb_xrgb8888_to_argb1555 =========
[20:27:48] ============ drm_test_fb_xrgb8888_to_rgba5551  =============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ======== [PASSED] drm_test_fb_xrgb8888_to_rgba5551 =========
[20:27:48] ============= drm_test_fb_xrgb8888_to_rgb888  ==============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ========= [PASSED] drm_test_fb_xrgb8888_to_rgb888 ==========
[20:27:48] ============= drm_test_fb_xrgb8888_to_bgr888  ==============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ========= [PASSED] drm_test_fb_xrgb8888_to_bgr888 ==========
[20:27:48] ============ drm_test_fb_xrgb8888_to_argb8888  =============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ======== [PASSED] drm_test_fb_xrgb8888_to_argb8888 =========
[20:27:48] =========== drm_test_fb_xrgb8888_to_xrgb2101010  ===========
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ======= [PASSED] drm_test_fb_xrgb8888_to_xrgb2101010 =======
[20:27:48] =========== drm_test_fb_xrgb8888_to_argb2101010  ===========
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ======= [PASSED] drm_test_fb_xrgb8888_to_argb2101010 =======
[20:27:48] ============== drm_test_fb_xrgb8888_to_mono  ===============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ========== [PASSED] drm_test_fb_xrgb8888_to_mono ===========
[20:27:48] ==================== drm_test_fb_swab  =====================
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ================ [PASSED] drm_test_fb_swab =================
[20:27:48] ============ drm_test_fb_xrgb8888_to_xbgr8888  =============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ======== [PASSED] drm_test_fb_xrgb8888_to_xbgr8888 =========
[20:27:48] ============ drm_test_fb_xrgb8888_to_abgr8888  =============
[20:27:48] [PASSED] single_pixel_source_buffer
[20:27:48] [PASSED] single_pixel_clip_rectangle
[20:27:48] [PASSED] well_known_colors
[20:27:48] [PASSED] destination_pitch
[20:27:48] ======== [PASSED] drm_test_fb_xrgb8888_to_abgr8888 =========
[20:27:48] ================= drm_test_fb_clip_offset  =================
[20:27:48] [PASSED] pass through
[20:27:48] [PASSED] horizontal offset
[20:27:48] [PASSED] vertical offset
[20:27:48] [PASSED] horizontal and vertical offset
[20:27:48] [PASSED] horizontal offset (custom pitch)
[20:27:48] [PASSED] vertical offset (custom pitch)
[20:27:48] [PASSED] horizontal and vertical offset (custom pitch)
[20:27:48] ============= [PASSED] drm_test_fb_clip_offset =============
[20:27:48] ============== drm_test_fb_build_fourcc_list  ==============
[20:27:48] [PASSED] no native formats
[20:27:48] [PASSED] XRGB8888 as native format
[20:27:48] [PASSED] remove duplicates
[20:27:48] [PASSED] convert alpha formats
[20:27:48] [PASSED] random formats
[20:27:48] ========== [PASSED] drm_test_fb_build_fourcc_list ==========
[20:27:48] =================== drm_test_fb_memcpy  ====================
[20:27:48] [PASSED] single_pixel_source_buffer: XR24 little-endian (0x34325258)
[20:27:48] [PASSED] single_pixel_source_buffer: XRA8 little-endian (0x38415258)
[20:27:48] [PASSED] single_pixel_source_buffer: YU24 little-endian (0x34325559)
[20:27:48] [PASSED] single_pixel_clip_rectangle: XB24 little-endian (0x34324258)
[20:27:48] [PASSED] single_pixel_clip_rectangle: XRA8 little-endian (0x38415258)
[20:27:48] [PASSED] single_pixel_clip_rectangle: YU24 little-endian (0x34325559)
[20:27:48] [PASSED] well_known_colors: XB24 little-endian (0x34324258)
[20:27:48] [PASSED] well_known_colors: XRA8 little-endian (0x38415258)
[20:27:48] [PASSED] well_known_colors: YU24 little-endian (0x34325559)
[20:27:48] [PASSED] destination_pitch: XB24 little-endian (0x34324258)
[20:27:48] [PASSED] destination_pitch: XRA8 little-endian (0x38415258)
[20:27:48] [PASSED] destination_pitch: YU24 little-endian (0x34325559)
[20:27:48] =============== [PASSED] drm_test_fb_memcpy ================
[20:27:48] ============= [PASSED] drm_format_helper_test ==============
[20:27:48] ================= drm_format (18 subtests) =================
[20:27:48] [PASSED] drm_test_format_block_width_invalid
[20:27:48] [PASSED] drm_test_format_block_width_one_plane
[20:27:48] [PASSED] drm_test_format_block_width_two_plane
[20:27:48] [PASSED] drm_test_format_block_width_three_plane
[20:27:48] [PASSED] drm_test_format_block_width_tiled
[20:27:48] [PASSED] drm_test_format_block_height_invalid
[20:27:48] [PASSED] drm_test_format_block_height_one_plane
[20:27:48] [PASSED] drm_test_format_block_height_two_plane
[20:27:48] [PASSED] drm_test_format_block_height_three_plane
[20:27:48] [PASSED] drm_test_format_block_height_tiled
[20:27:48] [PASSED] drm_test_format_min_pitch_invalid
[20:27:48] [PASSED] drm_test_format_min_pitch_one_plane_8bpp
[20:27:48] [PASSED] drm_test_format_min_pitch_one_plane_16bpp
[20:27:48] [PASSED] drm_test_format_min_pitch_one_plane_24bpp
[20:27:48] [PASSED] drm_test_format_min_pitch_one_plane_32bpp
[20:27:48] [PASSED] drm_test_format_min_pitch_two_plane
[20:27:48] [PASSED] drm_test_format_min_pitch_three_plane_8bpp
[20:27:48] [PASSED] drm_test_format_min_pitch_tiled
[20:27:48] =================== [PASSED] drm_format ====================
[20:27:48] ============== drm_framebuffer (10 subtests) ===============
[20:27:48] ========== drm_test_framebuffer_check_src_coords  ==========
[20:27:48] [PASSED] Success: source fits into fb
[20:27:48] [PASSED] Fail: overflowing fb with x-axis coordinate
[20:27:48] [PASSED] Fail: overflowing fb with y-axis coordinate
[20:27:48] [PASSED] Fail: overflowing fb with source width
[20:27:48] [PASSED] Fail: overflowing fb with source height
[20:27:48] ====== [PASSED] drm_test_framebuffer_check_src_coords ======
[20:27:48] [PASSED] drm_test_framebuffer_cleanup
[20:27:48] =============== drm_test_framebuffer_create  ===============
[20:27:48] [PASSED] ABGR8888 normal sizes
[20:27:48] [PASSED] ABGR8888 max sizes
[20:27:48] [PASSED] ABGR8888 pitch greater than min required
[20:27:48] [PASSED] ABGR8888 pitch less than min required
[20:27:48] [PASSED] ABGR8888 Invalid width
[20:27:48] [PASSED] ABGR8888 Invalid buffer handle
[20:27:48] [PASSED] No pixel format
[20:27:48] [PASSED] ABGR8888 Width 0
[20:27:48] [PASSED] ABGR8888 Height 0
[20:27:48] [PASSED] ABGR8888 Out of bound height * pitch combination
[20:27:48] [PASSED] ABGR8888 Large buffer offset
[20:27:48] [PASSED] ABGR8888 Buffer offset for inexistent plane
[20:27:48] [PASSED] ABGR8888 Invalid flag
[20:27:48] [PASSED] ABGR8888 Set DRM_MODE_FB_MODIFIERS without modifiers
[20:27:48] [PASSED] ABGR8888 Valid buffer modifier
[20:27:48] [PASSED] ABGR8888 Invalid buffer modifier(DRM_FORMAT_MOD_SAMSUNG_64_32_TILE)
[20:27:48] [PASSED] ABGR8888 Extra pitches without DRM_MODE_FB_MODIFIERS
[20:27:48] [PASSED] ABGR8888 Extra pitches with DRM_MODE_FB_MODIFIERS
[20:27:48] [PASSED] NV12 Normal sizes
[20:27:48] [PASSED] NV12 Max sizes
[20:27:48] [PASSED] NV12 Invalid pitch
[20:27:48] [PASSED] NV12 Invalid modifier/missing DRM_MODE_FB_MODIFIERS flag
[20:27:48] [PASSED] NV12 different  modifier per-plane
[20:27:48] [PASSED] NV12 with DRM_FORMAT_MOD_SAMSUNG_64_32_TILE
[20:27:48] [PASSED] NV12 Valid modifiers without DRM_MODE_FB_MODIFIERS
[20:27:48] [PASSED] NV12 Modifier for inexistent plane
[20:27:48] [PASSED] NV12 Handle for inexistent plane
[20:27:48] [PASSED] NV12 Handle for inexistent plane without DRM_MODE_FB_MODIFIERS
[20:27:48] [PASSED] YVU420 DRM_MODE_FB_MODIFIERS set without modifier
[20:27:48] [PASSED] YVU420 Normal sizes
[20:27:48] [PASSED] YVU420 Max sizes
[20:27:48] [PASSED] YVU420 Invalid pitch
[20:27:48] [PASSED] YVU420 Different pitches
[20:27:48] [PASSED] YVU420 Different buffer offsets/pitches
[20:27:48] [PASSED] YVU420 Modifier set just for plane 0, without DRM_MODE_FB_MODIFIERS
[20:27:48] [PASSED] YVU420 Modifier set just for planes 0, 1, without DRM_MODE_FB_MODIFIERS
[20:27:48] [PASSED] YVU420 Modifier set just for plane 0, 1, with DRM_MODE_FB_MODIFIERS
[20:27:48] [PASSED] YVU420 Valid modifier
[20:27:48] [PASSED] YVU420 Different modifiers per plane
[20:27:48] [PASSED] YVU420 Modifier for inexistent plane
[20:27:48] [PASSED] YUV420_10BIT Invalid modifier(DRM_FORMAT_MOD_LINEAR)
[20:27:48] [PASSED] X0L2 Normal sizes
[20:27:48] [PASSED] X0L2 Max sizes
[20:27:48] [PASSED] X0L2 Invalid pitch
[20:27:48] [PASSED] X0L2 Pitch greater than minimum required
[20:27:48] [PASSED] X0L2 Handle for inexistent plane
[20:27:48] [PASSED] X0L2 Offset for inexistent plane, without DRM_MODE_FB_MODIFIERS set
[20:27:48] [PASSED] X0L2 Modifier without DRM_MODE_FB_MODIFIERS set
[20:27:48] [PASSED] X0L2 Valid modifier
[20:27:48] [PASSED] X0L2 Modifier for inexistent plane
[20:27:48] =========== [PASSED] drm_test_framebuffer_create ===========
[20:27:48] [PASSED] drm_test_framebuffer_free
[20:27:48] [PASSED] drm_test_framebuffer_init
[20:27:48] [PASSED] drm_test_framebuffer_init_bad_format
[20:27:48] [PASSED] drm_test_framebuffer_init_dev_mismatch
[20:27:48] [PASSED] drm_test_framebuffer_lookup
[20:27:48] [PASSED] drm_test_framebuffer_lookup_inexistent
[20:27:48] [PASSED] drm_test_framebuffer_modifiers_not_supported
[20:27:48] ================= [PASSED] drm_framebuffer =================
[20:27:48] ================ drm_gem_shmem (8 subtests) ================
[20:27:48] [PASSED] drm_gem_shmem_test_obj_create
[20:27:48] [PASSED] drm_gem_shmem_test_obj_create_private
[20:27:48] [PASSED] drm_gem_shmem_test_pin_pages
[20:27:48] [PASSED] drm_gem_shmem_test_vmap
[20:27:48] [PASSED] drm_gem_shmem_test_get_pages_sgt
[20:27:48] [PASSED] drm_gem_shmem_test_get_sg_table
[20:27:48] [PASSED] drm_gem_shmem_test_madvise
[20:27:48] [PASSED] drm_gem_shmem_test_purge
[20:27:48] ================== [PASSED] drm_gem_shmem ==================
[20:27:48] === drm_atomic_helper_connector_hdmi_check (27 subtests) ===
[20:27:48] [PASSED] drm_test_check_broadcast_rgb_auto_cea_mode
[20:27:48] [PASSED] drm_test_check_broadcast_rgb_auto_cea_mode_vic_1
[20:27:48] [PASSED] drm_test_check_broadcast_rgb_full_cea_mode
[20:27:48] [PASSED] drm_test_check_broadcast_rgb_full_cea_mode_vic_1
[20:27:48] [PASSED] drm_test_check_broadcast_rgb_limited_cea_mode
[20:27:48] [PASSED] drm_test_check_broadcast_rgb_limited_cea_mode_vic_1
[20:27:48] ====== drm_test_check_broadcast_rgb_cea_mode_yuv420  =======
[20:27:48] [PASSED] Automatic
[20:27:48] [PASSED] Full
[20:27:48] [PASSED] Limited 16:235
[20:27:48] == [PASSED] drm_test_check_broadcast_rgb_cea_mode_yuv420 ===
[20:27:48] [PASSED] drm_test_check_broadcast_rgb_crtc_mode_changed
[20:27:48] [PASSED] drm_test_check_broadcast_rgb_crtc_mode_not_changed
[20:27:48] [PASSED] drm_test_check_disable_connector
[20:27:48] [PASSED] drm_test_check_hdmi_funcs_reject_rate
[20:27:48] [PASSED] drm_test_check_max_tmds_rate_bpc_fallback_rgb
[20:27:48] [PASSED] drm_test_check_max_tmds_rate_bpc_fallback_yuv420
[20:27:48] [PASSED] drm_test_check_max_tmds_rate_bpc_fallback_ignore_yuv422
[20:27:48] [PASSED] drm_test_check_max_tmds_rate_bpc_fallback_ignore_yuv420
[20:27:48] [PASSED] drm_test_check_driver_unsupported_fallback_yuv420
[20:27:48] [PASSED] drm_test_check_output_bpc_crtc_mode_changed
[20:27:48] [PASSED] drm_test_check_output_bpc_crtc_mode_not_changed
[20:27:48] [PASSED] drm_test_check_output_bpc_dvi
[20:27:48] [PASSED] drm_test_check_output_bpc_format_vic_1
[20:27:48] [PASSED] drm_test_check_output_bpc_format_display_8bpc_only
[20:27:48] [PASSED] drm_test_check_output_bpc_format_display_rgb_only
[20:27:48] [PASSED] drm_test_check_output_bpc_format_driver_8bpc_only
[20:27:48] [PASSED] drm_test_check_output_bpc_format_driver_rgb_only
[20:27:48] [PASSED] drm_test_check_tmds_char_rate_rgb_8bpc
[20:27:48] [PASSED] drm_test_check_tmds_char_rate_rgb_10bpc
[20:27:48] [PASSED] drm_test_check_tmds_char_rate_rgb_12bpc
[20:27:48] ===== [PASSED] drm_atomic_helper_connector_hdmi_check ======
[20:27:48] === drm_atomic_helper_connector_hdmi_reset (6 subtests) ====
[20:27:48] [PASSED] drm_test_check_broadcast_rgb_value
[20:27:48] [PASSED] drm_test_check_bpc_8_value
[20:27:48] [PASSED] drm_test_check_bpc_10_value
[20:27:48] [PASSED] drm_test_check_bpc_12_value
[20:27:48] [PASSED] drm_test_check_format_value
[20:27:48] [PASSED] drm_test_check_tmds_char_value
[20:27:48] ===== [PASSED] drm_atomic_helper_connector_hdmi_reset ======
[20:27:48] = drm_atomic_helper_connector_hdmi_mode_valid (4 subtests) =
[20:27:48] [PASSED] drm_test_check_mode_valid
[20:27:48] [PASSED] drm_test_check_mode_valid_reject
[20:27:48] [PASSED] drm_test_check_mode_valid_reject_rate
[20:27:48] [PASSED] drm_test_check_mode_valid_reject_max_clock
[20:27:48] === [PASSED] drm_atomic_helper_connector_hdmi_mode_valid ===
[20:27:48] ================= drm_managed (2 subtests) =================
[20:27:48] [PASSED] drm_test_managed_release_action
[20:27:48] [PASSED] drm_test_managed_run_action
[20:27:48] =================== [PASSED] drm_managed ===================
[20:27:48] =================== drm_mm (6 subtests) ====================
[20:27:48] [PASSED] drm_test_mm_init
[20:27:48] [PASSED] drm_test_mm_debug
[20:27:48] [PASSED] drm_test_mm_align32
[20:27:48] [PASSED] drm_test_mm_align64
[20:27:48] [PASSED] drm_test_mm_lowest
[20:27:48] [PASSED] drm_test_mm_highest
[20:27:48] ===================== [PASSED] drm_mm ======================
[20:27:48] ============= drm_modes_analog_tv (5 subtests) =============
[20:27:48] [PASSED] drm_test_modes_analog_tv_mono_576i
[20:27:48] [PASSED] drm_test_modes_analog_tv_ntsc_480i
[20:27:48] [PASSED] drm_test_modes_analog_tv_ntsc_480i_inlined
[20:27:48] [PASSED] drm_test_modes_analog_tv_pal_576i
[20:27:48] [PASSED] drm_test_modes_analog_tv_pal_576i_inlined
[20:27:48] =============== [PASSED] drm_modes_analog_tv ===============
[20:27:48] ============== drm_plane_helper (2 subtests) ===============
[20:27:48] =============== drm_test_check_plane_state  ================
[20:27:48] [PASSED] clipping_simple
[20:27:48] [PASSED] clipping_rotate_reflect
[20:27:48] [PASSED] positioning_simple
[20:27:48] [PASSED] upscaling
[20:27:48] [PASSED] downscaling
[20:27:48] [PASSED] rounding1
[20:27:48] [PASSED] rounding2
[20:27:48] [PASSED] rounding3
[20:27:48] [PASSED] rounding4
[20:27:48] =========== [PASSED] drm_test_check_plane_state ============
[20:27:48] =========== drm_test_check_invalid_plane_state  ============
[20:27:48] [PASSED] positioning_invalid
[20:27:48] [PASSED] upscaling_invalid
[20:27:48] [PASSED] downscaling_invalid
[20:27:48] ======= [PASSED] drm_test_check_invalid_plane_state ========
[20:27:48] ================ [PASSED] drm_plane_helper =================
[20:27:48] ====== drm_connector_helper_tv_get_modes (1 subtest) =======
[20:27:48] ====== drm_test_connector_helper_tv_get_modes_check  =======
[20:27:48] [PASSED] None
[20:27:48] [PASSED] PAL
[20:27:48] [PASSED] NTSC
[20:27:48] [PASSED] Both, NTSC Default
[20:27:48] [PASSED] Both, PAL Default
[20:27:48] [PASSED] Both, NTSC Default, with PAL on command-line
[20:27:48] [PASSED] Both, PAL Default, with NTSC on command-line
[20:27:48] == [PASSED] drm_test_connector_helper_tv_get_modes_check ===
[20:27:48] ======== [PASSED] drm_connector_helper_tv_get_modes ========
[20:27:48] ================== drm_rect (9 subtests) ===================
[20:27:48] [PASSED] drm_test_rect_clip_scaled_div_by_zero
[20:27:48] [PASSED] drm_test_rect_clip_scaled_not_clipped
[20:27:48] [PASSED] drm_test_rect_clip_scaled_clipped
[20:27:48] [PASSED] drm_test_rect_clip_scaled_signed_vs_unsigned
[20:27:48] ================= drm_test_rect_intersect  =================
[20:27:48] [PASSED] top-left x bottom-right: 2x2+1+1 x 2x2+0+0
[20:27:48] [PASSED] top-right x bottom-left: 2x2+0+0 x 2x2+1-1
[20:27:48] [PASSED] bottom-left x top-right: 2x2+1-1 x 2x2+0+0
[20:27:48] [PASSED] bottom-right x top-left: 2x2+0+0 x 2x2+1+1
[20:27:48] [PASSED] right x left: 2x1+0+0 x 3x1+1+0
[20:27:48] [PASSED] left x right: 3x1+1+0 x 2x1+0+0
[20:27:48] [PASSED] up x bottom: 1x2+0+0 x 1x3+0-1
[20:27:48] [PASSED] bottom x up: 1x3+0-1 x 1x2+0+0
[20:27:48] [PASSED] touching corner: 1x1+0+0 x 2x2+1+1
[20:27:48] [PASSED] touching side: 1x1+0+0 x 1x1+1+0
[20:27:48] [PASSED] equal rects: 2x2+0+0 x 2x2+0+0
[20:27:48] [PASSED] inside another: 2x2+0+0 x 1x1+1+1
[20:27:48] [PASSED] far away: 1x1+0+0 x 1x1+3+6
[20:27:48] [PASSED] points intersecting: 0x0+5+10 x 0x0+5+10
[20:27:48] [PASSED] points not intersecting: 0x0+0+0 x 0x0+5+10
[20:27:48] ============= [PASSED] drm_test_rect_intersect =============
[20:27:48] ================ drm_test_rect_calc_hscale  ================
[20:27:48] [PASSED] normal use
[20:27:48] [PASSED] out of max range
[20:27:48] [PASSED] out of min range
[20:27:48] [PASSED] zero dst
[20:27:48] [PASSED] negative src
[20:27:48] [PASSED] negative dst
[20:27:48] ============ [PASSED] drm_test_rect_calc_hscale ============
[20:27:48] ================ drm_test_rect_calc_vscale  ================
[20:27:48] [PASSED] normal use
[20:27:48] [PASSED] out of max range
[20:27:48] [PASSED] out of min range
[20:27:48] [PASSED] zero dst
[20:27:48] [PASSED] negative src
[20:27:48] [PASSED] negative dst
[20:27:48] ============ [PASSED] drm_test_rect_calc_vscale ============
[20:27:48] ================== drm_test_rect_rotate  ===================
[20:27:48] [PASSED] reflect-x
[20:27:48] [PASSED] reflect-y
[20:27:48] [PASSED] rotate-0
[20:27:48] [PASSED] rotate-90
[20:27:48] [PASSED] rotate-180
stty: 'standard input': Inappropriate ioctl for device
[20:27:48] [PASSED] rotate-270
[20:27:48] ============== [PASSED] drm_test_rect_rotate ===============
[20:27:48] ================ drm_test_rect_rotate_inv  =================
[20:27:48] [PASSED] reflect-x
[20:27:48] [PASSED] reflect-y
[20:27:48] [PASSED] rotate-0
[20:27:48] [PASSED] rotate-90
[20:27:48] [PASSED] rotate-180
[20:27:48] [PASSED] rotate-270
[20:27:48] ============ [PASSED] drm_test_rect_rotate_inv =============
[20:27:48] ==================== [PASSED] drm_rect =====================
[20:27:48] ============================================================
[20:27:48] Testing complete. Ran 614 tests: passed: 614
[20:27:48] Elapsed time: 23.159s total, 1.651s configuring, 21.340s building, 0.150s running

+ /kernel/tools/testing/kunit/kunit.py run --kunitconfig /kernel/drivers/gpu/drm/ttm/tests/.kunitconfig
ERROR:root:../drivers/gpu/drm/ttm/ttm_pool.c: In function ‘ttm_pool_mgr_init’:
../drivers/gpu/drm/ttm/ttm_pool.c:1335:30: error: ‘TTM_SHRINKER_BATCH’ undeclared (first use in this function)
 1335 |         mm_shrinker->batch = TTM_SHRINKER_BATCH;
      |                              ^~~~~~~~~~~~~~~~~~
../drivers/gpu/drm/ttm/ttm_pool.c:1335:30: note: each undeclared identifier is reported only once for each function it appears in
make[7]: *** [../scripts/Makefile.build:203: drivers/gpu/drm/ttm/ttm_pool.o] Error 1
make[7]: *** Waiting for unfinished jobs....
make[6]: *** [../scripts/Makefile.build:461: drivers/gpu/drm/ttm] Error 2
make[5]: *** [../scripts/Makefile.build:461: drivers/gpu/drm] Error 2
make[4]: *** [../scripts/Makefile.build:461: drivers/gpu] Error 2
make[3]: *** [../scripts/Makefile.build:461: drivers] Error 2
make[2]: *** [/kernel/Makefile:2003: .] Error 2
make[1]: *** [/kernel/Makefile:248: __sub-make] Error 2
make: *** [Makefile:248: __sub-make] Error 2

[20:27:48] Configuring KUnit Kernel ...
Regenerating .config ...
Populating config with:
$ make ARCH=um O=.kunit olddefconfig
[20:27:50] Building KUnit Kernel ...
Populating config with:
$ make ARCH=um O=.kunit olddefconfig
Building with:
$ make all compile_commands.json scripts_gdb ARCH=um O=.kunit --jobs=48
+ cleanup
++ stat -c %u:%g /kernel
+ chown -R 1003:1003 /kernel



^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units
  2025-06-03 20:21 ` [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units Ashutosh Dixit
@ 2025-06-04 23:42   ` Umesh Nerlige Ramappa
  2025-06-05 18:28     ` Dixit, Ashutosh
  0 siblings, 1 reply; 24+ messages in thread
From: Umesh Nerlige Ramappa @ 2025-06-04 23:42 UTC (permalink / raw)
  To: Ashutosh Dixit; +Cc: intel-xe

On Tue, Jun 03, 2025 at 01:21:29PM -0700, Ashutosh Dixit wrote:
>On Xe2+ platforms, media engines are attached to "SCMI" OA media (OAM)
>units. One or more SCMI OAM units might be present on a platform. In
>addition there is another OAM unit for global events, called
>OAM-SAG. Performance metrics for media workloads can be obtained from these
>OAM units, similar to OAG.
>
>Expose these OAM units for userspace to use. OAM-SAG is exposed as an OA
>unit without any attached engines.
>
>Bspec: 70819, 67103, 63844, 72572, 74476, 61284
>
>v2: Fix xe_gt_WARN_ON in __hwe_oam_unit for < 12.7 platforms
>v3: Return XE_OA_UNIT_INVALID for < 12.7 to indicate no OAM units
>v4: Move xe_oa_print_oa_units() to separate patch
>v5: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
>
>Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
>---
> drivers/gpu/drm/xe/xe_oa.c | 68 ++++++++++++++++++++++++++++----------
> include/uapi/drm/xe_drm.h  |  3 ++
> 2 files changed, 54 insertions(+), 17 deletions(-)
>
>diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
>index fb842fa0552e5..0de0d5a18df74 100644
>--- a/drivers/gpu/drm/xe/xe_oa.c
>+++ b/drivers/gpu/drm/xe/xe_oa.c
>@@ -43,6 +43,12 @@
> #define DEFAULT_POLL_PERIOD_NS (NSEC_PER_SEC / DEFAULT_POLL_FREQUENCY_HZ)
> #define XE_OA_UNIT_INVALID U32_MAX
>
>+enum xe_oam_unit_type {
>+	XE_OAM_UNIT_SAG,
>+	XE_OAM_UNIT_SCMI_0,
>+	XE_OAM_UNIT_SCMI_1,
>+};
>+
> enum xe_oa_submit_deps {
> 	XE_OA_SUBMIT_NO_DEPS,
> 	XE_OA_SUBMIT_ADD_DEPS,
>@@ -1881,6 +1887,7 @@ static bool engine_supports_oa_format(const struct xe_hw_engine *hwe, int type)
> 		return type == DRM_XE_OA_FMT_TYPE_OAG || type == DRM_XE_OA_FMT_TYPE_OAR ||
> 			type == DRM_XE_OA_FMT_TYPE_OAC || type == DRM_XE_OA_FMT_TYPE_PEC;
> 	case DRM_XE_OA_UNIT_TYPE_OAM:
>+	case DRM_XE_OA_UNIT_TYPE_OAM_SAG:
> 		return type == DRM_XE_OA_FMT_TYPE_OAM || type == DRM_XE_OA_FMT_TYPE_OAM_MPEC;
> 	default:
> 		return false;
>@@ -2448,20 +2455,38 @@ int xe_oa_register(struct xe_device *xe)
>
> static u32 num_oa_units_per_gt(struct xe_gt *gt)
> {
>-	return 1;
>+	if (!xe_gt_is_media_type(gt) || GRAPHICS_VER(gt_to_xe(gt)) < 20)
>+		return 1;
>+	else if (!IS_DGFX(gt_to_xe(gt)))
>+		return XE_OAM_UNIT_SCMI_0 + 1; /* SAG + SCMI_0 */
>+	else
>+		return XE_OAM_UNIT_SCMI_1 + 1; /* SAG + SCMI_0 + SCMI_1 */
> }
>
> static u32 __hwe_oam_unit(struct xe_hw_engine *hwe)
> {
>-	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) >= 1270) {
>-		/*
>-		 * There's 1 SAMEDIA gt and 1 OAM per SAMEDIA gt. All media slices
>-		 * within the gt use the same OAM. All MTL/LNL SKUs list 1 SA MEDIA
>-		 */
>-		xe_gt_WARN_ON(hwe->gt, hwe->gt->info.type != XE_GT_TYPE_MEDIA);
>+	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) < 1270)
>+		return XE_OA_UNIT_INVALID;
>
>+	xe_gt_WARN_ON(hwe->gt, !xe_gt_is_media_type(hwe->gt));
>+
>+	if (GRAPHICS_VER(gt_to_xe(hwe->gt)) < 20)
> 		return 0;
>-	}
>+	/*
>+	 * XE_OAM_UNIT_SAG has only GSCCS attached to it, but only on some platforms. Also
>+	 * GSCCS cannot be used to submit batches to program the OAM unit. Therefore we don't
>+	 * assign an OA unit to GSCCS. This means that XE_OAM_UNIT_SAG is exposed as an OA
>+	 * unit without attached engines. Fused off engines can also result in oa_unit's with
>+	 * num_engines == 0. OA streams can be opened on all OA units.
>+	 */
>+	else if (hwe->engine_id == XE_HW_ENGINE_GSCCS0)

You could just drop the case XE_ENGINE_CLASS_OTHER in caller 
(__hwe_oa_unit()) and then you dont need the XE_HW_ENGINE_GSCCS0 check 
here.

>+		return XE_OA_UNIT_INVALID;
>+	else if (!IS_DGFX(gt_to_xe(hwe->gt)))
>+		return XE_OAM_UNIT_SCMI_0;
>+	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_DECODE)
>+		return (hwe->instance / 2 & 0x1) + 1;

should be same as (hwe->instance / 2) + 1;

>+	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_ENHANCE)
>+		return (hwe->instance & 0x1) + 1;

same here, should be same as (hwe->instance + 1)

Thanks,
Umesh

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 2/5] drm/xe/oa: Print hwe to OA unit mapping
  2025-06-03 20:21 ` [PATCH 2/5] drm/xe/oa: Print hwe to OA unit mapping Ashutosh Dixit
@ 2025-06-04 23:49   ` Umesh Nerlige Ramappa
  2025-06-06 16:05     ` Dixit, Ashutosh
  0 siblings, 1 reply; 24+ messages in thread
From: Umesh Nerlige Ramappa @ 2025-06-04 23:49 UTC (permalink / raw)
  To: Ashutosh Dixit; +Cc: intel-xe

On Tue, Jun 03, 2025 at 01:21:30PM -0700, Ashutosh Dixit wrote:
>Print hwe to OA unit mapping to dmesg, to help debug for current and new
>platforms.
>
>Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
>---
> drivers/gpu/drm/xe/xe_oa.c | 27 +++++++++++++++++++++++++++
> 1 file changed, 27 insertions(+)
>
>diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
>index 0de0d5a18df74..94faa4ed2012f 100644
>--- a/drivers/gpu/drm/xe/xe_oa.c
>+++ b/drivers/gpu/drm/xe/xe_oa.c
>@@ -2603,6 +2603,31 @@ static int xe_oa_init_gt(struct xe_gt *gt)
> 	return 0;
> }
>
>+static void xe_oa_print_oa_units(struct xe_oa *oa)
>+{
>+	enum xe_hw_engine_id hwe_id;
>+	struct xe_hw_engine *hwe;
>+	struct xe_oa_unit *u;
>+	struct xe_gt *gt;
>+	int gt_id, i, n;
>+	char buf[256];
>+
>+	for_each_gt(gt, oa->xe, gt_id) {
>+		for (i = 0; i < gt->oa.num_oa_units; i++) {
>+			u = &gt->oa.oa_unit[i];
>+			buf[0] = '\0';
>+			n = 0;
>+
>+			for_each_hw_engine(hwe, gt, hwe_id)
>+				if (xe_oa_unit_id(hwe) == u->oa_unit_id)
>+					n += scnprintf(buf + n, sizeof(buf) - n, "%s ", hwe->name);
>+
>+			xe_gt_dbg(gt, "oa_unit %d, type %d, Engines: %s\n",
>+				  u->oa_unit_id, u->type, buf);
>+		}
>+	}
>+}
>+

nit: I would at least move one of the inner for loops outside to a 
separate helper.

otherwise, LGTM

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

Thanks,
Umesh

> static int xe_oa_init_oa_units(struct xe_oa *oa)
> {
> 	struct xe_gt *gt;
>@@ -2619,6 +2644,8 @@ static int xe_oa_init_oa_units(struct xe_oa *oa)
> 			return ret;
> 	}
>
>+	xe_oa_print_oa_units(oa);
>+
> 	return 0;
> }
>
>-- 
>2.48.1
>

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 3/5] drm/xe/oa: Introduce stream->oa_unit
  2025-06-03 20:21 ` [PATCH 3/5] drm/xe/oa: Introduce stream->oa_unit Ashutosh Dixit
@ 2025-06-04 23:54   ` Umesh Nerlige Ramappa
  0 siblings, 0 replies; 24+ messages in thread
From: Umesh Nerlige Ramappa @ 2025-06-04 23:54 UTC (permalink / raw)
  To: Ashutosh Dixit; +Cc: intel-xe

On Tue, Jun 03, 2025 at 01:21:31PM -0700, Ashutosh Dixit wrote:
>Previously, the oa_unit associated with an OA stream was derived from hwe
>associated with the stream (stream->hwe->oa_unit). This breaks with OAM_SAG
>since OAM_SAG does not have any attached hardware engines. Resolve this by
>introducing stream->oa_unit and stop depending on stream->hwe.
>
>Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>

LGTM

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

Thanks,
Umesh
>---
> drivers/gpu/drm/xe/xe_oa.c       | 51 +++++++++++++++++++++-----------
> drivers/gpu/drm/xe/xe_oa_types.h |  3 ++
> 2 files changed, 37 insertions(+), 17 deletions(-)
>
>diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
>index 94faa4ed2012f..4d6d9f0189a83 100644
>--- a/drivers/gpu/drm/xe/xe_oa.c
>+++ b/drivers/gpu/drm/xe/xe_oa.c
>@@ -83,7 +83,7 @@ struct xe_oa_config {
>
> struct xe_oa_open_param {
> 	struct xe_file *xef;
>-	u32 oa_unit_id;
>+	struct xe_oa_unit *oa_unit;
> 	bool sample;
> 	u32 metric_set;
> 	enum xe_oa_format_name oa_format;
>@@ -200,7 +200,7 @@ static void free_oa_config_bo(struct xe_oa_config_bo *oa_bo, struct dma_fence *l
>
> static const struct xe_oa_regs *__oa_regs(struct xe_oa_stream *stream)
> {
>-	return &stream->hwe->oa_unit->regs;
>+	return &stream->oa_unit->regs;
> }
>
> static u32 xe_oa_hw_tail_read(struct xe_oa_stream *stream)
>@@ -460,7 +460,7 @@ static u32 __oa_ccs_select(struct xe_oa_stream *stream)
>
> static u32 __oactrl_used_bits(struct xe_oa_stream *stream)
> {
>-	return stream->hwe->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG ?
>+	return stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG ?
> 		OAG_OACONTROL_USED_BITS : OAM_OACONTROL_USED_BITS;
> }
>
>@@ -481,7 +481,7 @@ static void xe_oa_enable(struct xe_oa_stream *stream)
> 		__oa_ccs_select(stream) | OAG_OACONTROL_OA_COUNTER_ENABLE;
>
> 	if (GRAPHICS_VER(stream->oa->xe) >= 20 &&
>-	    stream->hwe->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG)
>+	    stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG)
> 		val |= OAG_OACONTROL_OA_PES_DISAG_EN;
>
> 	xe_mmio_rmw32(&stream->gt->mmio, regs->oa_ctrl, __oactrl_used_bits(stream), val);
>@@ -848,7 +848,7 @@ static void xe_oa_disable_metric_set(struct xe_oa_stream *stream)
>
> static void xe_oa_stream_destroy(struct xe_oa_stream *stream)
> {
>-	struct xe_oa_unit *u = stream->hwe->oa_unit;
>+	struct xe_oa_unit *u = stream->oa_unit;
> 	struct xe_gt *gt = stream->hwe->gt;
>
> 	if (WARN_ON(stream != u->exclusive_stream))
>@@ -1145,14 +1145,31 @@ static int decode_oa_format(struct xe_oa *oa, u64 fmt, enum xe_oa_format_name *n
> 	return -EINVAL;
> }
>
>+static struct xe_oa_unit *xe_oa_lookup_oa_unit(struct xe_oa *oa, u32 oa_unit_id)
>+{
>+	struct xe_gt *gt;
>+	int gt_id, i;
>+
>+	for_each_gt(gt, oa->xe, gt_id) {
>+		for (i = 0; i < gt->oa.num_oa_units; i++) {
>+			struct xe_oa_unit *u = &gt->oa.oa_unit[i];
>+
>+			if (u->oa_unit_id == oa_unit_id)
>+				return u;
>+		}
>+	}
>+
>+	return NULL;
>+}
>+
> static int xe_oa_set_prop_oa_unit_id(struct xe_oa *oa, u64 value,
> 				     struct xe_oa_open_param *param)
> {
>-	if (value >= oa->oa_unit_ids) {
>+	param->oa_unit = xe_oa_lookup_oa_unit(oa, value);
>+	if (!param->oa_unit) {
> 		drm_dbg(&oa->xe->drm, "OA unit ID out of range %lld\n", value);
> 		return -EINVAL;
> 	}
>-	param->oa_unit_id = value;
> 	return 0;
> }
>
>@@ -1683,13 +1700,13 @@ static const struct file_operations xe_oa_fops = {
> static int xe_oa_stream_init(struct xe_oa_stream *stream,
> 			     struct xe_oa_open_param *param)
> {
>-	struct xe_oa_unit *u = param->hwe->oa_unit;
> 	struct xe_gt *gt = param->hwe->gt;
> 	unsigned int fw_ref;
> 	int ret;
>
> 	stream->exec_q = param->exec_q;
> 	stream->poll_period_ns = DEFAULT_POLL_PERIOD_NS;
>+	stream->oa_unit = param->oa_unit;
> 	stream->hwe = param->hwe;
> 	stream->gt = stream->hwe->gt;
> 	stream->oa_buffer.format = &stream->oa->oa_formats[param->oa_format];
>@@ -1710,7 +1727,7 @@ static int xe_oa_stream_init(struct xe_oa_stream *stream,
> 	 * buffer whose size, circ_size, is a multiple of the report size
> 	 */
> 	if (GRAPHICS_VER(stream->oa->xe) >= 20 &&
>-	    stream->hwe->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG && stream->sample)
>+	    stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAG && stream->sample)
> 		stream->oa_buffer.circ_size =
> 			param->oa_buffer_size -
> 			param->oa_buffer_size % stream->oa_buffer.format->size;
>@@ -1768,7 +1785,7 @@ static int xe_oa_stream_init(struct xe_oa_stream *stream,
> 	drm_dbg(&stream->oa->xe->drm, "opening stream oa config uuid=%s\n",
> 		stream->oa_config->uuid);
>
>-	WRITE_ONCE(u->exclusive_stream, stream);
>+	WRITE_ONCE(stream->oa_unit->exclusive_stream, stream);
>
> 	hrtimer_setup(&stream->poll_check_timer, xe_oa_poll_check_timer_cb, CLOCK_MONOTONIC,
> 		      HRTIMER_MODE_REL);
>@@ -1804,7 +1821,7 @@ static int xe_oa_stream_open_ioctl_locked(struct xe_oa *oa,
> 	int ret;
>
> 	/* We currently only allow exclusive access */
>-	if (param->hwe->oa_unit->exclusive_stream) {
>+	if (param->oa_unit->exclusive_stream) {
> 		drm_dbg(&oa->xe->drm, "OA unit already in use\n");
> 		ret = -EBUSY;
> 		goto exit;
>@@ -1880,9 +1897,9 @@ static u64 oa_exponent_to_ns(struct xe_gt *gt, int exponent)
> 	return div_u64(nom + den - 1, den);
> }
>
>-static bool engine_supports_oa_format(const struct xe_hw_engine *hwe, int type)
>+static bool oa_unit_supports_oa_format(struct xe_oa_open_param *param, int type)
> {
>-	switch (hwe->oa_unit->type) {
>+	switch (param->oa_unit->type) {
> 	case DRM_XE_OA_UNIT_TYPE_OAG:
> 		return type == DRM_XE_OA_FMT_TYPE_OAG || type == DRM_XE_OA_FMT_TYPE_OAR ||
> 			type == DRM_XE_OA_FMT_TYPE_OAC || type == DRM_XE_OA_FMT_TYPE_PEC;
>@@ -1922,7 +1939,7 @@ static int xe_oa_assign_hwe(struct xe_oa *oa, struct xe_oa_open_param *param)
> 		/* Else just get the first hwe attached to the oa unit */
> 		for_each_gt(gt, oa->xe, i) {
> 			for_each_hw_engine(hwe, gt, id) {
>-				if (xe_oa_unit_id(hwe) == param->oa_unit_id) {
>+				if (hwe->oa_unit == param->oa_unit) {
> 					param->hwe = hwe;
> 					goto out;
> 				}
>@@ -1930,10 +1947,10 @@ static int xe_oa_assign_hwe(struct xe_oa *oa, struct xe_oa_open_param *param)
> 		}
> 	}
> out:
>-	if (!param->hwe || xe_oa_unit_id(param->hwe) != param->oa_unit_id) {
>+	if (!param->hwe || param->hwe->oa_unit != param->oa_unit) {
> 		drm_dbg(&oa->xe->drm, "Unable to find hwe (%d, %d) for OA unit ID %d\n",
> 			param->exec_q ? param->exec_q->class : -1,
>-			param->engine_instance, param->oa_unit_id);
>+			param->engine_instance, param->oa_unit->oa_unit_id);
> 		ret = -EINVAL;
> 	}
>
>@@ -2014,7 +2031,7 @@ int xe_oa_stream_open_ioctl(struct drm_device *dev, u64 data, struct drm_file *f
>
> 	f = &oa->oa_formats[param.oa_format];
> 	if (!param.oa_format || !f->size ||
>-	    !engine_supports_oa_format(param.hwe, f->type)) {
>+	    !oa_unit_supports_oa_format(&param, f->type)) {
> 		drm_dbg(&oa->xe->drm, "Invalid OA format %d type %d size %d for class %d\n",
> 			param.oa_format, f->type, f->size, param.hwe->class);
> 		ret = -EINVAL;
>diff --git a/drivers/gpu/drm/xe/xe_oa_types.h b/drivers/gpu/drm/xe/xe_oa_types.h
>index 52e33c37d5ee8..a01c85931e2a5 100644
>--- a/drivers/gpu/drm/xe/xe_oa_types.h
>+++ b/drivers/gpu/drm/xe/xe_oa_types.h
>@@ -182,6 +182,9 @@ struct xe_oa_stream {
> 	/** @gt: gt associated with the oa stream */
> 	struct xe_gt *gt;
>
>+	/** @oa_unit: oa unit for this stream */
>+	struct xe_oa_unit *oa_unit;
>+
> 	/** @hwe: hardware engine associated with this oa stream */
> 	struct xe_hw_engine *hwe;
>
>-- 
>2.48.1
>

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 4/5] drm/xe/oa: Assign hwe for OAM_SAG
  2025-06-03 20:21 ` [PATCH 4/5] drm/xe/oa: Assign hwe for OAM_SAG Ashutosh Dixit
@ 2025-06-05  0:14   ` Umesh Nerlige Ramappa
  2025-06-06 16:07     ` Dixit, Ashutosh
  0 siblings, 1 reply; 24+ messages in thread
From: Umesh Nerlige Ramappa @ 2025-06-05  0:14 UTC (permalink / raw)
  To: Ashutosh Dixit; +Cc: intel-xe

On Tue, Jun 03, 2025 at 01:21:32PM -0700, Ashutosh Dixit wrote:
>Because OAM_SAG doesn't have an attached hwe, assign another hwe belonging
>to the same gt (and different OAM unit) to OAM_SAG. A hwe is needed for
>batch submissions to program OA HW.
>
>Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
>---
> drivers/gpu/drm/xe/xe_oa.c       | 54 +++++++++++++++++++-------------
> drivers/gpu/drm/xe/xe_oa_types.h |  3 ++
> 2 files changed, 35 insertions(+), 22 deletions(-)
>
>diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
>index 4d6d9f0189a83..35157424010bb 100644
>--- a/drivers/gpu/drm/xe/xe_oa.c
>+++ b/drivers/gpu/drm/xe/xe_oa.c
>@@ -1923,37 +1923,45 @@ u16 xe_oa_unit_id(struct xe_hw_engine *hwe)
> 		hwe->oa_unit->oa_unit_id : U16_MAX;
> }
>
>+/* A hwe must be assigned to stream/oa_unit for batch submissions */
> static int xe_oa_assign_hwe(struct xe_oa *oa, struct xe_oa_open_param *param)
> {
>-	struct xe_gt *gt;
>-	int i, ret = 0;
>+	struct xe_hw_engine *hwe;
>+	enum xe_hw_engine_id id;
>+	int ret = 0;
>+
>+	/* If not provided, OA unit defaults to OA unit 0 as per uapi */
>+	if (!param->oa_unit)
>+		param->oa_unit = &xe_device_get_gt(oa->xe, 0)->oa.oa_unit[0];
>
>+	/* When we have an exec_q, get hwe from the exec_q */
> 	if (param->exec_q) {
>-		/* When we have an exec_q, get hwe from the exec_q */
> 		param->hwe = xe_gt_hw_engine(param->exec_q->gt, param->exec_q->class,
> 					     param->engine_instance, true);
>-	} else {
>-		struct xe_hw_engine *hwe;
>-		enum xe_hw_engine_id id;
>-
>-		/* Else just get the first hwe attached to the oa unit */
>-		for_each_gt(gt, oa->xe, i) {
>-			for_each_hw_engine(hwe, gt, id) {
>-				if (hwe->oa_unit == param->oa_unit) {
>-					param->hwe = hwe;
>-					goto out;
>-				}
>-			}
>-		}
>+		if (!param->hwe || param->hwe->oa_unit != param->oa_unit)
>+			goto err;
>+		goto out;
> 	}
>-out:
>-	if (!param->hwe || param->hwe->oa_unit != param->oa_unit) {
>-		drm_dbg(&oa->xe->drm, "Unable to find hwe (%d, %d) for OA unit ID %d\n",
>-			param->exec_q ? param->exec_q->class : -1,
>-			param->engine_instance, param->oa_unit->oa_unit_id);
>-		ret = -EINVAL;
>+
>+	/* Else just get the first hwe attached to the oa unit */
>+	for_each_hw_engine(hwe, param->oa_unit->gt, id) {
>+		if (hwe->oa_unit == param->oa_unit) {
>+			param->hwe = hwe;
>+			goto out;
>+		}
> 	}
>
>+	/* If we still didn't find a hwe, just get one from the same gt */
>+	for_each_hw_engine(hwe, param->oa_unit->gt, id) {

Not sure if for_each_hw_engine omits reserved engines. If we should not 
use reserved engines, we should check for that here using 
xe_hw_engine_is_reserved(). Also, maybe we should only try to submit the 
batch on engine classes supported by OA. Submitting the batch from other 
engines (like bcs) is not really tested.

Thanks,
Umesh

>+		param->hwe = hwe;
>+		goto out;
>+	}
>+err:
>+	drm_dbg(&oa->xe->drm, "Unable to find hwe (%d, %d) for OA unit ID %d\n",
>+		param->exec_q ? param->exec_q->class : -1,
>+		param->engine_instance, param->oa_unit->oa_unit_id);
>+	ret = -EINVAL;
>+out:
> 	return ret;
> }
>
>@@ -2578,6 +2586,8 @@ static void __xe_oa_init_oa_units(struct xe_gt *gt)
> 				DRM_XE_OA_UNIT_TYPE_OAM_SAG : DRM_XE_OA_UNIT_TYPE_OAM;
> 		}
>
>+		u->gt = gt;
>+
> 		xe_mmio_write32(&gt->mmio, u->regs.oa_ctrl, 0);
>
> 		/* Ensure MMIO trigger remains disabled till there is a stream */
>diff --git a/drivers/gpu/drm/xe/xe_oa_types.h b/drivers/gpu/drm/xe/xe_oa_types.h
>index a01c85931e2a5..2628f78c4e8dc 100644
>--- a/drivers/gpu/drm/xe/xe_oa_types.h
>+++ b/drivers/gpu/drm/xe/xe_oa_types.h
>@@ -95,6 +95,9 @@ struct xe_oa_unit {
> 	/** @oa_unit_id: identifier for the OA unit */
> 	u16 oa_unit_id;
>
>+	/** @gt: gt associated with the OA unit */
>+	struct xe_gt *gt;
>+
> 	/** @type: Type of OA unit - OAM, OAG etc. */
> 	enum drm_xe_oa_unit_type type;
>
>-- 
>2.48.1
>

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 5/5] drm/xe/oa: Enable OAM latency measurement
  2025-06-03 20:21 ` [PATCH 5/5] drm/xe/oa: Enable OAM latency measurement Ashutosh Dixit
@ 2025-06-05 16:25   ` Umesh Nerlige Ramappa
  0 siblings, 0 replies; 24+ messages in thread
From: Umesh Nerlige Ramappa @ 2025-06-05 16:25 UTC (permalink / raw)
  To: Ashutosh Dixit; +Cc: intel-xe

On Tue, Jun 03, 2025 at 01:21:33PM -0700, Ashutosh Dixit wrote:
>Enable OAM latency measurement for Xe3+ platforms.
>
>Bspec: 58840
>
>v2: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
>
>Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>

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

>---
> drivers/gpu/drm/xe/regs/xe_oa_regs.h |  3 +++
> drivers/gpu/drm/xe/xe_oa.c           | 11 ++++++++++-
> 2 files changed, 13 insertions(+), 1 deletion(-)
>
>diff --git a/drivers/gpu/drm/xe/regs/xe_oa_regs.h b/drivers/gpu/drm/xe/regs/xe_oa_regs.h
>index a79ad2da070c2..e693a50706f84 100644
>--- a/drivers/gpu/drm/xe/regs/xe_oa_regs.h
>+++ b/drivers/gpu/drm/xe/regs/xe_oa_regs.h
>@@ -97,4 +97,7 @@
> #define OAM_STATUS(base)			XE_REG((base) + OAM_STATUS_OFFSET)
> #define OAM_MMIO_TRG(base)			XE_REG((base) + OAM_MMIO_TRG_OFFSET)
>
>+#define OAM_COMPRESSION_T3_CONTROL		XE_REG(0x1c2e00)
>+#define  OAM_LAT_MEASURE_ENABLE			REG_BIT(4)
>+
> #endif
>diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
>index 35157424010bb..5aa68bd63b00d 100644
>--- a/drivers/gpu/drm/xe/xe_oa.c
>+++ b/drivers/gpu/drm/xe/xe_oa.c
>@@ -844,6 +844,11 @@ static void xe_oa_disable_metric_set(struct xe_oa_stream *stream)
>
> 	/* Reset PMON Enable to save power. */
> 	xe_mmio_rmw32(mmio, XELPMP_SQCNT1, sqcnt1, 0);
>+
>+	if ((stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAM ||
>+	     stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAM_SAG) &&
>+	    GRAPHICS_VER(stream->oa->xe) >= 30)
>+		xe_mmio_rmw32(mmio, OAM_COMPRESSION_T3_CONTROL, OAM_LAT_MEASURE_ENABLE, 0);
> }
>
> static void xe_oa_stream_destroy(struct xe_oa_stream *stream)
>@@ -1111,9 +1116,13 @@ static int xe_oa_enable_metric_set(struct xe_oa_stream *stream)
> 	 */
> 	sqcnt1 = SQCNT1_PMON_ENABLE |
> 		 (HAS_OA_BPC_REPORTING(stream->oa->xe) ? SQCNT1_OABPC : 0);
>-
> 	xe_mmio_rmw32(mmio, XELPMP_SQCNT1, 0, sqcnt1);
>
>+	if ((stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAM ||
>+	     stream->oa_unit->type == DRM_XE_OA_UNIT_TYPE_OAM_SAG) &&
>+	    GRAPHICS_VER(stream->oa->xe) >= 30)
>+		xe_mmio_rmw32(mmio, OAM_COMPRESSION_T3_CONTROL, 0, OAM_LAT_MEASURE_ENABLE);
>+
> 	/* Configure OAR/OAC */
> 	if (stream->exec_q) {
> 		ret = xe_oa_configure_oa_context(stream, true);
>-- 
>2.48.1
>

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units
  2025-06-04 23:42   ` Umesh Nerlige Ramappa
@ 2025-06-05 18:28     ` Dixit, Ashutosh
  2025-06-06 16:42       ` Dixit, Ashutosh
  0 siblings, 1 reply; 24+ messages in thread
From: Dixit, Ashutosh @ 2025-06-05 18:28 UTC (permalink / raw)
  To: Umesh Nerlige Ramappa; +Cc: intel-xe

On Wed, 04 Jun 2025 16:42:04 -0700, Umesh Nerlige Ramappa wrote:
>

Hi Umesh,

> On Tue, Jun 03, 2025 at 01:21:29PM -0700, Ashutosh Dixit wrote:
> > On Xe2+ platforms, media engines are attached to "SCMI" OA media (OAM)
> > units. One or more SCMI OAM units might be present on a platform. In
> > addition there is another OAM unit for global events, called
> > OAM-SAG. Performance metrics for media workloads can be obtained from these
> > OAM units, similar to OAG.
> >
> > Expose these OAM units for userspace to use. OAM-SAG is exposed as an OA
> > unit without any attached engines.
> >
> > Bspec: 70819, 67103, 63844, 72572, 74476, 61284
> >
> > v2: Fix xe_gt_WARN_ON in __hwe_oam_unit for < 12.7 platforms
> > v3: Return XE_OA_UNIT_INVALID for < 12.7 to indicate no OAM units
> > v4: Move xe_oa_print_oa_units() to separate patch
> > v5: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
> >
> > Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
> > ---
> > drivers/gpu/drm/xe/xe_oa.c | 68 ++++++++++++++++++++++++++++----------
> > include/uapi/drm/xe_drm.h  |  3 ++
> > 2 files changed, 54 insertions(+), 17 deletions(-)
> >
> > diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
> > index fb842fa0552e5..0de0d5a18df74 100644
> > --- a/drivers/gpu/drm/xe/xe_oa.c
> > +++ b/drivers/gpu/drm/xe/xe_oa.c
> > @@ -43,6 +43,12 @@
> > #define DEFAULT_POLL_PERIOD_NS (NSEC_PER_SEC / DEFAULT_POLL_FREQUENCY_HZ)
> > #define XE_OA_UNIT_INVALID U32_MAX
> >
> > +enum xe_oam_unit_type {
> > +	XE_OAM_UNIT_SAG,
> > +	XE_OAM_UNIT_SCMI_0,
> > +	XE_OAM_UNIT_SCMI_1,
> > +};
> > +
> > enum xe_oa_submit_deps {
> >	XE_OA_SUBMIT_NO_DEPS,
> >	XE_OA_SUBMIT_ADD_DEPS,
> > @@ -1881,6 +1887,7 @@ static bool engine_supports_oa_format(const struct xe_hw_engine *hwe, int type)
> >		return type == DRM_XE_OA_FMT_TYPE_OAG || type == DRM_XE_OA_FMT_TYPE_OAR ||
> >			type == DRM_XE_OA_FMT_TYPE_OAC || type == DRM_XE_OA_FMT_TYPE_PEC;
> >	case DRM_XE_OA_UNIT_TYPE_OAM:
> > +	case DRM_XE_OA_UNIT_TYPE_OAM_SAG:
> >		return type == DRM_XE_OA_FMT_TYPE_OAM || type == DRM_XE_OA_FMT_TYPE_OAM_MPEC;
> >	default:
> >		return false;
> > @@ -2448,20 +2455,38 @@ int xe_oa_register(struct xe_device *xe)
> >
> > static u32 num_oa_units_per_gt(struct xe_gt *gt)
> > {
> > -	return 1;
> > +	if (!xe_gt_is_media_type(gt) || GRAPHICS_VER(gt_to_xe(gt)) < 20)
> > +		return 1;
> > +	else if (!IS_DGFX(gt_to_xe(gt)))
> > +		return XE_OAM_UNIT_SCMI_0 + 1; /* SAG + SCMI_0 */
> > +	else
> > +		return XE_OAM_UNIT_SCMI_1 + 1; /* SAG + SCMI_0 + SCMI_1 */
> > }
> >
> > static u32 __hwe_oam_unit(struct xe_hw_engine *hwe)
> > {
> > -	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) >= 1270) {
> > -		/*
> > -		 * There's 1 SAMEDIA gt and 1 OAM per SAMEDIA gt. All media slices
> > -		 * within the gt use the same OAM. All MTL/LNL SKUs list 1 SA MEDIA
> > -		 */
> > -		xe_gt_WARN_ON(hwe->gt, hwe->gt->info.type != XE_GT_TYPE_MEDIA);
> > +	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) < 1270)
> > +		return XE_OA_UNIT_INVALID;
> >
> > +	xe_gt_WARN_ON(hwe->gt, !xe_gt_is_media_type(hwe->gt));
> > +
> > +	if (GRAPHICS_VER(gt_to_xe(hwe->gt)) < 20)
> >		return 0;
> > -	}
> > +	/*
> > +	 * XE_OAM_UNIT_SAG has only GSCCS attached to it, but only on some platforms. Also
> > +	 * GSCCS cannot be used to submit batches to program the OAM unit. Therefore we don't
> > +	 * assign an OA unit to GSCCS. This means that XE_OAM_UNIT_SAG is exposed as an OA
> > +	 * unit without attached engines. Fused off engines can also result in oa_unit's with
> > +	 * num_engines == 0. OA streams can be opened on all OA units.
> > +	 */
> > +	else if (hwe->engine_id == XE_HW_ENGINE_GSCCS0)
>
> You could just drop the case XE_ENGINE_CLASS_OTHER in caller
> (__hwe_oa_unit()) and then you dont need the XE_HW_ENGINE_GSCCS0 check
> here.

Yes, I was doing that initially. But then I changed to this to make it
*explicit* that even when GSC is attached to OAM-SAG, it is not assigned to
any OA unit. Because it is really an exception, as the comment above
explains.

If you are asking why XE_ENGINE_CLASS_OTHER calls __hwe_oam_unit(), that is
because GSC is present on media GT and is used for HuC authentication
etc. (also related to media).

If you insist I can change it, but I think it is better to leave as
is. This way it is part of the code, the other way it will be in a comment
(and would be implicit and later people might wonder if it is missed). Let
me know.

>
> > +		return XE_OA_UNIT_INVALID;
> > +	else if (!IS_DGFX(gt_to_xe(hwe->gt)))
> > +		return XE_OAM_UNIT_SCMI_0;
> > +	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_DECODE)
> > +		return (hwe->instance / 2 & 0x1) + 1;
>
> should be same as (hwe->instance / 2) + 1;

To map any possible VCS (VCS0 - VCS7) to OAM-SCMI-0 or OAM-SCMI-1 we need
the '& 0x1'.

>
> > +	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_ENHANCE)
> > +		return (hwe->instance & 0x1) + 1;
>
> same here, should be same as (hwe->instance + 1)

Similarly, to map any possible VECS (VECS0 - VECS3) to OAM-SCMI-0 or 1 we
need the '& 0x1'.

Thanks.
--
Ashutosh

^ permalink raw reply	[flat|nested] 24+ messages in thread

* [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units
  2025-06-06 16:02 [PATCH v4 0/5] " Ashutosh Dixit
@ 2025-06-06 16:02 ` Ashutosh Dixit
  2025-06-06 17:37   ` Umesh Nerlige Ramappa
  0 siblings, 1 reply; 24+ messages in thread
From: Ashutosh Dixit @ 2025-06-06 16:02 UTC (permalink / raw)
  To: intel-xe; +Cc: Umesh Nerlige Ramappa

On Xe2+ platforms, media engines are attached to "SCMI" OA media (OAM)
units. One or more SCMI OAM units might be present on a platform. In
addition there is another OAM unit for global events, called
OAM-SAG. Performance metrics for media workloads can be obtained from these
OAM units, similar to OAG.

Expose these OAM units for userspace to use. OAM-SAG is exposed as an OA
unit without any attached engines.

Bspec: 70819, 67103, 63844, 72572, 74476, 61284

v2: Fix xe_gt_WARN_ON in __hwe_oam_unit for < 12.7 platforms
v3: Return XE_OA_UNIT_INVALID for < 12.7 to indicate no OAM units
v4: Move xe_oa_print_oa_units() to separate patch
v5: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG

Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
---
 drivers/gpu/drm/xe/xe_oa.c | 68 ++++++++++++++++++++++++++++----------
 include/uapi/drm/xe_drm.h  |  3 ++
 2 files changed, 54 insertions(+), 17 deletions(-)

diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
index fb842fa0552e5..0de0d5a18df74 100644
--- a/drivers/gpu/drm/xe/xe_oa.c
+++ b/drivers/gpu/drm/xe/xe_oa.c
@@ -43,6 +43,12 @@
 #define DEFAULT_POLL_PERIOD_NS (NSEC_PER_SEC / DEFAULT_POLL_FREQUENCY_HZ)
 #define XE_OA_UNIT_INVALID U32_MAX
 
+enum xe_oam_unit_type {
+	XE_OAM_UNIT_SAG,
+	XE_OAM_UNIT_SCMI_0,
+	XE_OAM_UNIT_SCMI_1,
+};
+
 enum xe_oa_submit_deps {
 	XE_OA_SUBMIT_NO_DEPS,
 	XE_OA_SUBMIT_ADD_DEPS,
@@ -1881,6 +1887,7 @@ static bool engine_supports_oa_format(const struct xe_hw_engine *hwe, int type)
 		return type == DRM_XE_OA_FMT_TYPE_OAG || type == DRM_XE_OA_FMT_TYPE_OAR ||
 			type == DRM_XE_OA_FMT_TYPE_OAC || type == DRM_XE_OA_FMT_TYPE_PEC;
 	case DRM_XE_OA_UNIT_TYPE_OAM:
+	case DRM_XE_OA_UNIT_TYPE_OAM_SAG:
 		return type == DRM_XE_OA_FMT_TYPE_OAM || type == DRM_XE_OA_FMT_TYPE_OAM_MPEC;
 	default:
 		return false;
@@ -2448,20 +2455,38 @@ int xe_oa_register(struct xe_device *xe)
 
 static u32 num_oa_units_per_gt(struct xe_gt *gt)
 {
-	return 1;
+	if (!xe_gt_is_media_type(gt) || GRAPHICS_VER(gt_to_xe(gt)) < 20)
+		return 1;
+	else if (!IS_DGFX(gt_to_xe(gt)))
+		return XE_OAM_UNIT_SCMI_0 + 1; /* SAG + SCMI_0 */
+	else
+		return XE_OAM_UNIT_SCMI_1 + 1; /* SAG + SCMI_0 + SCMI_1 */
 }
 
 static u32 __hwe_oam_unit(struct xe_hw_engine *hwe)
 {
-	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) >= 1270) {
-		/*
-		 * There's 1 SAMEDIA gt and 1 OAM per SAMEDIA gt. All media slices
-		 * within the gt use the same OAM. All MTL/LNL SKUs list 1 SA MEDIA
-		 */
-		xe_gt_WARN_ON(hwe->gt, hwe->gt->info.type != XE_GT_TYPE_MEDIA);
+	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) < 1270)
+		return XE_OA_UNIT_INVALID;
 
+	xe_gt_WARN_ON(hwe->gt, !xe_gt_is_media_type(hwe->gt));
+
+	if (GRAPHICS_VER(gt_to_xe(hwe->gt)) < 20)
 		return 0;
-	}
+	/*
+	 * XE_OAM_UNIT_SAG has only GSCCS attached to it, but only on some platforms. Also
+	 * GSCCS cannot be used to submit batches to program the OAM unit. Therefore we don't
+	 * assign an OA unit to GSCCS. This means that XE_OAM_UNIT_SAG is exposed as an OA
+	 * unit without attached engines. Fused off engines can also result in oa_unit's with
+	 * num_engines == 0. OA streams can be opened on all OA units.
+	 */
+	else if (hwe->engine_id == XE_HW_ENGINE_GSCCS0)
+		return XE_OA_UNIT_INVALID;
+	else if (!IS_DGFX(gt_to_xe(hwe->gt)))
+		return XE_OAM_UNIT_SCMI_0;
+	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_DECODE)
+		return (hwe->instance / 2 & 0x1) + 1;
+	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_ENHANCE)
+		return (hwe->instance & 0x1) + 1;
 
 	return XE_OA_UNIT_INVALID;
 }
@@ -2475,6 +2500,7 @@ static u32 __hwe_oa_unit(struct xe_hw_engine *hwe)
 
 	case XE_ENGINE_CLASS_VIDEO_DECODE:
 	case XE_ENGINE_CLASS_VIDEO_ENHANCE:
+	case XE_ENGINE_CLASS_OTHER:
 		return __hwe_oam_unit(hwe);
 
 	default:
@@ -2514,18 +2540,25 @@ static struct xe_oa_regs __oag_regs(void)
 
 static void __xe_oa_init_oa_units(struct xe_gt *gt)
 {
-	const u32 mtl_oa_base[] = { 0x13000 };
+	/* Actual address is MEDIA_GT_GSI_OFFSET + oam_base_addr[i] */
+	const u32 oam_base_addr[] = {
+		[XE_OAM_UNIT_SAG]    = 0x13000,
+		[XE_OAM_UNIT_SCMI_0] = 0x14000,
+		[XE_OAM_UNIT_SCMI_1] = 0x14800,
+	};
 	int i, num_units = gt->oa.num_oa_units;
 
 	for (i = 0; i < num_units; i++) {
 		struct xe_oa_unit *u = &gt->oa.oa_unit[i];
 
-		if (gt->info.type != XE_GT_TYPE_MEDIA) {
+		if (!xe_gt_is_media_type(gt)) {
 			u->regs = __oag_regs();
 			u->type = DRM_XE_OA_UNIT_TYPE_OAG;
-		} else if (GRAPHICS_VERx100(gt_to_xe(gt)) >= 1270) {
-			u->regs = __oam_regs(mtl_oa_base[i]);
-			u->type = DRM_XE_OA_UNIT_TYPE_OAM;
+		} else {
+			xe_gt_assert(gt, GRAPHICS_VERx100(gt_to_xe(gt)) >= 1270);
+			u->regs = __oam_regs(oam_base_addr[i]);
+			u->type = i == XE_OAM_UNIT_SAG && GRAPHICS_VER(gt_to_xe(gt)) >= 20 ?
+				DRM_XE_OA_UNIT_TYPE_OAM_SAG : DRM_XE_OA_UNIT_TYPE_OAM;
 		}
 
 		xe_mmio_write32(&gt->mmio, u->regs.oa_ctrl, 0);
@@ -2560,10 +2593,6 @@ static int xe_oa_init_gt(struct xe_gt *gt)
 		}
 	}
 
-	/*
-	 * Fused off engines can result in oa_unit's with num_engines == 0. These units
-	 * will appear in OA unit query, but no OA streams can be opened on them.
-	 */
 	gt->oa.num_oa_units = num_oa_units;
 	gt->oa.oa_unit = u;
 
@@ -2579,6 +2608,11 @@ static int xe_oa_init_oa_units(struct xe_oa *oa)
 	struct xe_gt *gt;
 	int i, ret;
 
+	/* Needed for OAM implementation here */
+	BUILD_BUG_ON(XE_OAM_UNIT_SAG != 0);
+	BUILD_BUG_ON(XE_OAM_UNIT_SCMI_0 != 1);
+	BUILD_BUG_ON(XE_OAM_UNIT_SCMI_1 != 2);
+
 	for_each_gt(gt, oa->xe, i) {
 		ret = xe_oa_init_gt(gt);
 		if (ret)
diff --git a/include/uapi/drm/xe_drm.h b/include/uapi/drm/xe_drm.h
index 6a702ba7817c3..5460ba1e4cc37 100644
--- a/include/uapi/drm/xe_drm.h
+++ b/include/uapi/drm/xe_drm.h
@@ -1617,6 +1617,9 @@ enum drm_xe_oa_unit_type {
 
 	/** @DRM_XE_OA_UNIT_TYPE_OAM: OAM OA unit */
 	DRM_XE_OA_UNIT_TYPE_OAM,
+
+	/** @DRM_XE_OA_UNIT_TYPE_OAM_SAG: OAM_SAG OA unit */
+	DRM_XE_OA_UNIT_TYPE_OAM_SAG,
 };
 
 /**
-- 
2.48.1


^ permalink raw reply related	[flat|nested] 24+ messages in thread

* Re: [PATCH 2/5] drm/xe/oa: Print hwe to OA unit mapping
  2025-06-04 23:49   ` Umesh Nerlige Ramappa
@ 2025-06-06 16:05     ` Dixit, Ashutosh
  0 siblings, 0 replies; 24+ messages in thread
From: Dixit, Ashutosh @ 2025-06-06 16:05 UTC (permalink / raw)
  To: Umesh Nerlige Ramappa; +Cc: intel-xe

On Wed, 04 Jun 2025 16:49:11 -0700, Umesh Nerlige Ramappa wrote:
>
> On Tue, Jun 03, 2025 at 01:21:30PM -0700, Ashutosh Dixit wrote:
> > Print hwe to OA unit mapping to dmesg, to help debug for current and new
> > platforms.
> >
> > Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
> > ---
> > drivers/gpu/drm/xe/xe_oa.c | 27 +++++++++++++++++++++++++++
> > 1 file changed, 27 insertions(+)
> >
> > diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
> > index 0de0d5a18df74..94faa4ed2012f 100644
> > --- a/drivers/gpu/drm/xe/xe_oa.c
> > +++ b/drivers/gpu/drm/xe/xe_oa.c
> > @@ -2603,6 +2603,31 @@ static int xe_oa_init_gt(struct xe_gt *gt)
> >	return 0;
> > }
> >
> > +static void xe_oa_print_oa_units(struct xe_oa *oa)
> > +{
> > +	enum xe_hw_engine_id hwe_id;
> > +	struct xe_hw_engine *hwe;
> > +	struct xe_oa_unit *u;
> > +	struct xe_gt *gt;
> > +	int gt_id, i, n;
> > +	char buf[256];
> > +
> > +	for_each_gt(gt, oa->xe, gt_id) {
> > +		for (i = 0; i < gt->oa.num_oa_units; i++) {
> > +			u = &gt->oa.oa_unit[i];
> > +			buf[0] = '\0';
> > +			n = 0;
> > +
> > +			for_each_hw_engine(hwe, gt, hwe_id)
> > +				if (xe_oa_unit_id(hwe) == u->oa_unit_id)
> > +					n += scnprintf(buf + n, sizeof(buf) - n, "%s ", hwe->name);
> > +
> > +			xe_gt_dbg(gt, "oa_unit %d, type %d, Engines: %s\n",
> > +				  u->oa_unit_id, u->type, buf);
> > +		}
> > +	}
> > +}
> > +
>
> nit: I would at least move one of the inner for loops outside to a separate
> helper.

Separated out the first inner loop into xe_oa_print_gt_oa_units().

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

Thanks.
--
Ashutosh


>
> > static int xe_oa_init_oa_units(struct xe_oa *oa)
> > {
> >	struct xe_gt *gt;
> > @@ -2619,6 +2644,8 @@ static int xe_oa_init_oa_units(struct xe_oa *oa)
> >			return ret;
> >	}
> >
> > +	xe_oa_print_oa_units(oa);
> > +
> >	return 0;
> > }
> >
> > --
> > 2.48.1
> >

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 4/5] drm/xe/oa: Assign hwe for OAM_SAG
  2025-06-05  0:14   ` Umesh Nerlige Ramappa
@ 2025-06-06 16:07     ` Dixit, Ashutosh
  0 siblings, 0 replies; 24+ messages in thread
From: Dixit, Ashutosh @ 2025-06-06 16:07 UTC (permalink / raw)
  To: Umesh Nerlige Ramappa; +Cc: intel-xe

On Wed, 04 Jun 2025 17:14:40 -0700, Umesh Nerlige Ramappa wrote:
>
> On Tue, Jun 03, 2025 at 01:21:32PM -0700, Ashutosh Dixit wrote:
> > Because OAM_SAG doesn't have an attached hwe, assign another hwe belonging
> > to the same gt (and different OAM unit) to OAM_SAG. A hwe is needed for
> > batch submissions to program OA HW.
> >
> > Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
> > ---
> > drivers/gpu/drm/xe/xe_oa.c       | 54 +++++++++++++++++++-------------
> > drivers/gpu/drm/xe/xe_oa_types.h |  3 ++
> > 2 files changed, 35 insertions(+), 22 deletions(-)
> >
> > diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
> > index 4d6d9f0189a83..35157424010bb 100644
> > --- a/drivers/gpu/drm/xe/xe_oa.c
> > +++ b/drivers/gpu/drm/xe/xe_oa.c
> > @@ -1923,37 +1923,45 @@ u16 xe_oa_unit_id(struct xe_hw_engine *hwe)
> >		hwe->oa_unit->oa_unit_id : U16_MAX;
> > }
> >
> > +/* A hwe must be assigned to stream/oa_unit for batch submissions */
> > static int xe_oa_assign_hwe(struct xe_oa *oa, struct xe_oa_open_param *param)
> > {
> > -	struct xe_gt *gt;
> > -	int i, ret = 0;
> > +	struct xe_hw_engine *hwe;
> > +	enum xe_hw_engine_id id;
> > +	int ret = 0;
> > +
> > +	/* If not provided, OA unit defaults to OA unit 0 as per uapi */
> > +	if (!param->oa_unit)
> > +		param->oa_unit = &xe_device_get_gt(oa->xe, 0)->oa.oa_unit[0];
> >
> > +	/* When we have an exec_q, get hwe from the exec_q */
> >	if (param->exec_q) {
> > -		/* When we have an exec_q, get hwe from the exec_q */
> >		param->hwe = xe_gt_hw_engine(param->exec_q->gt, param->exec_q->class,
> >					     param->engine_instance, true);
> > -	} else {
> > -		struct xe_hw_engine *hwe;
> > -		enum xe_hw_engine_id id;
> > -
> > -		/* Else just get the first hwe attached to the oa unit */
> > -		for_each_gt(gt, oa->xe, i) {
> > -			for_each_hw_engine(hwe, gt, id) {
> > -				if (hwe->oa_unit == param->oa_unit) {
> > -					param->hwe = hwe;
> > -					goto out;
> > -				}
> > -			}
> > -		}
> > +		if (!param->hwe || param->hwe->oa_unit != param->oa_unit)
> > +			goto err;
> > +		goto out;
> >	}
> > -out:
> > -	if (!param->hwe || param->hwe->oa_unit != param->oa_unit) {
> > -		drm_dbg(&oa->xe->drm, "Unable to find hwe (%d, %d) for OA unit ID %d\n",
> > -			param->exec_q ? param->exec_q->class : -1,
> > -			param->engine_instance, param->oa_unit->oa_unit_id);
> > -		ret = -EINVAL;
> > +
> > +	/* Else just get the first hwe attached to the oa unit */
> > +	for_each_hw_engine(hwe, param->oa_unit->gt, id) {
> > +		if (hwe->oa_unit == param->oa_unit) {
> > +			param->hwe = hwe;
> > +			goto out;
> > +		}
> >	}
> >
> > +	/* If we still didn't find a hwe, just get one from the same gt */
> > +	for_each_hw_engine(hwe, param->oa_unit->gt, id) {
>
> Not sure if for_each_hw_engine omits reserved engines.

It does not, they have to be omitted separately.

> If we should not use reserved engines, we should check for that here
> using xe_hw_engine_is_reserved().

Reserved means those engines are not available for user space. I think it
is ok for the kernel to use them, at least in some cases reserved means
reserved for the kernel. Reserved engines are different from fused off
engines and for_each_hw_engine() skips fused off engines (via
xe_hw_engine_is_valid()).

I was looking at OA code and looks like in OA we have assumed (mostly
without realizing it :/) that reserved engines can be used by OA internally
and reserved engines are attached to OA units. But we don't expose reserved
engines to userspace in the OA query.

So along those lines, I have skipped checking for reserved engines here. If
we really need to skip reserved engines, that should be done globally in OA
code (don't attach reserved engines to OA units itself), otherwise it will
unnecessarily mess up the code. So for now I am assuming OA code reserved
engine usage is ok.

> Also, maybe we should only try to submit the batch on engine classes
> supported by OA. Submitting the batch from other engines (like bcs) is
> not really tested.

I have added this check now, good catch:

	if (!hwe->oa_unit)
		continue;

Thanks.
--
Ashutosh

>
> > +		param->hwe = hwe;
> > +		goto out;
> > +	}
> > +err:
> > +	drm_dbg(&oa->xe->drm, "Unable to find hwe (%d, %d) for OA unit ID %d\n",
> > +		param->exec_q ? param->exec_q->class : -1,
> > +		param->engine_instance, param->oa_unit->oa_unit_id);
> > +	ret = -EINVAL;
> > +out:
> >	return ret;
> > }
> >
> > @@ -2578,6 +2586,8 @@ static void __xe_oa_init_oa_units(struct xe_gt *gt)
> >				DRM_XE_OA_UNIT_TYPE_OAM_SAG : DRM_XE_OA_UNIT_TYPE_OAM;
> >		}
> >
> > +		u->gt = gt;
> > +
> >		xe_mmio_write32(&gt->mmio, u->regs.oa_ctrl, 0);
> >
> >		/* Ensure MMIO trigger remains disabled till there is a stream */
> > diff --git a/drivers/gpu/drm/xe/xe_oa_types.h b/drivers/gpu/drm/xe/xe_oa_types.h
> > index a01c85931e2a5..2628f78c4e8dc 100644
> > --- a/drivers/gpu/drm/xe/xe_oa_types.h
> > +++ b/drivers/gpu/drm/xe/xe_oa_types.h
> > @@ -95,6 +95,9 @@ struct xe_oa_unit {
> >	/** @oa_unit_id: identifier for the OA unit */
> >	u16 oa_unit_id;
> >
> > +	/** @gt: gt associated with the OA unit */
> > +	struct xe_gt *gt;
> > +
> >	/** @type: Type of OA unit - OAM, OAG etc. */
> >	enum drm_xe_oa_unit_type type;
> >
> > --
> > 2.48.1
> >

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units
  2025-06-05 18:28     ` Dixit, Ashutosh
@ 2025-06-06 16:42       ` Dixit, Ashutosh
  0 siblings, 0 replies; 24+ messages in thread
From: Dixit, Ashutosh @ 2025-06-06 16:42 UTC (permalink / raw)
  To: Umesh Nerlige Ramappa; +Cc: intel-xe

On Thu, 05 Jun 2025 11:28:59 -0700, Dixit, Ashutosh wrote:
>
> On Wed, 04 Jun 2025 16:42:04 -0700, Umesh Nerlige Ramappa wrote:
> >

Hi Umesh,

> > On Tue, Jun 03, 2025 at 01:21:29PM -0700, Ashutosh Dixit wrote:
> > > On Xe2+ platforms, media engines are attached to "SCMI" OA media (OAM)
> > > units. One or more SCMI OAM units might be present on a platform. In
> > > addition there is another OAM unit for global events, called
> > > OAM-SAG. Performance metrics for media workloads can be obtained from these
> > > OAM units, similar to OAG.
> > >
> > > Expose these OAM units for userspace to use. OAM-SAG is exposed as an OA
> > > unit without any attached engines.
> > >
> > > Bspec: 70819, 67103, 63844, 72572, 74476, 61284
> > >
> > > v2: Fix xe_gt_WARN_ON in __hwe_oam_unit for < 12.7 platforms
> > > v3: Return XE_OA_UNIT_INVALID for < 12.7 to indicate no OAM units
> > > v4: Move xe_oa_print_oa_units() to separate patch
> > > v5: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
> > >
> > > Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
> > > ---
> > > drivers/gpu/drm/xe/xe_oa.c | 68 ++++++++++++++++++++++++++++----------
> > > include/uapi/drm/xe_drm.h  |  3 ++
> > > 2 files changed, 54 insertions(+), 17 deletions(-)
> > >
> > > diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
> > > index fb842fa0552e5..0de0d5a18df74 100644
> > > --- a/drivers/gpu/drm/xe/xe_oa.c
> > > +++ b/drivers/gpu/drm/xe/xe_oa.c
> > > @@ -43,6 +43,12 @@
> > > #define DEFAULT_POLL_PERIOD_NS (NSEC_PER_SEC / DEFAULT_POLL_FREQUENCY_HZ)
> > > #define XE_OA_UNIT_INVALID U32_MAX
> > >
> > > +enum xe_oam_unit_type {
> > > +	XE_OAM_UNIT_SAG,
> > > +	XE_OAM_UNIT_SCMI_0,
> > > +	XE_OAM_UNIT_SCMI_1,
> > > +};
> > > +
> > > enum xe_oa_submit_deps {
> > >	XE_OA_SUBMIT_NO_DEPS,
> > >	XE_OA_SUBMIT_ADD_DEPS,
> > > @@ -1881,6 +1887,7 @@ static bool engine_supports_oa_format(const struct xe_hw_engine *hwe, int type)
> > >		return type == DRM_XE_OA_FMT_TYPE_OAG || type == DRM_XE_OA_FMT_TYPE_OAR ||
> > >			type == DRM_XE_OA_FMT_TYPE_OAC || type == DRM_XE_OA_FMT_TYPE_PEC;
> > >	case DRM_XE_OA_UNIT_TYPE_OAM:
> > > +	case DRM_XE_OA_UNIT_TYPE_OAM_SAG:
> > >		return type == DRM_XE_OA_FMT_TYPE_OAM || type == DRM_XE_OA_FMT_TYPE_OAM_MPEC;
> > >	default:
> > >		return false;
> > > @@ -2448,20 +2455,38 @@ int xe_oa_register(struct xe_device *xe)
> > >
> > > static u32 num_oa_units_per_gt(struct xe_gt *gt)
> > > {
> > > -	return 1;
> > > +	if (!xe_gt_is_media_type(gt) || GRAPHICS_VER(gt_to_xe(gt)) < 20)
> > > +		return 1;
> > > +	else if (!IS_DGFX(gt_to_xe(gt)))
> > > +		return XE_OAM_UNIT_SCMI_0 + 1; /* SAG + SCMI_0 */
> > > +	else
> > > +		return XE_OAM_UNIT_SCMI_1 + 1; /* SAG + SCMI_0 + SCMI_1 */
> > > }
> > >
> > > static u32 __hwe_oam_unit(struct xe_hw_engine *hwe)
> > > {
> > > -	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) >= 1270) {
> > > -		/*
> > > -		 * There's 1 SAMEDIA gt and 1 OAM per SAMEDIA gt. All media slices
> > > -		 * within the gt use the same OAM. All MTL/LNL SKUs list 1 SA MEDIA
> > > -		 */
> > > -		xe_gt_WARN_ON(hwe->gt, hwe->gt->info.type != XE_GT_TYPE_MEDIA);
> > > +	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) < 1270)
> > > +		return XE_OA_UNIT_INVALID;
> > >
> > > +	xe_gt_WARN_ON(hwe->gt, !xe_gt_is_media_type(hwe->gt));
> > > +
> > > +	if (GRAPHICS_VER(gt_to_xe(hwe->gt)) < 20)
> > >		return 0;
> > > -	}
> > > +	/*
> > > +	 * XE_OAM_UNIT_SAG has only GSCCS attached to it, but only on some platforms. Also
> > > +	 * GSCCS cannot be used to submit batches to program the OAM unit. Therefore we don't
> > > +	 * assign an OA unit to GSCCS. This means that XE_OAM_UNIT_SAG is exposed as an OA
> > > +	 * unit without attached engines. Fused off engines can also result in oa_unit's with
> > > +	 * num_engines == 0. OA streams can be opened on all OA units.
> > > +	 */
> > > +	else if (hwe->engine_id == XE_HW_ENGINE_GSCCS0)
> >
> > You could just drop the case XE_ENGINE_CLASS_OTHER in caller
> > (__hwe_oa_unit()) and then you dont need the XE_HW_ENGINE_GSCCS0 check
> > here.
>
> Yes, I was doing that initially. But then I changed to this to make it
> *explicit* that even when GSC is attached to OAM-SAG, it is not assigned to
> any OA unit. Because it is really an exception, as the comment above
> explains.
>
> If you are asking why XE_ENGINE_CLASS_OTHER calls __hwe_oam_unit(), that is
> because GSC is present on media GT and is used for HuC authentication
> etc. (also related to media).
>
> If you insist I can change it, but I think it is better to leave as
> is. This way it is part of the code, the other way it will be in a comment
> (and would be implicit and later people might wonder if it is missed). Let
> me know.
>
> >
> > > +		return XE_OA_UNIT_INVALID;
> > > +	else if (!IS_DGFX(gt_to_xe(hwe->gt)))
> > > +		return XE_OAM_UNIT_SCMI_0;
> > > +	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_DECODE)
> > > +		return (hwe->instance / 2 & 0x1) + 1;
> >
> > should be same as (hwe->instance / 2) + 1;
>
> To map any possible VCS (VCS0 - VCS7) to OAM-SCMI-0 or OAM-SCMI-1 we need
> the '& 0x1'.
>
> >
> > > +	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_ENHANCE)
> > > +		return (hwe->instance & 0x1) + 1;
> >
> > same here, should be same as (hwe->instance + 1)
>
> Similarly, to map any possible VECS (VECS0 - VECS3) to OAM-SCMI-0 or 1 we
> need the '& 0x1'.

So I ended up not making any changes to this patch. Anyway please take
another look and let me know what you think.

Thanks.
--
Ashutosh

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units
  2025-06-06 16:02 ` [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units Ashutosh Dixit
@ 2025-06-06 17:37   ` Umesh Nerlige Ramappa
  2025-06-06 19:21     ` Dixit, Ashutosh
  0 siblings, 1 reply; 24+ messages in thread
From: Umesh Nerlige Ramappa @ 2025-06-06 17:37 UTC (permalink / raw)
  To: Ashutosh Dixit; +Cc: intel-xe

On Fri, Jun 06, 2025 at 09:02:49AM -0700, Ashutosh Dixit wrote:
>On Xe2+ platforms, media engines are attached to "SCMI" OA media (OAM)
>units. One or more SCMI OAM units might be present on a platform. In
>addition there is another OAM unit for global events, called
>OAM-SAG. Performance metrics for media workloads can be obtained from these
>OAM units, similar to OAG.
>
>Expose these OAM units for userspace to use. OAM-SAG is exposed as an OA
>unit without any attached engines.
>
>Bspec: 70819, 67103, 63844, 72572, 74476, 61284
>
>v2: Fix xe_gt_WARN_ON in __hwe_oam_unit for < 12.7 platforms
>v3: Return XE_OA_UNIT_INVALID for < 12.7 to indicate no OAM units
>v4: Move xe_oa_print_oa_units() to separate patch
>v5: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
>
>Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>

LGTM,

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

Thanks,
Umesh
>---
> drivers/gpu/drm/xe/xe_oa.c | 68 ++++++++++++++++++++++++++++----------
> include/uapi/drm/xe_drm.h  |  3 ++
> 2 files changed, 54 insertions(+), 17 deletions(-)
>
>diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
>index fb842fa0552e5..0de0d5a18df74 100644
>--- a/drivers/gpu/drm/xe/xe_oa.c
>+++ b/drivers/gpu/drm/xe/xe_oa.c
>@@ -43,6 +43,12 @@
> #define DEFAULT_POLL_PERIOD_NS (NSEC_PER_SEC / DEFAULT_POLL_FREQUENCY_HZ)
> #define XE_OA_UNIT_INVALID U32_MAX
>
>+enum xe_oam_unit_type {
>+	XE_OAM_UNIT_SAG,
>+	XE_OAM_UNIT_SCMI_0,
>+	XE_OAM_UNIT_SCMI_1,
>+};
>+
> enum xe_oa_submit_deps {
> 	XE_OA_SUBMIT_NO_DEPS,
> 	XE_OA_SUBMIT_ADD_DEPS,
>@@ -1881,6 +1887,7 @@ static bool engine_supports_oa_format(const struct xe_hw_engine *hwe, int type)
> 		return type == DRM_XE_OA_FMT_TYPE_OAG || type == DRM_XE_OA_FMT_TYPE_OAR ||
> 			type == DRM_XE_OA_FMT_TYPE_OAC || type == DRM_XE_OA_FMT_TYPE_PEC;
> 	case DRM_XE_OA_UNIT_TYPE_OAM:
>+	case DRM_XE_OA_UNIT_TYPE_OAM_SAG:
> 		return type == DRM_XE_OA_FMT_TYPE_OAM || type == DRM_XE_OA_FMT_TYPE_OAM_MPEC;
> 	default:
> 		return false;
>@@ -2448,20 +2455,38 @@ int xe_oa_register(struct xe_device *xe)
>
> static u32 num_oa_units_per_gt(struct xe_gt *gt)
> {
>-	return 1;
>+	if (!xe_gt_is_media_type(gt) || GRAPHICS_VER(gt_to_xe(gt)) < 20)
>+		return 1;
>+	else if (!IS_DGFX(gt_to_xe(gt)))
>+		return XE_OAM_UNIT_SCMI_0 + 1; /* SAG + SCMI_0 */
>+	else
>+		return XE_OAM_UNIT_SCMI_1 + 1; /* SAG + SCMI_0 + SCMI_1 */
> }
>
> static u32 __hwe_oam_unit(struct xe_hw_engine *hwe)
> {
>-	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) >= 1270) {
>-		/*
>-		 * There's 1 SAMEDIA gt and 1 OAM per SAMEDIA gt. All media slices
>-		 * within the gt use the same OAM. All MTL/LNL SKUs list 1 SA MEDIA
>-		 */
>-		xe_gt_WARN_ON(hwe->gt, hwe->gt->info.type != XE_GT_TYPE_MEDIA);
>+	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) < 1270)
>+		return XE_OA_UNIT_INVALID;
>
>+	xe_gt_WARN_ON(hwe->gt, !xe_gt_is_media_type(hwe->gt));
>+
>+	if (GRAPHICS_VER(gt_to_xe(hwe->gt)) < 20)
> 		return 0;
>-	}
>+	/*
>+	 * XE_OAM_UNIT_SAG has only GSCCS attached to it, but only on some platforms. Also
>+	 * GSCCS cannot be used to submit batches to program the OAM unit. Therefore we don't
>+	 * assign an OA unit to GSCCS. This means that XE_OAM_UNIT_SAG is exposed as an OA
>+	 * unit without attached engines. Fused off engines can also result in oa_unit's with
>+	 * num_engines == 0. OA streams can be opened on all OA units.
>+	 */
>+	else if (hwe->engine_id == XE_HW_ENGINE_GSCCS0)
>+		return XE_OA_UNIT_INVALID;
>+	else if (!IS_DGFX(gt_to_xe(hwe->gt)))
>+		return XE_OAM_UNIT_SCMI_0;
>+	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_DECODE)
>+		return (hwe->instance / 2 & 0x1) + 1;
>+	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_ENHANCE)
>+		return (hwe->instance & 0x1) + 1;
>
> 	return XE_OA_UNIT_INVALID;
> }
>@@ -2475,6 +2500,7 @@ static u32 __hwe_oa_unit(struct xe_hw_engine *hwe)
>
> 	case XE_ENGINE_CLASS_VIDEO_DECODE:
> 	case XE_ENGINE_CLASS_VIDEO_ENHANCE:
>+	case XE_ENGINE_CLASS_OTHER:
> 		return __hwe_oam_unit(hwe);
>
> 	default:
>@@ -2514,18 +2540,25 @@ static struct xe_oa_regs __oag_regs(void)
>
> static void __xe_oa_init_oa_units(struct xe_gt *gt)
> {
>-	const u32 mtl_oa_base[] = { 0x13000 };
>+	/* Actual address is MEDIA_GT_GSI_OFFSET + oam_base_addr[i] */
>+	const u32 oam_base_addr[] = {
>+		[XE_OAM_UNIT_SAG]    = 0x13000,
>+		[XE_OAM_UNIT_SCMI_0] = 0x14000,
>+		[XE_OAM_UNIT_SCMI_1] = 0x14800,
>+	};
> 	int i, num_units = gt->oa.num_oa_units;
>
> 	for (i = 0; i < num_units; i++) {
> 		struct xe_oa_unit *u = &gt->oa.oa_unit[i];
>
>-		if (gt->info.type != XE_GT_TYPE_MEDIA) {
>+		if (!xe_gt_is_media_type(gt)) {
> 			u->regs = __oag_regs();
> 			u->type = DRM_XE_OA_UNIT_TYPE_OAG;
>-		} else if (GRAPHICS_VERx100(gt_to_xe(gt)) >= 1270) {
>-			u->regs = __oam_regs(mtl_oa_base[i]);
>-			u->type = DRM_XE_OA_UNIT_TYPE_OAM;
>+		} else {
>+			xe_gt_assert(gt, GRAPHICS_VERx100(gt_to_xe(gt)) >= 1270);
>+			u->regs = __oam_regs(oam_base_addr[i]);
>+			u->type = i == XE_OAM_UNIT_SAG && GRAPHICS_VER(gt_to_xe(gt)) >= 20 ?
>+				DRM_XE_OA_UNIT_TYPE_OAM_SAG : DRM_XE_OA_UNIT_TYPE_OAM;
> 		}
>
> 		xe_mmio_write32(&gt->mmio, u->regs.oa_ctrl, 0);
>@@ -2560,10 +2593,6 @@ static int xe_oa_init_gt(struct xe_gt *gt)
> 		}
> 	}
>
>-	/*
>-	 * Fused off engines can result in oa_unit's with num_engines == 0. These units
>-	 * will appear in OA unit query, but no OA streams can be opened on them.
>-	 */
> 	gt->oa.num_oa_units = num_oa_units;
> 	gt->oa.oa_unit = u;
>
>@@ -2579,6 +2608,11 @@ static int xe_oa_init_oa_units(struct xe_oa *oa)
> 	struct xe_gt *gt;
> 	int i, ret;
>
>+	/* Needed for OAM implementation here */
>+	BUILD_BUG_ON(XE_OAM_UNIT_SAG != 0);
>+	BUILD_BUG_ON(XE_OAM_UNIT_SCMI_0 != 1);
>+	BUILD_BUG_ON(XE_OAM_UNIT_SCMI_1 != 2);
>+
> 	for_each_gt(gt, oa->xe, i) {
> 		ret = xe_oa_init_gt(gt);
> 		if (ret)
>diff --git a/include/uapi/drm/xe_drm.h b/include/uapi/drm/xe_drm.h
>index 6a702ba7817c3..5460ba1e4cc37 100644
>--- a/include/uapi/drm/xe_drm.h
>+++ b/include/uapi/drm/xe_drm.h
>@@ -1617,6 +1617,9 @@ enum drm_xe_oa_unit_type {
>
> 	/** @DRM_XE_OA_UNIT_TYPE_OAM: OAM OA unit */
> 	DRM_XE_OA_UNIT_TYPE_OAM,
>+
>+	/** @DRM_XE_OA_UNIT_TYPE_OAM_SAG: OAM_SAG OA unit */
>+	DRM_XE_OA_UNIT_TYPE_OAM_SAG,
> };
>
> /**
>-- 
>2.48.1
>

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units
  2025-06-06 17:37   ` Umesh Nerlige Ramappa
@ 2025-06-06 19:21     ` Dixit, Ashutosh
  2025-06-10 22:57       ` Dixit, Ashutosh
  0 siblings, 1 reply; 24+ messages in thread
From: Dixit, Ashutosh @ 2025-06-06 19:21 UTC (permalink / raw)
  To: Umesh Nerlige Ramappa; +Cc: intel-xe

On Fri, 06 Jun 2025 10:37:53 -0700, Umesh Nerlige Ramappa wrote:
>
> On Fri, Jun 06, 2025 at 09:02:49AM -0700, Ashutosh Dixit wrote:
> > On Xe2+ platforms, media engines are attached to "SCMI" OA media (OAM)
> > units. One or more SCMI OAM units might be present on a platform. In
> > addition there is another OAM unit for global events, called
> > OAM-SAG. Performance metrics for media workloads can be obtained from these
> > OAM units, similar to OAG.
> >
> > Expose these OAM units for userspace to use. OAM-SAG is exposed as an OA
> > unit without any attached engines.
> >
> > Bspec: 70819, 67103, 63844, 72572, 74476, 61284
> >
> > v2: Fix xe_gt_WARN_ON in __hwe_oam_unit for < 12.7 platforms
> > v3: Return XE_OA_UNIT_INVALID for < 12.7 to indicate no OAM units
> > v4: Move xe_oa_print_oa_units() to separate patch
> > v5: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
> >
> > Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
>
> LGTM,
>
> Reviewed-by: Umesh Nerlige Ramappa <umesh.nerlige.ramappa@intel.com>

Thanks Umesh. I also just added a DRM_XE_OA_CAPS_OAM capability also to
this patch. I was debating initially, since userland will see at least 2
OAM units after this series is merged, so that is the way to figure out if
correct OAM support is present in the driver. But then went ahead and added
DRM_XE_OA_CAPS_OAM, since that's how we've been doing things: if you change
uapi, you add a capability. Thanks.

^ permalink raw reply	[flat|nested] 24+ messages in thread

* [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units
  2025-06-06 19:26 [PATCH 0/5] Enable media OA Ashutosh Dixit
@ 2025-06-06 19:26 ` Ashutosh Dixit
  0 siblings, 0 replies; 24+ messages in thread
From: Ashutosh Dixit @ 2025-06-06 19:26 UTC (permalink / raw)
  To: intel-xe

On Xe2+ platforms, media engines are attached to "SCMI" OA media (OAM)
units. One or more SCMI OAM units might be present on a platform. In
addition there is another OAM unit for global events, called
OAM-SAG. Performance metrics for media workloads can be obtained from these
OAM units, similar to OAG.

Expose these OAM units for userspace to use. OAM-SAG is exposed as an OA
unit without any attached engines.

Bspec: 70819, 67103, 63844, 72572, 74476, 61284

v2: Fix xe_gt_WARN_ON in __hwe_oam_unit for < 12.7 platforms
v3: Return XE_OA_UNIT_INVALID for < 12.7 to indicate no OAM units
v4: Move xe_oa_print_oa_units() to separate patch
v5: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
v6: Introduce DRM_XE_OA_CAPS_OAM

Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
Reviewed-by: Umesh Nerlige Ramappa <umesh.nerlige.ramappa@intel.com>
---
 drivers/gpu/drm/xe/xe_oa.c    | 68 ++++++++++++++++++++++++++---------
 drivers/gpu/drm/xe/xe_query.c |  4 +--
 include/uapi/drm/xe_drm.h     |  4 +++
 3 files changed, 57 insertions(+), 19 deletions(-)

diff --git a/drivers/gpu/drm/xe/xe_oa.c b/drivers/gpu/drm/xe/xe_oa.c
index fb842fa0552e5..0de0d5a18df74 100644
--- a/drivers/gpu/drm/xe/xe_oa.c
+++ b/drivers/gpu/drm/xe/xe_oa.c
@@ -43,6 +43,12 @@
 #define DEFAULT_POLL_PERIOD_NS (NSEC_PER_SEC / DEFAULT_POLL_FREQUENCY_HZ)
 #define XE_OA_UNIT_INVALID U32_MAX
 
+enum xe_oam_unit_type {
+	XE_OAM_UNIT_SAG,
+	XE_OAM_UNIT_SCMI_0,
+	XE_OAM_UNIT_SCMI_1,
+};
+
 enum xe_oa_submit_deps {
 	XE_OA_SUBMIT_NO_DEPS,
 	XE_OA_SUBMIT_ADD_DEPS,
@@ -1881,6 +1887,7 @@ static bool engine_supports_oa_format(const struct xe_hw_engine *hwe, int type)
 		return type == DRM_XE_OA_FMT_TYPE_OAG || type == DRM_XE_OA_FMT_TYPE_OAR ||
 			type == DRM_XE_OA_FMT_TYPE_OAC || type == DRM_XE_OA_FMT_TYPE_PEC;
 	case DRM_XE_OA_UNIT_TYPE_OAM:
+	case DRM_XE_OA_UNIT_TYPE_OAM_SAG:
 		return type == DRM_XE_OA_FMT_TYPE_OAM || type == DRM_XE_OA_FMT_TYPE_OAM_MPEC;
 	default:
 		return false;
@@ -2448,20 +2455,38 @@ int xe_oa_register(struct xe_device *xe)
 
 static u32 num_oa_units_per_gt(struct xe_gt *gt)
 {
-	return 1;
+	if (!xe_gt_is_media_type(gt) || GRAPHICS_VER(gt_to_xe(gt)) < 20)
+		return 1;
+	else if (!IS_DGFX(gt_to_xe(gt)))
+		return XE_OAM_UNIT_SCMI_0 + 1; /* SAG + SCMI_0 */
+	else
+		return XE_OAM_UNIT_SCMI_1 + 1; /* SAG + SCMI_0 + SCMI_1 */
 }
 
 static u32 __hwe_oam_unit(struct xe_hw_engine *hwe)
 {
-	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) >= 1270) {
-		/*
-		 * There's 1 SAMEDIA gt and 1 OAM per SAMEDIA gt. All media slices
-		 * within the gt use the same OAM. All MTL/LNL SKUs list 1 SA MEDIA
-		 */
-		xe_gt_WARN_ON(hwe->gt, hwe->gt->info.type != XE_GT_TYPE_MEDIA);
+	if (GRAPHICS_VERx100(gt_to_xe(hwe->gt)) < 1270)
+		return XE_OA_UNIT_INVALID;
 
+	xe_gt_WARN_ON(hwe->gt, !xe_gt_is_media_type(hwe->gt));
+
+	if (GRAPHICS_VER(gt_to_xe(hwe->gt)) < 20)
 		return 0;
-	}
+	/*
+	 * XE_OAM_UNIT_SAG has only GSCCS attached to it, but only on some platforms. Also
+	 * GSCCS cannot be used to submit batches to program the OAM unit. Therefore we don't
+	 * assign an OA unit to GSCCS. This means that XE_OAM_UNIT_SAG is exposed as an OA
+	 * unit without attached engines. Fused off engines can also result in oa_unit's with
+	 * num_engines == 0. OA streams can be opened on all OA units.
+	 */
+	else if (hwe->engine_id == XE_HW_ENGINE_GSCCS0)
+		return XE_OA_UNIT_INVALID;
+	else if (!IS_DGFX(gt_to_xe(hwe->gt)))
+		return XE_OAM_UNIT_SCMI_0;
+	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_DECODE)
+		return (hwe->instance / 2 & 0x1) + 1;
+	else if (hwe->class == XE_ENGINE_CLASS_VIDEO_ENHANCE)
+		return (hwe->instance & 0x1) + 1;
 
 	return XE_OA_UNIT_INVALID;
 }
@@ -2475,6 +2500,7 @@ static u32 __hwe_oa_unit(struct xe_hw_engine *hwe)
 
 	case XE_ENGINE_CLASS_VIDEO_DECODE:
 	case XE_ENGINE_CLASS_VIDEO_ENHANCE:
+	case XE_ENGINE_CLASS_OTHER:
 		return __hwe_oam_unit(hwe);
 
 	default:
@@ -2514,18 +2540,25 @@ static struct xe_oa_regs __oag_regs(void)
 
 static void __xe_oa_init_oa_units(struct xe_gt *gt)
 {
-	const u32 mtl_oa_base[] = { 0x13000 };
+	/* Actual address is MEDIA_GT_GSI_OFFSET + oam_base_addr[i] */
+	const u32 oam_base_addr[] = {
+		[XE_OAM_UNIT_SAG]    = 0x13000,
+		[XE_OAM_UNIT_SCMI_0] = 0x14000,
+		[XE_OAM_UNIT_SCMI_1] = 0x14800,
+	};
 	int i, num_units = gt->oa.num_oa_units;
 
 	for (i = 0; i < num_units; i++) {
 		struct xe_oa_unit *u = &gt->oa.oa_unit[i];
 
-		if (gt->info.type != XE_GT_TYPE_MEDIA) {
+		if (!xe_gt_is_media_type(gt)) {
 			u->regs = __oag_regs();
 			u->type = DRM_XE_OA_UNIT_TYPE_OAG;
-		} else if (GRAPHICS_VERx100(gt_to_xe(gt)) >= 1270) {
-			u->regs = __oam_regs(mtl_oa_base[i]);
-			u->type = DRM_XE_OA_UNIT_TYPE_OAM;
+		} else {
+			xe_gt_assert(gt, GRAPHICS_VERx100(gt_to_xe(gt)) >= 1270);
+			u->regs = __oam_regs(oam_base_addr[i]);
+			u->type = i == XE_OAM_UNIT_SAG && GRAPHICS_VER(gt_to_xe(gt)) >= 20 ?
+				DRM_XE_OA_UNIT_TYPE_OAM_SAG : DRM_XE_OA_UNIT_TYPE_OAM;
 		}
 
 		xe_mmio_write32(&gt->mmio, u->regs.oa_ctrl, 0);
@@ -2560,10 +2593,6 @@ static int xe_oa_init_gt(struct xe_gt *gt)
 		}
 	}
 
-	/*
-	 * Fused off engines can result in oa_unit's with num_engines == 0. These units
-	 * will appear in OA unit query, but no OA streams can be opened on them.
-	 */
 	gt->oa.num_oa_units = num_oa_units;
 	gt->oa.oa_unit = u;
 
@@ -2579,6 +2608,11 @@ static int xe_oa_init_oa_units(struct xe_oa *oa)
 	struct xe_gt *gt;
 	int i, ret;
 
+	/* Needed for OAM implementation here */
+	BUILD_BUG_ON(XE_OAM_UNIT_SAG != 0);
+	BUILD_BUG_ON(XE_OAM_UNIT_SCMI_0 != 1);
+	BUILD_BUG_ON(XE_OAM_UNIT_SCMI_1 != 2);
+
 	for_each_gt(gt, oa->xe, i) {
 		ret = xe_oa_init_gt(gt);
 		if (ret)
diff --git a/drivers/gpu/drm/xe/xe_query.c b/drivers/gpu/drm/xe/xe_query.c
index 2dbf4066d86ff..e8e1743dcb1e0 100644
--- a/drivers/gpu/drm/xe/xe_query.c
+++ b/drivers/gpu/drm/xe/xe_query.c
@@ -683,8 +683,8 @@ static int query_oa_units(struct xe_device *xe,
 			du->oa_timestamp_freq = xe_oa_timestamp_frequency(gt);
 			du->capabilities = DRM_XE_OA_CAPS_BASE | DRM_XE_OA_CAPS_SYNCS |
 					   DRM_XE_OA_CAPS_OA_BUFFER_SIZE |
-					   DRM_XE_OA_CAPS_WAIT_NUM_REPORTS;
-
+					   DRM_XE_OA_CAPS_WAIT_NUM_REPORTS |
+					   DRM_XE_OA_CAPS_OAM;
 			j = 0;
 			for_each_hw_engine(hwe, gt, hwe_id) {
 				if (!xe_hw_engine_is_reserved(hwe) &&
diff --git a/include/uapi/drm/xe_drm.h b/include/uapi/drm/xe_drm.h
index 6a702ba7817c3..8e8bbdec8c5ca 100644
--- a/include/uapi/drm/xe_drm.h
+++ b/include/uapi/drm/xe_drm.h
@@ -1617,6 +1617,9 @@ enum drm_xe_oa_unit_type {
 
 	/** @DRM_XE_OA_UNIT_TYPE_OAM: OAM OA unit */
 	DRM_XE_OA_UNIT_TYPE_OAM,
+
+	/** @DRM_XE_OA_UNIT_TYPE_OAM_SAG: OAM_SAG OA unit */
+	DRM_XE_OA_UNIT_TYPE_OAM_SAG,
 };
 
 /**
@@ -1638,6 +1641,7 @@ struct drm_xe_oa_unit {
 #define DRM_XE_OA_CAPS_SYNCS		(1 << 1)
 #define DRM_XE_OA_CAPS_OA_BUFFER_SIZE	(1 << 2)
 #define DRM_XE_OA_CAPS_WAIT_NUM_REPORTS	(1 << 3)
+#define DRM_XE_OA_CAPS_OAM		(1 << 4)
 
 	/** @oa_timestamp_freq: OA timestamp freq */
 	__u64 oa_timestamp_freq;
-- 
2.48.1


^ permalink raw reply related	[flat|nested] 24+ messages in thread

* Re: [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units
  2025-06-06 19:21     ` Dixit, Ashutosh
@ 2025-06-10 22:57       ` Dixit, Ashutosh
  2025-06-16 22:26         ` Dixit, Ashutosh
  0 siblings, 1 reply; 24+ messages in thread
From: Dixit, Ashutosh @ 2025-06-10 22:57 UTC (permalink / raw)
  To: intel-xe

On Fri, 06 Jun 2025 12:21:11 -0700, Dixit, Ashutosh wrote:
>
> On Fri, 06 Jun 2025 10:37:53 -0700, Umesh Nerlige Ramappa wrote:
> >
> > On Fri, Jun 06, 2025 at 09:02:49AM -0700, Ashutosh Dixit wrote:
> > > On Xe2+ platforms, media engines are attached to "SCMI" OA media (OAM)
> > > units. One or more SCMI OAM units might be present on a platform. In
> > > addition there is another OAM unit for global events, called
> > > OAM-SAG. Performance metrics for media workloads can be obtained from these
> > > OAM units, similar to OAG.
> > >
> > > Expose these OAM units for userspace to use. OAM-SAG is exposed as an OA
> > > unit without any attached engines.
> > >
> > > Bspec: 70819, 67103, 63844, 72572, 74476, 61284
> > >
> > > v2: Fix xe_gt_WARN_ON in __hwe_oam_unit for < 12.7 platforms
> > > v3: Return XE_OA_UNIT_INVALID for < 12.7 to indicate no OAM units
> > > v4: Move xe_oa_print_oa_units() to separate patch
> > > v5: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
> > >
> > > Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
> >
> > LGTM,
> >
> > Reviewed-by: Umesh Nerlige Ramappa <umesh.nerlige.ramappa@intel.com>
>
> Thanks Umesh. I also just added a DRM_XE_OA_CAPS_OAM capability also to
> this patch. I was debating initially, since userland will see at least 2
> OAM units after this series is merged, so that is the way to figure out if
> correct OAM support is present in the driver. But then went ahead and added
> DRM_XE_OA_CAPS_OAM, since that's how we've been doing things: if you change
> uapi, you add a capability. Thanks.

MDAPI PR which consumes uapi changes in this patch:

https://github.com/intel/metrics-discovery/pull/35

^ permalink raw reply	[flat|nested] 24+ messages in thread

* Re: [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units
  2025-06-10 22:57       ` Dixit, Ashutosh
@ 2025-06-16 22:26         ` Dixit, Ashutosh
  0 siblings, 0 replies; 24+ messages in thread
From: Dixit, Ashutosh @ 2025-06-16 22:26 UTC (permalink / raw)
  To: intel-xe; +Cc: Umesh Nerlige Ramappa

On Tue, 10 Jun 2025 15:57:37 -0700, Dixit, Ashutosh wrote:
>
> On Fri, 06 Jun 2025 12:21:11 -0700, Dixit, Ashutosh wrote:
> >
> > On Fri, 06 Jun 2025 10:37:53 -0700, Umesh Nerlige Ramappa wrote:
> > >
> > > On Fri, Jun 06, 2025 at 09:02:49AM -0700, Ashutosh Dixit wrote:
> > > > On Xe2+ platforms, media engines are attached to "SCMI" OA media (OAM)
> > > > units. One or more SCMI OAM units might be present on a platform. In
> > > > addition there is another OAM unit for global events, called
> > > > OAM-SAG. Performance metrics for media workloads can be obtained from these
> > > > OAM units, similar to OAG.
> > > >
> > > > Expose these OAM units for userspace to use. OAM-SAG is exposed as an OA
> > > > unit without any attached engines.
> > > >
> > > > Bspec: 70819, 67103, 63844, 72572, 74476, 61284
> > > >
> > > > v2: Fix xe_gt_WARN_ON in __hwe_oam_unit for < 12.7 platforms
> > > > v3: Return XE_OA_UNIT_INVALID for < 12.7 to indicate no OAM units
> > > > v4: Move xe_oa_print_oa_units() to separate patch
> > > > v5: Introduce DRM_XE_OA_UNIT_TYPE_OAM_SAG
> > > >
> > > > Signed-off-by: Ashutosh Dixit <ashutosh.dixit@intel.com>
> > >
> > > LGTM,
> > >
> > > Reviewed-by: Umesh Nerlige Ramappa <umesh.nerlige.ramappa@intel.com>
> >
> > Thanks Umesh. I also just added a DRM_XE_OA_CAPS_OAM capability also to
> > this patch. I was debating initially, since userland will see at least 2
> > OAM units after this series is merged, so that is the way to figure out if
> > correct OAM support is present in the driver. But then went ahead and added
> > DRM_XE_OA_CAPS_OAM, since that's how we've been doing things: if you change
> > uapi, you add a capability. Thanks.
>
> MDAPI PR which consumes uapi changes in this patch:
>
> https://github.com/intel/metrics-discovery/pull/35

More user space updates for this series:

- IGT xe perf tools update:

  https://patchwork.freedesktop.org/series/150274/

- gpuvis PR:

  https://github.com/mikesart/gpuvis/pull/100/

^ permalink raw reply	[flat|nested] 24+ messages in thread

end of thread, other threads:[~2025-06-16 22:26 UTC | newest]

Thread overview: 24+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-06-03 20:21 [PATCH v3 0/5] Enable media OA Ashutosh Dixit
2025-06-03 20:21 ` [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units Ashutosh Dixit
2025-06-04 23:42   ` Umesh Nerlige Ramappa
2025-06-05 18:28     ` Dixit, Ashutosh
2025-06-06 16:42       ` Dixit, Ashutosh
2025-06-03 20:21 ` [PATCH 2/5] drm/xe/oa: Print hwe to OA unit mapping Ashutosh Dixit
2025-06-04 23:49   ` Umesh Nerlige Ramappa
2025-06-06 16:05     ` Dixit, Ashutosh
2025-06-03 20:21 ` [PATCH 3/5] drm/xe/oa: Introduce stream->oa_unit Ashutosh Dixit
2025-06-04 23:54   ` Umesh Nerlige Ramappa
2025-06-03 20:21 ` [PATCH 4/5] drm/xe/oa: Assign hwe for OAM_SAG Ashutosh Dixit
2025-06-05  0:14   ` Umesh Nerlige Ramappa
2025-06-06 16:07     ` Dixit, Ashutosh
2025-06-03 20:21 ` [PATCH 5/5] drm/xe/oa: Enable OAM latency measurement Ashutosh Dixit
2025-06-05 16:25   ` Umesh Nerlige Ramappa
2025-06-03 20:26 ` ✓ CI.Patch_applied: success for Enable media OA Patchwork
2025-06-03 20:26 ` ✓ CI.checkpatch: " Patchwork
2025-06-03 20:27 ` ✗ CI.KUnit: failure " Patchwork
  -- strict thread matches above, loose matches on Subject: below --
2025-06-06 16:02 [PATCH v4 0/5] " Ashutosh Dixit
2025-06-06 16:02 ` [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units Ashutosh Dixit
2025-06-06 17:37   ` Umesh Nerlige Ramappa
2025-06-06 19:21     ` Dixit, Ashutosh
2025-06-10 22:57       ` Dixit, Ashutosh
2025-06-16 22:26         ` Dixit, Ashutosh
2025-06-06 19:26 [PATCH 0/5] Enable media OA Ashutosh Dixit
2025-06-06 19:26 ` [PATCH 1/5] drm/xe/oa/uapi: Expose media OA units Ashutosh Dixit

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).