logical_sort() looks up the engine for each logical instance i by
scanning all MAX_ENGINE_INSTANCE + 1 slots of the engines array, even
though its only caller initializes just num_engines entries, so the
scan can dereference uninitialized stack pointers. In addition, the
final memcpy() passes *engines and *sorted instead of the arrays
themselves, so it copies engine structure data rather than the pointer
arrays.
Replace the implementation with a plain sort() of the initialized part
of the array, keyed by the logical mask. This touches only initialized
entries, does not copy anything by hand, and does not rely on the
logical numbering being contiguous.
Fixes: f9d72092cb49 ("drm/i915/guc: Add basic GuC multi-lrc selftest")
Signed-off-by: Linmao Li <[email protected]>
---
.../drm/i915/gt/uc/selftest_guc_multi_lrc.c | 28 ++++++++++---------
1 file changed, 15 insertions(+), 13 deletions(-)
diff --git a/drivers/gpu/drm/i915/gt/uc/selftest_guc_multi_lrc.c
b/drivers/gpu/drm/i915/gt/uc/selftest_guc_multi_lrc.c
index 28e8a092f4e7..b56768d202b0 100644
--- a/drivers/gpu/drm/i915/gt/uc/selftest_guc_multi_lrc.c
+++ b/drivers/gpu/drm/i915/gt/uc/selftest_guc_multi_lrc.c
@@ -3,6 +3,8 @@
* Copyright © 2019 Intel Corporation
*/
+#include <linux/sort.h>
+
#include "gt/intel_gt_print.h"
#include "selftests/igt_spinner.h"
#include "selftests/igt_reset.h"
@@ -10,21 +12,21 @@
#include "gt/intel_engine_heartbeat.h"
#include "gem/selftests/mock_context.h"
+static int cmp_logical_instance(const void *a, const void *b)
+{
+ const struct intel_engine_cs *ea = *(const struct intel_engine_cs **)a;
+ const struct intel_engine_cs *eb = *(const struct intel_engine_cs **)b;
+
+ if (ea->logical_mask < eb->logical_mask)
+ return -1;
+ if (ea->logical_mask > eb->logical_mask)
+ return 1;
+ return 0;
+}
+
static void logical_sort(struct intel_engine_cs **engines, int num_engines)
{
- struct intel_engine_cs *sorted[MAX_ENGINE_INSTANCE + 1];
- int i, j;
-
- for (i = 0; i < num_engines; ++i)
- for (j = 0; j < MAX_ENGINE_INSTANCE + 1; ++j) {
- if (engines[j]->logical_mask & BIT(i)) {
- sorted[i] = engines[j];
- break;
- }
- }
-
- memcpy(*engines, *sorted,
- sizeof(struct intel_engine_cs *) * num_engines);
+ sort(engines, num_engines, sizeof(*engines), cmp_logical_instance,
NULL);
}
static struct intel_context *
--
2.25.1