drm/i915/guc/slpc: Add get max/min freq hooks
authorVinay Belgaumkar <vinay.belgaumkar@intel.com>
Fri, 30 Jul 2021 20:21:13 +0000 (13:21 -0700)
committerJohn Harrison <John.C.Harrison@Intel.com>
Tue, 3 Aug 2021 23:05:34 +0000 (16:05 -0700)
Add helpers to read the min/max frequency being used
by SLPC. This is done by send a H2G command which forces
SLPC to update the shared data struct which can then be
read. These helpers will be used in a sysfs patch later
on.

v2: Address review comments (Michal W)
v3: Return err in case of query failure (Michal W)
v4: Move decode_min/max_freq to this patch

Reviewed-by: Michal Wajdeczko <michal.wajdeczko@intel.com>
Signed-off-by: Vinay Belgaumkar <vinay.belgaumkar@intel.com>
Signed-off-by: Sundaresan Sujaritha <sujaritha.sundaresan@intel.com>
Signed-off-by: John Harrison <John.C.Harrison@Intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20210730202119.23810-9-vinay.belgaumkar@intel.com
drivers/gpu/drm/i915/gt/uc/intel_guc_slpc.c
drivers/gpu/drm/i915/gt/uc/intel_guc_slpc.h

index 2635feb..8bfd188 100644 (file)
@@ -245,6 +245,28 @@ static int slpc_reset(struct intel_guc_slpc *slpc)
        return 0;
 }
 
+static u32 slpc_decode_min_freq(struct intel_guc_slpc *slpc)
+{
+       struct slpc_shared_data *data = slpc->vaddr;
+
+       GEM_BUG_ON(!slpc->vma);
+
+       return  DIV_ROUND_CLOSEST(REG_FIELD_GET(SLPC_MIN_UNSLICE_FREQ_MASK,
+                                 data->task_state_data.freq) *
+                                 GT_FREQUENCY_MULTIPLIER, GEN9_FREQ_SCALER);
+}
+
+static u32 slpc_decode_max_freq(struct intel_guc_slpc *slpc)
+{
+       struct slpc_shared_data *data = slpc->vaddr;
+
+       GEM_BUG_ON(!slpc->vma);
+
+       return  DIV_ROUND_CLOSEST(REG_FIELD_GET(SLPC_MAX_UNSLICE_FREQ_MASK,
+                                 data->task_state_data.freq) *
+                                 GT_FREQUENCY_MULTIPLIER, GEN9_FREQ_SCALER);
+}
+
 static void slpc_shared_data_reset(struct slpc_shared_data *data)
 {
        memset(data, 0, sizeof(struct slpc_shared_data));
@@ -292,6 +314,33 @@ int intel_guc_slpc_set_max_freq(struct intel_guc_slpc *slpc, u32 val)
 }
 
 /**
+ * intel_guc_slpc_get_max_freq() - Get max frequency limit for SLPC.
+ * @slpc: pointer to intel_guc_slpc.
+ * @val: pointer to val which will hold max frequency (MHz)
+ *
+ * This function will invoke GuC SLPC action to read the max frequency
+ * limit for unslice.
+ *
+ * Return: 0 on success, non-zero error code on failure.
+ */
+int intel_guc_slpc_get_max_freq(struct intel_guc_slpc *slpc, u32 *val)
+{
+       struct drm_i915_private *i915 = slpc_to_i915(slpc);
+       intel_wakeref_t wakeref;
+       int ret = 0;
+
+       with_intel_runtime_pm(&i915->runtime_pm, wakeref) {
+               /* Force GuC to update task data */
+               ret = slpc_query_task_state(slpc);
+
+               if (!ret)
+                       *val = slpc_decode_max_freq(slpc);
+       }
+
+       return ret;
+}
+
+/**
  * intel_guc_slpc_set_min_freq() - Set min frequency limit for SLPC.
  * @slpc: pointer to intel_guc_slpc.
  * @val: frequency (MHz)
@@ -320,6 +369,33 @@ int intel_guc_slpc_set_min_freq(struct intel_guc_slpc *slpc, u32 val)
        return ret;
 }
 
+/**
+ * intel_guc_slpc_get_min_freq() - Get min frequency limit for SLPC.
+ * @slpc: pointer to intel_guc_slpc.
+ * @val: pointer to val which will hold min frequency (MHz)
+ *
+ * This function will invoke GuC SLPC action to read the min frequency
+ * limit for unslice.
+ *
+ * Return: 0 on success, non-zero error code on failure.
+ */
+int intel_guc_slpc_get_min_freq(struct intel_guc_slpc *slpc, u32 *val)
+{
+       struct drm_i915_private *i915 = slpc_to_i915(slpc);
+       intel_wakeref_t wakeref;
+       int ret = 0;
+
+       with_intel_runtime_pm(&i915->runtime_pm, wakeref) {
+               /* Force GuC to update task data */
+               ret = slpc_query_task_state(slpc);
+
+               if (!ret)
+                       *val = slpc_decode_min_freq(slpc);
+       }
+
+       return ret;
+}
+
 /*
  * intel_guc_slpc_enable() - Start SLPC
  * @slpc: pointer to intel_guc_slpc.
index 788d87f..78a7893 100644 (file)
@@ -31,5 +31,7 @@ int intel_guc_slpc_enable(struct intel_guc_slpc *slpc);
 void intel_guc_slpc_fini(struct intel_guc_slpc *slpc);
 int intel_guc_slpc_set_max_freq(struct intel_guc_slpc *slpc, u32 val);
 int intel_guc_slpc_set_min_freq(struct intel_guc_slpc *slpc, u32 val);
+int intel_guc_slpc_get_max_freq(struct intel_guc_slpc *slpc, u32 *val);
+int intel_guc_slpc_get_min_freq(struct intel_guc_slpc *slpc, u32 *val);
 
 #endif