Already thermal monitor in pass get the thermal information with
'thermal_device_name' property. When over-temperature is deteced,
must need to prevent the dangerous situation by using the cooling-device
which is attached to a thermal device.
So that add 'cooling_device_name' property in 'device_list' section
in order to get/set the information of cooling-device.
Also, 'thermal,cooling_device_state' property will be used
when try to change the state of cooling-device if over-temperature is
detected.
Lastly, enable thermal operation for both new PASS_RESOURCE_BATTERY_ID devie type
and PASS_RESOURCE_NONSTANDARD_ID.
[Newly added properties for cooling-device]
- 'cooling_device_name' property in 'device_list' section
- 'thermal,cooling_device_state' property in 'level_list' section
[Example of cooling-device properties]
In case of scripts/pass.json,
"device_name" : "cpu0",
"device_config_path" : "/hal/etc/pass/pass-cpu0.json",
"thermal_device_name" : "thermal_zone0",
"cooling_device_name" : "cooling_device0", <- Added
"cpu,number_of_cpus" : 4,
"cpu,first_cpu" : 0,
In case of scripts/pass-cpu0.json,
{
"level" : 0,
"dvfs,minimum_frequency_khz" : 600000,
"dvfs,maximum_frequency_khz" :
1500000,
"thermal,cooling_device_state" : 0 <- Added
}, {
"level" : 1,
"dvfs,minimum_frequency_khz" :
1500000,
"dvfs,maximum_frequency_khz" :
1500000,
"thermal,cooling_device_state" : 1 <- Added
},
Change-Id: I86bfc5ce2037559e81bbf70567b82457167d4ced
Signed-off-by: Chanwoo Choi <cw00.choi@samsung.com>
policy);
}
+/**
+ * @brief Get the state of cooling_device for h/w resource
+ * @param [in] res Instance of h/w resource
+ * @return @c positive integer on success, otherwise error value
+ * @retval -22 Invalid argument (-EINVAL)
+ * @retval -1 Operation not permitted (-EPERM)
+ * @retval -19 Operation not supported (-ENOTSUP)
+ */
+int pass_hal_get_cooling_device_state(struct pass_resource *res)
+{
+ if (!res)
+ return -EINVAL;
+
+ /*
+ * In the case of the HAL TMU ops, res_cooling_name is used
+ * as the first argument instead of res_name.
+ */
+ return hal_power_thermal_get_cooling_device_state(
+ res->config_data.res_type,
+ res->config_data.res_cooling_name);
+}
+
+/**
+ * @brief Set the state to cooling_device for h/w resource
+ * @param [in] res Instance of h/w resource
+ * @param [in] state State of cooling device
+ * @return @c positive integer on success, otherwise error value
+ * @retval -22 Invalid argument (-EINVAL)
+ * @retval -1 Operation not permitted (-EPERM)
+ * @retval -19 Operation not supported (-ENOTSUP)
+ */
+int pass_hal_set_cooling_device_state(struct pass_resource *res, int state)
+{
+ if (!res)
+ return -EINVAL;
+
+ /*
+ * In the case of the HAL TMU ops, res_cooling_name is used
+ * as the first argument instead of res_name.
+ */
+ return hal_power_thermal_set_cooling_device_state(
+ res->config_data.res_type,
+ res->config_data.res_cooling_name,
+ state);
+}
+
+/**
+ * @brief Get the maximum state of cooling_device for h/w resource
+ * @param [in] res Instance of h/w resource
+ * @return @c positive integer on success, otherwise error value
+ * @retval -22 Invalid argument (-EINVAL)
+ * @retval -1 Operation not permitted (-EPERM)
+ * @retval -19 Operation not supported (-ENOTSUP)
+ */
+int pass_hal_get_cooling_device_max_state(struct pass_resource *res)
+{
+ if (!res)
+ return -EINVAL;
+
+ /*
+ * In the case of the HAL TMU ops, res_cooling_name is used
+ * as the first argument instead of res_name.
+ */
+ return hal_power_thermal_get_cooling_device_max_state(
+ res->config_data.res_type,
+ res->config_data.res_cooling_name);
+}
+
/**
* @brief Set the fault_around_bytes for memory h/w resource
* @param [in] res Instance of h/w resource
int pass_hal_get_temp(struct pass_resource *res);
int pass_hal_get_tmu_policy(struct pass_resource *res, char *policy);
+/* Get and set the state of cooling device on specific h/w. */
+int pass_hal_get_cooling_device_state(struct pass_resource *res);
+int pass_hal_set_cooling_device_state(struct pass_resource *res, int state);
+int pass_hal_get_cooling_device_max_state(struct pass_resource *res);
+
/***
* Functions for CPU H/W resources
*/
level->gov_timeout = INIT_VALUE;
level->fault_around_bytes = INIT_VALUE;
+
+ level->cooling_device_state = INIT_VALUE;
}
static int parse_level(struct pass_resource *res, json_object *obj,
int num_left_cond_busy_cpu;
double governor_timeout_sec;
int fault_around_bytes;
+ int cooling_device_state;
/* Get property values */
level = get_int_from_object(obj, "level");
fault_around_bytes = get_int_from_object(obj, "memory,fault_around_bytes");
+ cooling_device_state = get_int_from_object(obj, "thermal,cooling_device_state");
+
/* Check the mandatory property values are valid or not */
if (level < 0) {
_E("Failed to get 'level' property in 'level_list' section\n");
if (fault_around_bytes >= 0)
target_level->fault_around_bytes = fault_around_bytes;
+ /*
+ * Properties for the following h/w resources:
+ * - PASS_RESOURCE_CPU_ID
+ * - PASS_RESOURCE_BUS_ID
+ * - PASS_RESOURCE_GPU_ID
+ * - PASS_RESOURCE_BATTERY_ID
+ * - PASS_RESOURCE_NONSTANDARD_ID
+ */
+ if (cooling_device_state >= 0)
+ target_level->cooling_device_state = cooling_device_state;
+
return 0;
}
const char *device_type;
const char *device_name;
const char *thermal_device_name;
+ const char *cooling_device_name;
const char *device_config_path;
const char *cpu_load_path;
int number_of_cpus;
/* - optional properties */
thermal_device_name = get_string_from_object(obj, "thermal_device_name");
+ cooling_device_name = get_string_from_object(obj, "cooling_device_name");
/* - optional properties for only CPU */
cpu_load_path = get_string_from_object(obj, "cpu,cpu_load_path");
snprintf(config_data->res_name, BUFF_MAX, "%s", device_name);
snprintf(config_data->res_thermal_name, BUFF_MAX, "%s", thermal_device_name);
+ snprintf(config_data->res_cooling_name, BUFF_MAX, "%s", cooling_device_name);
snprintf(config_data->path_conf_file, BUFF_MAX, "%s", device_config_path);
snprintf(config_data->path_load_table, BUFF_MAX, "%s", cpu_load_path);
config_data->num_cpus = number_of_cpus;
level->fault_around_bytes,
res->config_data.res_name);
}
+
+ if (level->cooling_device_state >= 0) {
+ _D("cooling_device_state is %10d of '%s' resource\n",
+ level->cooling_device_state,
+ res->config_data.res_name);
+ }
+
}
static void rescon_adjust_level(struct pass_level *a, struct pass_level *b)
if (a->fault_around_bytes > MAX_FAULT_AROUND_BYTES)
a->fault_around_bytes = MAX_FAULT_AROUND_BYTES;
}
+
+ /* Adjust cooling_device_state */
+ a->cooling_device_state = MAX(a->cooling_device_state,
+ b->cooling_device_state);
}
static int rescon_update(struct pass_resource *res)
int limit_min_cpu = -1;
int limit_max_cpu = -1;
int fault_around_bytes = -1;
+ int cooling_device_state = -1;
int ret, i;
int failed = 0;
adjusted_level.limit_min_cpu = MIN_INT;
adjusted_level.limit_max_cpu = MAX_INT;
adjusted_level.fault_around_bytes = MIN_INT;
+ adjusted_level.cooling_device_state = MIN_INT;
/* Adjust with pass_level */
if (res->rescon.curr_level >= 0)
case PASS_RESOURCE_BUS_ID:
limit_max_freq = adjusted_level.limit_max_freq;
limit_min_freq = adjusted_level.limit_min_freq;
+ /* fall through */
+ case PASS_RESOURCE_BATTERY_ID:
+ case PASS_RESOURCE_NONSTANDARD_ID:
+ cooling_device_state = adjusted_level.cooling_device_state;
break;
case PASS_RESOURCE_MEMORY_ID:
fault_around_bytes = adjusted_level.fault_around_bytes;
break;
- case PASS_RESOURCE_NONSTANDARD_ID:
- break;
default:
return -EINVAL;
}
}
}
+ /* Set cooling device state for specific h/w */
+ if (cooling_device_state >= 0) {
+ ret = pass_hal_set_cooling_device_state(res, cooling_device_state);
+ if (ret < 0) {
+ _W("failed to set the cooling_device_state(%d) of %s",
+ cooling_device_state,
+ res->config_data.res_name);
+ failed = 1;
+ }
+ }
+
if (!failed)
rescon_print_level(res, &adjusted_level);
else
_I("Resource%d type : %d\n", i, config_data->res_type);
_I("Resource%d name : %s\n", i, config_data->res_name);
_I("Resource%d thermal name : %s\n", i, config_data->res_thermal_name);
+ _I("Resource%d cooling name : %s\n", i, config_data->res_cooling_name);
_I("Resource%d path_conf_file : %s\n", i, config_data->path_conf_file);
_I("Resource%d path_load_table: %s\n", i, config_data->path_load_table);
_I("Resource%d number of cpus : %d\n", i, config_data->num_cpus);
* - PASS_RESOURCE_MEMORY_ID
*/
int fault_around_bytes;
-
+ /**
+ * The current state of cooling device
+ * and this property is used for the following resources:
+ * - PASS_RESOURCE_CPU_ID
+ * - PASS_RESOURCE_BUS_ID
+ * - PASS_RESOURCE_GPU_ID
+ * - PASS_RESOURCE_BATTERY_ID
+ * - PASS_RESOURCE_NONSTANDARD_ID
+ */
+ int cooling_device_state;
/* Properties for the timer */
* res_thermal_name is 'thermal_zone3'.
*/
char res_thermal_name[BUFF_MAX];
+ /**
+ * [optional] the unique sysfs node name of cooling device for each resource
+ * - In the case of 'cpu0',
+ * If sysfs node of cooling device is /sys/class/thermal/cooling_device0,
+ * res_cooling_name is 'cooling_device0'.
+ */
+ char res_cooling_name[BUFF_MAX];
/** [mandatory] Path fo configuration for each h/w resource */
char path_conf_file[BUFF_MAX];