]> www.infradead.org Git - users/hch/misc.git/commitdiff
drm/xe/vf: Enable CCS save/restore only on supported GUC versions
authorSatyanarayana K V P <satyanarayana.k.v.p@intel.com>
Tue, 2 Sep 2025 10:32:57 +0000 (16:02 +0530)
committerMichal Wajdeczko <michal.wajdeczko@intel.com>
Tue, 2 Sep 2025 16:59:17 +0000 (18:59 +0200)
CCS save/restore is supported starting with GuC 70.48.0 (compatibility
version 1.23.0). Gate the feature on the GuC firmware version and keep it
disabled on older or unsupported versions.

Fixes: f3009272ff2e ("drm/xe/vf: Create contexts for CCS read write")
Signed-off-by: Satyanarayana K V P <satyanarayana.k.v.p@intel.com>
Cc: Michal Wajdeczko <michal.wajdeczko@intel.com>
Cc: Daniele Ceraolo Spurio <daniele.ceraolospurio@intel.com>
Cc: Andi Shyti <andi.shyti@kernel.org>
Reviewed-by: Michal Wajdeczko <michal.wajdeczko@intel.com>
Signed-off-by: Michal Wajdeczko <michal.wajdeczko@intel.com>
Link: https://lore.kernel.org/r/20250902103256.21658-2-satyanarayana.k.v.p@intel.com
drivers/gpu/drm/xe/xe_device.c
drivers/gpu/drm/xe/xe_sriov.c
drivers/gpu/drm/xe/xe_sriov.h
drivers/gpu/drm/xe/xe_sriov_vf.c
drivers/gpu/drm/xe/xe_sriov_vf.h
drivers/gpu/drm/xe/xe_sriov_vf_ccs.c
drivers/gpu/drm/xe/xe_sriov_vf_types.h

index 9e4773a17ef8d0f7cf4366b27807cdae78c2d59c..9e2952c9c06a8bb3b8914e96c3bbbadc7e6618d3 100644 (file)
@@ -950,7 +950,7 @@ int xe_device_probe(struct xe_device *xe)
 
        xe_vsec_init(xe);
 
-       err = xe_sriov_late_init(xe);
+       err = xe_sriov_init_late(xe);
        if (err)
                goto err_unregister_display;
 
index 87911fb4eea7a2e34487cd0341cd6f4c971bdddc..7d2d6de2aabfeea3dee99829dac6e5e264fe1037 100644 (file)
@@ -160,19 +160,15 @@ const char *xe_sriov_function_name(unsigned int n, char *buf, size_t size)
 }
 
 /**
- * xe_sriov_late_init() - SR-IOV late initialization functions.
+ * xe_sriov_init_late() - SR-IOV late initialization functions.
  * @xe: the &xe_device to initialize
  *
- * On VF this function will initialize code for CCS migration.
- *
  * Return: 0 on success or a negative error code on failure.
  */
-int xe_sriov_late_init(struct xe_device *xe)
+int xe_sriov_init_late(struct xe_device *xe)
 {
-       int err = 0;
-
-       if (IS_VF_CCS_INIT_NEEDED(xe))
-               err = xe_sriov_vf_ccs_init(xe);
+       if (IS_SRIOV_VF(xe))
+               return xe_sriov_vf_init_late(xe);
 
-       return err;
+       return 0;
 }
index 0e0c1abf2d14ff19e3ec9feb90ffde0a69b3dcd1..6db45df556158ad76404e03ec0119188b93e0d4b 100644 (file)
@@ -18,7 +18,7 @@ const char *xe_sriov_function_name(unsigned int n, char *buf, size_t len);
 void xe_sriov_probe_early(struct xe_device *xe);
 void xe_sriov_print_info(struct xe_device *xe, struct drm_printer *p);
 int xe_sriov_init(struct xe_device *xe);
