1 // SPDX-License-Identifier: MIT
2 /*
3  * Copyright © 2021 Intel Corporation
4  */
5 
6 #include <linux/string_helpers.h>
7 
8 #include "intel_guc_rc.h"
9 #include "intel_guc_print.h"
10 #include "gt/intel_gt.h"
11 #include "i915_drv.h"
12 
__guc_rc_supported(struct intel_guc * guc)13 static bool __guc_rc_supported(struct intel_guc *guc)
14 {
15 	/* GuC RC is unavailable for pre-Gen12 */
16 	return guc->submission_supported &&
17 		GRAPHICS_VER(guc_to_i915(guc)) >= 12;
18 }
19 
__guc_rc_selected(struct intel_guc * guc)20 static bool __guc_rc_selected(struct intel_guc *guc)
21 {
22 	if (!intel_guc_rc_is_supported(guc))
23 		return false;
24 
25 	return guc->submission_selected;
26 }
27 
intel_guc_rc_init_early(struct intel_guc * guc)28 void intel_guc_rc_init_early(struct intel_guc *guc)
29 {
30 	guc->rc_supported = __guc_rc_supported(guc);
31 	guc->rc_selected = __guc_rc_selected(guc);
32 }
33 
guc_action_control_gucrc(struct intel_guc * guc,bool enable)34 static int guc_action_control_gucrc(struct intel_guc *guc, bool enable)
35 {
36 	u32 rc_mode = enable ? INTEL_GUCRC_FIRMWARE_CONTROL :
37 				INTEL_GUCRC_HOST_CONTROL;
38 	u32 action[] = {
39 		INTEL_GUC_ACTION_SETUP_PC_GUCRC,
40 		rc_mode
41 	};
42 	int ret;
43 
44 	ret = intel_guc_send(guc, action, ARRAY_SIZE(action));
45 	ret = ret > 0 ? -EPROTO : ret;
46 
47 	return ret;
48 }
49 
__guc_rc_control(struct intel_guc * guc,bool enable)50 static int __guc_rc_control(struct intel_guc *guc, bool enable)
51 {
52 	struct intel_gt *gt = guc_to_gt(guc);
53 	int ret;
54 
55 	if (!intel_uc_uses_guc_rc(&gt->uc))
56 		return -EOPNOTSUPP;
57 
58 	if (!intel_guc_is_ready(guc))
59 		return -EINVAL;
60 
61 	ret = guc_action_control_gucrc(guc, enable);
62 	if (ret) {
63 		guc_probe_error(guc, "Failed to %s RC (%pe)\n",
64 				str_enable_disable(enable), ERR_PTR(ret));
65 		return ret;
66 	}
67 
68 	guc_info(guc, "RC %s\n", str_enabled_disabled(enable));
69 
70 	return 0;
71 }
72 
intel_guc_rc_enable(struct intel_guc * guc)73 int intel_guc_rc_enable(struct intel_guc *guc)
74 {
75 	return __guc_rc_control(guc, true);
76 }
77 
intel_guc_rc_disable(struct intel_guc * guc)78 int intel_guc_rc_disable(struct intel_guc *guc)
79 {
80 	return __guc_rc_control(guc, false);
81 }
82