1 // SPDX-License-Identifier: MIT
2 /*
3 * Copyright © 2021 Intel Corporation
4 */
5
6 #define NUM_STEPS 5
7 #define H2G_DELAY 50000
8 #define delay_for_h2g() usleep_range(H2G_DELAY, H2G_DELAY + 10000)
9 #define FREQUENCY_REQ_UNIT DIV_ROUND_CLOSEST(GT_FREQUENCY_MULTIPLIER, \
10 GEN9_FREQ_SCALER)
11 enum test_type {
12 VARY_MIN,
13 VARY_MAX,
14 MAX_GRANTED,
15 SLPC_POWER,
16 TILE_INTERACTION,
17 };
18
19 struct slpc_thread {
20 struct kthread_worker *worker;
21 struct kthread_work work;
22 struct intel_gt *gt;
23 int result;
24 };
25
slpc_set_min_freq(struct intel_guc_slpc * slpc,u32 freq)26 static int slpc_set_min_freq(struct intel_guc_slpc *slpc, u32 freq)
27 {
28 int ret;
29
30 ret = intel_guc_slpc_set_min_freq(slpc, freq);
31 if (ret)
32 pr_err("Could not set min frequency to [%u]\n", freq);
33 else /* Delay to ensure h2g completes */
34 delay_for_h2g();
35
36 return ret;
37 }
38
slpc_set_max_freq(struct intel_guc_slpc * slpc,u32 freq)39 static int slpc_set_max_freq(struct intel_guc_slpc *slpc, u32 freq)
40 {
41 int ret;
42
43 ret = intel_guc_slpc_set_max_freq(slpc, freq);
44 if (ret)
45 pr_err("Could not set maximum frequency [%u]\n",
46 freq);
47 else /* Delay to ensure h2g completes */
48 delay_for_h2g();
49
50 return ret;
51 }
52
slpc_set_freq(struct intel_gt * gt,u32 freq)53 static int slpc_set_freq(struct intel_gt *gt, u32 freq)
54 {
55 int err;
56 struct intel_guc_slpc *slpc = >_to_guc(gt)->slpc;
57
58 err = slpc_set_max_freq(slpc, freq);
59 if (err) {
60 pr_err("Unable to update max freq");
61 return err;
62 }
63
64 err = slpc_set_min_freq(slpc, freq);
65 if (err) {
66 pr_err("Unable to update min freq");
67 return err;
68 }
69
70 return err;
71 }
72
slpc_restore_freq(struct intel_guc_slpc * slpc,u32 min,u32 max)73 static int slpc_restore_freq(struct intel_guc_slpc *slpc, u32 min, u32 max)
74 {
75 int err;
76
77 err = slpc_set_max_freq(slpc, max);
78 if (err) {
79 pr_err("Unable to restore max freq");
80 return err;
81 }
82
83 err = slpc_set_min_freq(slpc, min);
84 if (err) {
85 pr_err("Unable to restore min freq");
86 return err;
87 }
88
89 err = intel_guc_slpc_set_ignore_eff_freq(slpc, false);
90 if (err) {
91 pr_err("Unable to restore efficient freq");
92 return err;
93 }
94
95 return 0;
96 }
97
slpc_measure_power(struct intel_rps * rps,int * freq)98 static u64 slpc_measure_power(struct intel_rps *rps, int *freq)
99 {
100 u64 x[5];
101 int i;
102
103 for (i = 0; i < 5; i++)
104 x[i] = __measure_power(5);
105
106 *freq = (*freq + intel_rps_read_actual_frequency(rps)) / 2;
107
108 /* A simple triangle filter for better result stability */
109 sort(x, 5, sizeof(*x), cmp_u64, NULL);
110 return div_u64(x[1] + 2 * x[2] + x[3], 4);
111 }
112
measure_power_at_freq(struct intel_gt * gt,int * freq,u64 * power)113 static u64 measure_power_at_freq(struct intel_gt *gt, int *freq, u64 *power)
114 {
115 int err = 0;
116
117 err = slpc_set_freq(gt, *freq);
118 if (err)
119 return err;
120 *freq = intel_rps_read_actual_frequency(>->rps);
121 *power = slpc_measure_power(>->rps, freq);
122
123 return err;
124 }
125
vary_max_freq(struct intel_guc_slpc * slpc,struct intel_rps * rps,u32 * max_act_freq)126 static int vary_max_freq(struct intel_guc_slpc *slpc, struct intel_rps *rps,
127 u32 *max_act_freq)
128 {
129 u32 step, max_freq, req_freq;
130 u32 act_freq;
131 int err = 0;
132
133 /* Go from max to min in 5 steps */
134 step = (slpc->rp0_freq - slpc->min_freq) / NUM_STEPS;
135 *max_act_freq = slpc->min_freq;
136 for (max_freq = slpc->rp0_freq; max_freq > slpc->min_freq;
137 max_freq -= step) {
138 err = slpc_set_max_freq(slpc, max_freq);
139 if (err)
140 break;
141
142 req_freq = intel_rps_read_punit_req_frequency(rps);
143
144 /* GuC requests freq in multiples of 50/3 MHz */
145 if (req_freq > (max_freq + FREQUENCY_REQ_UNIT)) {
146 pr_err("SWReq is %d, should be at most %d\n", req_freq,
147 max_freq + FREQUENCY_REQ_UNIT);
148 err = -EINVAL;
149 }
150
151 act_freq = intel_rps_read_actual_frequency(rps);
152 if (act_freq > *max_act_freq)
153 *max_act_freq = act_freq;
154
155 if (err)
156 break;
157 }
158
159 return err;
160 }
161
vary_min_freq(struct intel_guc_slpc * slpc,struct intel_rps * rps,u32 * max_act_freq)162 static int vary_min_freq(struct intel_guc_slpc *slpc, struct intel_rps *rps,
163 u32 *max_act_freq)
164 {
165 u32 step, min_freq, req_freq;
166 u32 act_freq;
167 int err = 0;
168
169 /* Go from min to max in 5 steps */
170 step = (slpc->rp0_freq - slpc->min_freq) / NUM_STEPS;
171 *max_act_freq = slpc->min_freq;
172 for (min_freq = slpc->min_freq; min_freq < slpc->rp0_freq;
173 min_freq += step) {
174 err = slpc_set_min_freq(slpc, min_freq);
175 if (err)
176 break;
177
178 req_freq = intel_rps_read_punit_req_frequency(rps);
179
180 /* GuC requests freq in multiples of 50/3 MHz */
181 if (req_freq < (min_freq - FREQUENCY_REQ_UNIT)) {
182 pr_err("SWReq is %d, should be at least %d\n", req_freq,
183 min_freq - FREQUENCY_REQ_UNIT);
184 err = -EINVAL;
185 }
186
187 act_freq = intel_rps_read_actual_frequency(rps);
188 if (act_freq > *max_act_freq)
189 *max_act_freq = act_freq;
190
191 if (err)
192 break;
193 }
194
195 return err;
196 }
197
slpc_power(struct intel_gt * gt,struct intel_engine_cs * engine)198 static int slpc_power(struct intel_gt *gt, struct intel_engine_cs *engine)
199 {
200 struct intel_guc_slpc *slpc = >_to_guc(gt)->slpc;
201 struct {
202 u64 power;
203 int freq;
204 } min, max;
205 int err = 0;
206
207 /*
208 * Our fundamental assumption is that running at lower frequency
209 * actually saves power. Let's see if our RAPL measurement supports
210 * that theory.
211 */
212 if (!librapl_supported(gt->i915))
213 return 0;
214
215 min.freq = slpc->min_freq;
216 err = measure_power_at_freq(gt, &min.freq, &min.power);
217
218 if (err)
219 return err;
220
221 max.freq = slpc->rp0_freq;
222 err = measure_power_at_freq(gt, &max.freq, &max.power);
223
224 if (err)
225 return err;
226
227 pr_info("%s: min:%llumW @ %uMHz, max:%llumW @ %uMHz\n",
228 engine->name,
229 min.power, min.freq,
230 max.power, max.freq);
231
232 if (10 * min.freq >= 9 * max.freq) {
233 pr_notice("Could not control frequency, ran at [%uMHz, %uMhz]\n",
234 min.freq, max.freq);
235 }
236
237 if (11 * min.power > 10 * max.power) {
238 pr_err("%s: did not conserve power when setting lower frequency!\n",
239 engine->name);
240 err = -EINVAL;
241 }
242
243 /* Restore min/max frequencies */
244 slpc_set_max_freq(slpc, slpc->rp0_freq);
245 slpc_set_min_freq(slpc, slpc->min_freq);
246
247 return err;
248 }
249
max_granted_freq(struct intel_guc_slpc * slpc,struct intel_rps * rps,u32 * max_act_freq)250 static int max_granted_freq(struct intel_guc_slpc *slpc, struct intel_rps *rps, u32 *max_act_freq)
251 {
252 struct intel_gt *gt = rps_to_gt(rps);
253 u32 perf_limit_reasons;
254 int err = 0;
255
256 err = slpc_set_min_freq(slpc, slpc->rp0_freq);
257 if (err)
258 return err;
259
260 *max_act_freq = intel_rps_read_actual_frequency(rps);
261 if (*max_act_freq != slpc->rp0_freq) {
262 /* Check if there was some throttling by pcode */
263 perf_limit_reasons = intel_uncore_read(gt->uncore,
264 intel_gt_perf_limit_reasons_reg(gt));
265
266 /* If not, this is an error */
267 if (!(perf_limit_reasons & GT0_PERF_LIMIT_REASONS_MASK)) {
268 pr_err("Pcode did not grant max freq\n");
269 err = -EINVAL;
270 } else {
271 pr_info("Pcode throttled frequency 0x%x\n", perf_limit_reasons);
272 }
273 }
274
275 return err;
276 }
277
run_test(struct intel_gt * gt,int test_type)278 static int run_test(struct intel_gt *gt, int test_type)
279 {
280 struct intel_guc_slpc *slpc = >_to_guc(gt)->slpc;
281 struct intel_rps *rps = >->rps;
282 struct intel_engine_cs *engine;
283 enum intel_engine_id id;
284 intel_wakeref_t wakeref;
285 struct igt_spinner spin;
286 u32 slpc_min_freq, slpc_max_freq;
287 int err = 0;
288
289 if (!intel_uc_uses_guc_slpc(>->uc))
290 return 0;
291
292 if (slpc->min_freq == slpc->rp0_freq) {
293 pr_err("Min/Max are fused to the same value\n");
294 return -EINVAL;
295 }
296
297 if (igt_spinner_init(&spin, gt))
298 return -ENOMEM;
299
300 if (intel_guc_slpc_get_max_freq(slpc, &slpc_max_freq)) {
301 pr_err("Could not get SLPC max freq\n");
302 return -EIO;
303 }
304
305 if (intel_guc_slpc_get_min_freq(slpc, &slpc_min_freq)) {
306 pr_err("Could not get SLPC min freq\n");
307 return -EIO;
308 }
309
310 /*
311 * Set min frequency to RPn so that we can test the whole
312 * range of RPn-RP0.
313 */
314 err = slpc_set_min_freq(slpc, slpc->min_freq);
315 if (err) {
316 pr_err("Unable to update min freq!");
317 return err;
318 }
319
320 /*
321 * Turn off efficient frequency so RPn/RP0 ranges are obeyed.
322 */
323 err = intel_guc_slpc_set_ignore_eff_freq(slpc, true);
324 if (err) {
325 pr_err("Unable to turn off efficient freq!");
326 return err;
327 }
328
329 intel_gt_pm_wait_for_idle(gt);
330 wakeref = intel_gt_pm_get(gt);
331 for_each_engine(engine, gt, id) {
332 struct i915_request *rq;
333 u32 max_act_freq;
334
335 if (!intel_engine_can_store_dword(engine))
336 continue;
337
338 st_engine_heartbeat_disable(engine);
339
340 rq = igt_spinner_create_request(&spin,
341 engine->kernel_context,
342 MI_NOOP);
343 if (IS_ERR(rq)) {
344 err = PTR_ERR(rq);
345 st_engine_heartbeat_enable(engine);
346 break;
347 }
348
349 i915_request_add(rq);
350
351 if (!igt_wait_for_spinner(&spin, rq)) {
352 pr_err("%s: Spinner did not start\n",
353 engine->name);
354 igt_spinner_end(&spin);
355 st_engine_heartbeat_enable(engine);
356 intel_gt_set_wedged(engine->gt);
357 err = -EIO;
358 break;
359 }
360
361 switch (test_type) {
362 case VARY_MIN:
363 err = vary_min_freq(slpc, rps, &max_act_freq);
364 break;
365
366 case VARY_MAX:
367 err = vary_max_freq(slpc, rps, &max_act_freq);
368 break;
369
370 case MAX_GRANTED:
371 case TILE_INTERACTION:
372 /* Media engines have a different RP0 */
373 if (gt->type != GT_MEDIA && (engine->class == VIDEO_DECODE_CLASS ||
374 engine->class == VIDEO_ENHANCEMENT_CLASS)) {
375 igt_spinner_end(&spin);
376 st_engine_heartbeat_enable(engine);
377 err = 0;
378 continue;
379 }
380
381 err = max_granted_freq(slpc, rps, &max_act_freq);
382 break;
383
384 case SLPC_POWER:
385 err = slpc_power(gt, engine);
386 break;
387 }
388
389 if (test_type != SLPC_POWER) {
390 pr_info("Max actual frequency for %s was %d\n",
391 engine->name, max_act_freq);
392
393 /* Actual frequency should rise above min */
394 if (max_act_freq <= slpc->min_freq) {
395 pr_err("Actual freq did not rise above min\n");
396 pr_err("Perf Limit Reasons: 0x%x\n",
397 intel_uncore_read(gt->uncore,
398 intel_gt_perf_limit_reasons_reg(gt)));
399 err = -EINVAL;
400 }
401 }
402
403 igt_spinner_end(&spin);
404 st_engine_heartbeat_enable(engine);
405
406 if (err)
407 break;
408 }
409
410 /* Restore min/max/efficient frequencies */
411 err = slpc_restore_freq(slpc, slpc_min_freq, slpc_max_freq);
412
413 if (igt_flush_test(gt->i915))
414 err = -EIO;
415
416 intel_gt_pm_put(gt, wakeref);
417 igt_spinner_fini(&spin);
418 intel_gt_pm_wait_for_idle(gt);
419
420 return err;
421 }
422
live_slpc_vary_min(void * arg)423 static int live_slpc_vary_min(void *arg)
424 {
425 struct drm_i915_private *i915 = arg;
426 struct intel_gt *gt;
427 unsigned int i;
428 int ret;
429
430 for_each_gt(gt, i915, i) {
431 ret = run_test(gt, VARY_MIN);
432 if (ret)
433 return ret;
434 }
435
436 return ret;
437 }
438
live_slpc_vary_max(void * arg)439 static int live_slpc_vary_max(void *arg)
440 {
441 struct drm_i915_private *i915 = arg;
442 struct intel_gt *gt;
443 unsigned int i;
444 int ret;
445
446 for_each_gt(gt, i915, i) {
447 ret = run_test(gt, VARY_MAX);
448 if (ret)
449 return ret;
450 }
451
452 return ret;
453 }
454
455 /* check if pcode can grant RP0 */
live_slpc_max_granted(void * arg)456 static int live_slpc_max_granted(void *arg)
457 {
458 struct drm_i915_private *i915 = arg;
459 struct intel_gt *gt;
460 unsigned int i;
461 int ret;
462
463 for_each_gt(gt, i915, i) {
464 ret = run_test(gt, MAX_GRANTED);
465 if (ret)
466 return ret;
467 }
468
469 return ret;
470 }
471
live_slpc_power(void * arg)472 static int live_slpc_power(void *arg)
473 {
474 struct drm_i915_private *i915 = arg;
475 struct intel_gt *gt;
476 unsigned int i;
477 int ret;
478
479 for_each_gt(gt, i915, i) {
480 ret = run_test(gt, SLPC_POWER);
481 if (ret)
482 return ret;
483 }
484
485 return ret;
486 }
487
slpc_spinner_thread(struct kthread_work * work)488 static void slpc_spinner_thread(struct kthread_work *work)
489 {
490 struct slpc_thread *thread = container_of(work, typeof(*thread), work);
491
492 thread->result = run_test(thread->gt, TILE_INTERACTION);
493 }
494
live_slpc_tile_interaction(void * arg)495 static int live_slpc_tile_interaction(void *arg)
496 {
497 struct drm_i915_private *i915 = arg;
498 struct intel_gt *gt;
499 struct slpc_thread *threads;
500 int i = 0, ret = 0;
501
502 threads = kcalloc(I915_MAX_GT, sizeof(*threads), GFP_KERNEL);
503 if (!threads)
504 return -ENOMEM;
505
506 for_each_gt(gt, i915, i) {
507 threads[i].worker = kthread_run_worker(0, "igt/slpc_parallel:%d", gt->info.id);
508
509 if (IS_ERR(threads[i].worker)) {
510 ret = PTR_ERR(threads[i].worker);
511 break;
512 }
513
514 threads[i].gt = gt;
515 kthread_init_work(&threads[i].work, slpc_spinner_thread);
516 kthread_queue_work(threads[i].worker, &threads[i].work);
517 }
518
519 for_each_gt(gt, i915, i) {
520 int status;
521
522 if (IS_ERR_OR_NULL(threads[i].worker))
523 continue;
524
525 kthread_flush_work(&threads[i].work);
526 status = READ_ONCE(threads[i].result);
527 if (status && !ret) {
528 pr_err("%s GT %d failed ", __func__, gt->info.id);
529 ret = status;
530 }
531 kthread_destroy_worker(threads[i].worker);
532 }
533
534 kfree(threads);
535 return ret;
536 }
537
intel_slpc_live_selftests(struct drm_i915_private * i915)538 int intel_slpc_live_selftests(struct drm_i915_private *i915)
539 {
540 static const struct i915_subtest tests[] = {
541 SUBTEST(live_slpc_vary_max),
542 SUBTEST(live_slpc_vary_min),
543 SUBTEST(live_slpc_max_granted),
544 SUBTEST(live_slpc_power),
545 SUBTEST(live_slpc_tile_interaction),
546 };
547
548 struct intel_gt *gt;
549 unsigned int i;
550
551 for_each_gt(gt, i915, i) {
552 if (intel_gt_is_wedged(gt))
553 return 0;
554 }
555
556 return i915_live_subtests(tests, i915);
557 }
558