File Index
Files and directories
Sign in
FILE

command.c

File preview with syntax highlighting.

linux-6.19.14/drivers/thermal/testing/command.c C
  1// SPDX-License-Identifier: GPL-2.0
  2/*
  3 * Copyright 2024, Intel Corporation
  4 *
  5 * Author: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
  6 *
  7 * Thermal subsystem testing facility.
  8 *
  9 * This facility allows the thermal core functionality to be exercised in a
 10 * controlled way in order to verify its behavior.
 11 *
 12 * It resides in the "thermal-testing" directory under the debugfs root and
 13 * starts with a single file called "command" which can be written a string
 14 * representing a thermal testing facility command.
 15 *
 16 * The currently supported commands are listed in the tt_commands enum below.
 17 *
 18 * The "addtz" command causes a new test thermal zone template to be created,
 19 * for example:
 20 *
 21 * # echo addtz > /sys/kernel/debug/thermal-testing/command
 22 *
 23 * That template will be represented as a subdirectory in the "thermal-testing"
 24 * directory, for example
 25 *
 26 * # ls /sys/kernel/debug/thermal-testing/
 27 * command tz0
 28 *
 29 * The thermal zone template can be populated with trip points with the help of
 30 * the "tzaddtrip" command, for example:
 31 *
 32 * # echo tzaddtrip:0 > /sys/kernel/debug/thermal-testing/command
 33 *
 34 * which causes a trip point template to be added to the test thermal zone
 35 * template 0 (represented by the tz0 subdirectory in "thermal-testing").
 36 *
 37 * # ls /sys/kernel/debug/thermal-testing/tz0
 38 * init_temp temp trip_0_temp trip_0_hyst
 39 *
 40 * The temperature of a trip point template is initially THERMAL_TEMP_INVALID
 41 * and its hysteresis is initially 0.  They can be adjusted by writing to the
 42 * "trip_x_temp" and "trip_x_hyst" files correspoinding to that trip point
 43 * template, respectively.
 44 *
 45 * The initial temperature of a thermal zone based on a template can be set by
 46 * writing to the "init_temp" file in its directory under "thermal-testing", for
 47 * example:
 48 *
 49 * echo 50000 > /sys/kernel/debug/thermal-testing/tz0/init_temp
 50 *
 51 * When ready, "tzreg" command can be used for registering and enabling a
 52 * thermal zone based on a given template with the thermal core, for example
 53 *
 54 * # echo tzreg:0 > /sys/kernel/debug/thermal-testing/command
 55 *
 56 * In this case, test thermal zone template 0 is used for registering a new
 57 * thermal zone and the set of trip point templates associated with it is used
 58 * for populating the new thermal zone's trip points table.  The type of the new
 59 * thermal zone is "test_tz".
 60 *
 61 * The temperature and hysteresis of all of the trip points in that new thermal
 62 * zone are adjustable via sysfs, so they can be updated at any time.
 63 *
 64 * The current temperature of the new thermal zone can be set by writing to the
 65 * "temp" file in the corresponding thermal zone template's directory under
 66 * "thermal-testing", for example
 67 *
 68 * echo 10000 > /sys/kernel/debug/thermal-testing/tz0/temp
 69 *
 70 * which will also trigger a temperature update for this zone in the thermal
 71 * core, including checking its trip points, sending notifications to user space
 72 * if any of them have been crossed and so on.
 73 *
 74 * When it is not needed any more, a test thermal zone template can be deleted
 75 * with the help of the "deltz" command, for example
 76 *
 77 * # echo deltz:0 > /sys/kernel/debug/thermal-testing/command
 78 *
 79 * which will also unregister the thermal zone based on it, if present.
 80 */
 81
 82#define pr_fmt(fmt) "thermal-testing: " fmt
 83
 84#include <linux/debugfs.h>
 85#include <linux/module.h>
 86
 87#include "thermal_testing.h"
 88
 89struct dentry *d_testing;
 90
 91#define TT_COMMAND_SIZE		16
 92
 93enum tt_commands {
 94	TT_CMD_ADDTZ,
 95	TT_CMD_DELTZ,
 96	TT_CMD_TZADDTRIP,
 97	TT_CMD_TZREG,
 98	TT_CMD_TZUNREG,
 99};
100
101static const char *tt_command_strings[] = {
102	[TT_CMD_ADDTZ] = "addtz",
103	[TT_CMD_DELTZ] = "deltz",
104	[TT_CMD_TZADDTRIP] = "tzaddtrip",
105	[TT_CMD_TZREG] = "tzreg",
106	[TT_CMD_TZUNREG] = "tzunreg",
107};
108
109static int tt_command_exec(int index, const char *arg)
110{
111	int ret;
112
113	switch (index) {
114	case TT_CMD_ADDTZ:
115		ret = tt_add_tz();
116		break;
117
118	case TT_CMD_DELTZ:
119		ret = tt_del_tz(arg);
120		break;
121
122	case TT_CMD_TZADDTRIP:
123		ret = tt_zone_add_trip(arg);
124		break;
125
126	case TT_CMD_TZREG:
127		ret = tt_zone_reg(arg);
128		break;
129
130	case TT_CMD_TZUNREG:
131		ret = tt_zone_unreg(arg);
132		break;
133
134	default:
135		ret = -EINVAL;
136		break;
137	}
138
139	return ret;
140}
141
142static ssize_t tt_command_process(char *s)
143{
144	char *arg;
145	int i;
146
147	strim(s);
148
149	arg = strchr(s, ':');
150	if (arg) {
151		*arg = '\0';
152		arg++;
153	}
154
155	for (i = 0; i < ARRAY_SIZE(tt_command_strings); i++) {
156		if (!strcmp(s, tt_command_strings[i]))
157			return tt_command_exec(i, arg);
158	}
159
160	return -EINVAL;
161}
162
163static ssize_t tt_command_write(struct file *file, const char __user *user_buf,
164				size_t count, loff_t *ppos)
165{
166	char buf[TT_COMMAND_SIZE];
167	ssize_t ret;
168
169	if (*ppos)
170		return -EINVAL;
171
172	if (count > TT_COMMAND_SIZE - 1)
173		return -E2BIG;
174
175	if (copy_from_user(buf, user_buf, count))
176		return -EFAULT;
177	buf[count] = '\0';
178
179	ret = tt_command_process(buf);
180	if (ret)
181		return ret;
182
183	return count;
184}
185
186static const struct file_operations tt_command_fops = {
187	.write = tt_command_write,
188	.open =	 simple_open,
189	.llseek = default_llseek,
190};
191
192static int __init thermal_testing_init(void)
193{
194	d_testing = debugfs_create_dir("thermal-testing", NULL);
195	if (!IS_ERR(d_testing))
196		debugfs_create_file("command", 0200, d_testing, NULL,
197				    &tt_command_fops);
198
199	return 0;
200}
201module_init(thermal_testing_init);
202
203static void __exit thermal_testing_exit(void)
204{
205	debugfs_remove(d_testing);
206	tt_zone_cleanup();
207}
208module_exit(thermal_testing_exit);
209
210MODULE_DESCRIPTION("Thermal core testing facility");
211MODULE_LICENSE("GPL v2");
~/ Read-only file preview.