-int xe_sriov_late_init(struct xe_device *xe);
+int xe_sriov_init_late(struct xe_device *xe);
 
 static inline enum xe_sriov_mode xe_device_sriov_mode(const struct xe_device *xe)
 {
index 5de81f213d83e3735dae89e1e84bbc949748444a..cb062328551aa2c4131a2f58869ab3c38e4e80cf 100644 (file)
@@ -10,6 +10,7 @@
 #include "xe_gt.h"
 #include "xe_gt_sriov_printk.h"
 #include "xe_gt_sriov_vf.h"
+#include "xe_guc.h"
 #include "xe_guc_ct.h"
 #include "xe_guc_submit.h"
 #include "xe_irq.h"
@@ -18,6 +19,7 @@
 #include "xe_sriov.h"
 #include "xe_sriov_printk.h"
 #include "xe_sriov_vf.h"
+#include "xe_sriov_vf_ccs.h"
 #include "xe_tile_sriov_vf.h"
 
 /**
  *      |                               |                               |
  */
 
-static bool vf_migration_supported(struct xe_device *xe)
+/**
+ * xe_sriov_vf_migration_supported - Report whether SR-IOV VF migration is
+ * supported or not.
+ * @xe: the &xe_device to check
+ *
+ * Returns: true if VF migration is supported, false otherwise.
+ */
+bool xe_sriov_vf_migration_supported(struct xe_device *xe)
+{
+       xe_assert(xe, IS_SRIOV_VF(xe));
+       return xe->sriov.vf.migration.enabled;
+}
+
+static void vf_disable_migration(struct xe_device *xe, const char *fmt, ...)
+{
+       struct va_format vaf;
+       va_list va_args;
+
+       xe_assert(xe, IS_SRIOV_VF(xe));
+
+       va_start(va_args, fmt);
+       vaf.fmt = fmt;
+       vaf.va  = &va_args;
+       xe_sriov_notice(xe, "migration disabled: %pV\n", &vaf);
+       va_end(va_args);
+
+       xe->sriov.vf.migration.enabled = false;
+}
+
+static void migration_worker_func(struct work_struct *w);
+
+static void vf_migration_init_early(struct xe_device *xe)
 {
        /*
         * TODO: Add conditions to allow specific platforms, when they're
         * supported at production quality.
         */
-       return IS_ENABLED(CONFIG_DRM_XE_DEBUG);
-}
+       if (!IS_ENABLED(CONFIG_DRM_XE_DEBUG))
+               return vf_disable_migration(xe,
+                                           "experimental feature not available on production builds");
+
+       if (GRAPHICS_VER(xe) < 20)
+               return vf_disable_migration(xe, "requires gfx version >= 20, but only %u found",
+                                           GRAPHICS_VER(xe));
+
+       if (!IS_DGFX(xe)) {
+               struct xe_uc_fw_version guc_version;
+
+               xe_gt_sriov_vf_guc_versions(xe_device_get_gt(xe, 0), NULL, &guc_version);
+               if (MAKE_GUC_VER_STRUCT(guc_version) < MAKE_GUC_VER(1, 23, 0))
+                       return vf_disable_migration(xe,
+                                                   "CCS migration requires GuC ABI >= 1.23 but only %u.%u found",
+                                                   guc_version.major, guc_version.minor);
+       }
 
-static void migration_worker_func(struct work_struct *w);
+       INIT_WORK(&xe->sriov.vf.migration.worker, migration_worker_func);
+
+       xe->sriov.vf.migration.enabled = true;
+       xe_sriov_dbg(xe, "migration support enabled\n");
+}
 
 /**
  * xe_sriov_vf_init_early - Initialize SR-IOV VF specific data.
@@ -144,10 +196,7 @@ static void migration_worker_func(struct work_struct *w);
  */
 void xe_sriov_vf_init_early(struct xe_device *xe)
 {
-       INIT_WORK(&xe->sriov.vf.migration.worker, migration_worker_func);
-
-       if (!vf_migration_supported(xe))
-               xe_sriov_info(xe, "migration not supported by this module version\n");
+       vf_migration_init_early(xe);
 }
 
 /**
@@ -302,8 +351,8 @@ static void vf_post_migration_recovery(struct xe_device *xe)
        xe_pm_runtime_get(xe);
        vf_post_migration_shutdown(xe);
 
-       if (!vf_migration_supported(xe)) {
-               xe_sriov_err(xe, "migration not supported by this module version\n");
+       if (!xe_sriov_vf_migration_supported(xe)) {
+               xe_sriov_err(xe, "migration is not supported\n");
                err = -ENOTRECOVERABLE;
                goto fail;
        }
@@ -378,3 +427,21 @@ void xe_sriov_vf_start_migration_recovery(struct xe_device *xe)
        drm_info(&xe->drm, "VF migration recovery %s\n", started ?
                 "scheduled" : "already in progress");
 }
+
+/**
+ * xe_sriov_vf_init_late() - SR-IOV VF late initialization functions.
+ * @xe: the &xe_device to initialize
+ *
+ * This function initializes code for CCS migration.
+ *
+ * Return: 0 on success or a negative error code on failure.
+ */
+int xe_sriov_vf_init_late(struct xe_device *xe)
+{
+       int err = 0;
+
+       if (xe_sriov_vf_migration_supported(xe))
+               err = xe_sriov_vf_ccs_init(xe);
+
+       return err;
+}
index 7b8622cff2b79d5782fcc8684a7259373fbf3087..3bf3364799ad609d279e06b81c6966c5fd6f62fd 100644 (file)
@@ -6,9 +6,13 @@
 #ifndef _XE_SRIOV_VF_H_
 #define _XE_SRIOV_VF_H_
 
+#include <linux/types.h>
+
 struct xe_device;
 
 void xe_sriov_vf_init_early(struct xe_device *xe);
+int xe_sriov_vf_init_late(struct xe_device *xe);
 void xe_sriov_vf_start_migration_recovery(struct xe_device *xe);
+bool xe_sriov_vf_migration_supported(struct xe_device *xe);
 
 #endif
index 4872e43eb440c92262ea54a97c52d65e81e1f96f..908590fa79d4a4fda2544cea278b4ef19ad86296 100644 (file)
@@ -264,9 +264,8 @@ int xe_sriov_vf_ccs_init(struct xe_device *xe)
        u32 flags;
        int err;
 
-       xe_assert(xe, IS_SRIOV_VF(xe));
-       xe_assert(xe, !IS_DGFX(xe));
-       xe_assert(xe, xe_device_has_flat_ccs(xe));
+       if (!IS_VF_CCS_INIT_NEEDED(xe))
+               return 0;
 
        for_each_ccs_rw_ctx(ctx_id) {
                ctx = &tile->sriov.vf.ccs[ctx_id];
index 24a873c50c49bbbb4a260688fd4105bbc9ad4ea3..2c94d1f92187fa37e6cebd17111a8549da76b7e7 100644 (file)
@@ -35,6 +35,11 @@ struct xe_device_vf {
                struct work_struct worker;
                /** @migration.gt_flags: Per-GT request flags for VF migration recovery */
                unsigned long gt_flags;
+               /**
+                * @migration.enabled: flag indicating if migration support
+                * was enabled or not due to missing prerequisites
+                */
+               bool enabled;
        } migration;
 
        /** @ccs: VF CCS state data */