summaryrefslogtreecommitdiff
path: root/lib/i915/intel_drrs.c
blob: ac8dd5e61d2190e8093e54e01c277ee888f037ee (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
/* SPDX-License-Identifier: MIT */
/*
 * Copyright © 2023 Intel Corporation
 */

#include <fcntl.h>

#include "igt.h"
#include "igt_sysfs.h"

#include "intel_drrs.h"

/**
 * intel_is_drrs_supported:
 * @device: fd of the device
 * @pipe: Display pipe
 *
 * Check if DRRS is supported on given pipe.
 *
 * Returns:
 * true if DRRS is supported and false otherwise.
 */
bool intel_is_drrs_supported(int device, enum pipe pipe)
{
	char buf[256];
	int dir;

	dir = igt_debugfs_pipe_dir(device, pipe, O_DIRECTORY);
	igt_require_fd(dir);
	igt_debugfs_simple_read(dir, "i915_drrs_status", buf, sizeof(buf));
	close(dir);

	return strstr(buf, "DRRS capable: yes");
}

/**
 * intel_output_has_drrs
 * @device: fd of the device
 * @output: Display output
 *
 * Check if drrs used on given output.
 *
 * Returns:
 * true if DRRS is used and false otherwise.
 */
bool intel_output_has_drrs(int device, igt_output_t *output)
{
	char buf[256];
	int dir;

	dir = igt_debugfs_connector_dir(device, output->name, O_DIRECTORY);
	igt_require_fd(dir);
	igt_debugfs_simple_read(dir, "i915_drrs_type", buf, sizeof(buf));
	close(dir);

	return strstr(buf, "seamless");
}

static void drrs_set(int device, enum pipe pipe, unsigned int val)
{
	char buf[2];
	int dir, ret;

	igt_debug("Manually %sabling DRRS. %u\n", val ? "en" : "dis", val);
	snprintf(buf, sizeof(buf), "%d", val);

	dir = igt_debugfs_pipe_dir(device, pipe, O_DIRECTORY);
	igt_require_fd(dir);
	ret = igt_sysfs_write(dir, "i915_drrs_ctl", buf, sizeof(buf) - 1);
	close(dir);

	/*
	 * drrs_enable() is called on DRRS capable platform only,
	 * whereas drrs_disable() is called on all platforms.
	 * So handle the failure of debugfs_write only for drrs_enable().
	 */
	if (val)
		igt_assert_f(ret == (sizeof(buf) - 1), "debugfs_write failed");
}

/**
 * intel_drrs_enable:
 * @device: fd of the device
 * @pipe: Display pipe
 *
 * Enable DRRS on given pipe
 *
 * Returns:
 * none
 */
void intel_drrs_enable(int device, enum pipe pipe)
{
	drrs_set(device, pipe, 1);
}

/**
 * intel_drrs_disable:
 * @device: fd of the device
 * @pipe: Display pipe
 *
 * Disable DRRS on given pipe
 *
 * Returns:
 * none
 */
void intel_drrs_disable(int device, enum pipe pipe)
{
	drrs_set(device, pipe, 0);
}

/**
 * intel_is_drrs_inactive:
 * @device: fd of the device
 * @pipe: Display pipe
 *
 * Check if drrs is inactive on given pipe
 *
 * Returns:
 * true if inactive and false otherwise
 */
bool intel_is_drrs_inactive(int device, enum pipe pipe)
{
	char buf[256];
	int dir;

	dir = igt_debugfs_pipe_dir(device, pipe, O_DIRECTORY);
	igt_require_fd(dir);
	igt_debugfs_simple_read(dir, "i915_drrs_status", buf, sizeof(buf));
	close(dir);

	return strstr(buf, "DRRS active: no");
}