From 5125dc4361d5f5fabb6f947d594fde89f217aa04 Mon Sep 17 00:00:00 2001 From: Chanwoo Choi Date: Fri, 14 Jul 2017 10:37:18 +0900 Subject: [PATCH] pass: rescon: Separate pass-rescon module from pass-gov module The existing pass-gov module has the three features as following: - Resource Controller to change the current/min/max 'PASS Level' -> rescon. - Resource Monitor to collect the current system status -> resmon. - Runtime governor for CPU hotplug policy. In order to make the pass-rescon as the separate module, this patch creates the pass-rescon.c module from pass-gov module separately. Change-Id: I2f4e96fa47e95b0f503638cf4c944699fbea44c5 Signed-off-by: Chanwoo Choi --- CMakeLists.txt | 1 + src/pass/pass-gov.c | 165 +------------------------------------------- src/pass/pass-gov.h | 2 - src/pass/pass-pmqos.c | 5 +- src/pass/pass-rescon.c | 184 +++++++++++++++++++++++++++++++++++++++++++++++++ src/pass/pass-rescon.h | 25 +++++++ 6 files changed, 216 insertions(+), 166 deletions(-) create mode 100644 src/pass/pass-rescon.c create mode 100644 src/pass/pass-rescon.h diff --git a/CMakeLists.txt b/CMakeLists.txt index 2715865..54b8036 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -68,6 +68,7 @@ SET(SRCS src/pass/pass-gov-step.c src/pass/pass-parser.c src/pass/pass-hal.c + src/pass/pass-rescon.c src/pass/pass-pmqos.c src/pmqos/pmqos.c src/pmqos/pmqos-parser.c diff --git a/src/pass/pass-gov.c b/src/pass/pass-gov.c index b4d0de5..4080008 100644 --- a/src/pass/pass-gov.c +++ b/src/pass/pass-gov.c @@ -25,6 +25,7 @@ #include "pass-gov.h" #include "pass-pmqos.h" #include "pass-hal.h" +#include "pass-rescon.h" #include "core/device-notifier.h" #include "core/config-parser.h" @@ -93,46 +94,6 @@ static int pass_notifier_exit(struct pass_policy *policy) ****************************************************************************/ /* - * pass_hotplug_set_online - Change the minimum number of online cpu - * - * @policy: the instance of struct pass_policy - * @min_num: the minimum number of online cpu - */ -static void pass_hotplug_set_online(struct pass_policy *policy, - unsigned int min_num) -{ - struct pass_resource *res = to_pass_resource(policy); - struct pass_hotplug *hotplug = policy->hotplug; - int i; - - if (!hotplug || min_num == hotplug->online) - return; - - if (min_num > hotplug->num_cpus) - min_num = hotplug->num_cpus; - - pass_set_online_min_num(res, min_num); - - for (i = 0 ; i < hotplug->num_cpus; i++) { - if (i < min_num) { - pass_set_online_state(res, hotplug->sequence[i], - PASS_CPU_UP); - } else { - pass_set_online_state(res, hotplug->sequence[i], - PASS_CPU_DOWN); - } - } - - /* - _I("- CPU %4s '%d->%d'Core\n", - (hotplug->online > min_num ? "DOWN" : "UP"), - hotplug->online, min_num); - */ - - hotplug->online = min_num; -} - -/* * pass_hotplug_stop - Stop PASS hotplug * * @policy: the instance of struct pass_policy @@ -194,84 +155,6 @@ struct pass_hotplug* pass_get_hotplug(struct pass_policy *policy, ****************************************************************************/ /* - * pass_governor_change_level - Change frequency and number of online resources - * - * @policy: the instance of struct pass_policy - * @new_level: the desired pass level - */ -static int pass_governor_change_level(struct pass_policy *policy, int new_level) -{ - struct pass_resource *res = to_pass_resource(policy); - struct pass_conf_data *cdata = &res->cdata; - struct pass_table *table = policy->pass_table; - struct pass_hotplug *hotplug = policy->hotplug; - int curr_level = policy->curr_level; - int limit_max_freq; - int limit_min_freq; - int limit_min_cpu; - int ret; - - if (new_level > policy->max_level) - new_level = policy->max_level; - - if (new_level < policy->min_level) - new_level = policy->min_level; - - if (new_level == curr_level) - return 0; - - /* - * Get the max/min frequency and the number of max online - * according to PASS level. - */ - limit_max_freq = table[new_level].limit_max_freq; - limit_min_freq = table[new_level].limit_min_freq; - - policy->prev_level = curr_level; - policy->curr_level = new_level; - - /* Turn on/off CPUs according the maximum number of online CPU */ - if (hotplug) { - if (hotplug->governor) - limit_min_cpu = hotplug->governor(policy); - else - limit_min_cpu = 1; - - pass_hotplug_set_online(policy, limit_min_cpu); - } - - /* Set maximum frequency */ - if (limit_max_freq) { - ret = pass_set_max_freq(res, limit_max_freq); - if (ret < 0) { - _E("cannot set the maximum frequency of %s", - cdata->res_name); - return -EINVAL; - } - } - - /* Set minimum frequency */ - if (limit_min_freq) { - ret = pass_set_min_freq(res, limit_min_freq); - if (ret < 0) { - _E("cannot set the minimum frequency of %s", - cdata->res_name); - return -EINVAL; - } - } - - /* - _I("[PASS %s] Level %4s '%d->%d' : 'max %d | min %d'Hz/'%d'Core\n", - res->cdata.res_name, - (curr_level > new_level ? "DOWN" : "UP"), - curr_level, new_level, - limit_max_freq, limit_min_freq, limit_min_cpu); - */ - - return 0; -}; - -/* * pass_calculate_busy_cpu - Count a number of busy cpu among NR_CPUS by using * runnable_avg_sum/runnable_avg_period * @@ -386,7 +269,7 @@ static Eina_Bool pass_governor_core_timer(void *data) if (policy->governor->governor) { level = policy->governor->governor(policy); - pass_governor_change_level(policy, level); + pass_rescon_set_level(policy, level); } else { _E("cannot execute governor function"); pass_governor_update(policy, PASS_GOV_STOP); @@ -452,7 +335,7 @@ static void __pass_governor_start(struct pass_policy *policy) if (policy->init_level > policy->max_level) policy->init_level = policy->max_level; - pass_governor_change_level(policy, policy->init_level); + pass_rescon_set_level(policy, policy->init_level); /* Set PASS state as PASS_GOV_START */ policy->gov_state = PASS_GOV_START; @@ -586,48 +469,6 @@ static int __pass_governor_update(struct pass_policy *policy, } /* - * pass_governor_change_level_scope - Change the scope of pass level - * - * @policy: the instance of struct pass_policy - * @new_level: the desirous pass level - * @min_level: the minimum pass level - * @max_level: the maximum pass level - * @data: the PMQoS's data containing the scenario name and lock state - */ -int pass_governor_change_level_scope(struct pass_policy *policy, int new_level, - int min_level, int max_level, void *data) -{ - if (!policy) - return -EINVAL; - - /* - * FIXME: PMQoS core sends the raw data to the HAL in order to - * support the backwards compatibility. This function call will - * be removed after finding the proper method. - */ - if (data) - pass_set_pmqos_data(to_pass_resource(policy), data); - - if (min_level > max_level) { - _E("min_level(%d) have to be smaller than max_level(%d)\n", - min_level, max_level); - return -EINVAL; - } - - if (min_level == policy->min_level - && max_level == policy->max_level) - return 0; - - /* Change minimum/maximum pass level */ - policy->min_level = min_level; - policy->max_level = max_level; - - pass_governor_change_level(policy, new_level); - - return 0; -} - -/* * Define PASS governor * * - Step governor diff --git a/src/pass/pass-gov.h b/src/pass/pass-gov.h index 221a54b..0032752 100644 --- a/src/pass/pass-gov.h +++ b/src/pass/pass-gov.h @@ -23,8 +23,6 @@ int pass_governor_init(struct pass_policy *policy); int pass_governor_exit(struct pass_policy *policy); int pass_governor_update(struct pass_policy *policy, enum pass_gov_state state); -int pass_governor_change_level_scope(struct pass_policy *policy, int new_level, - int min_level, int max_level, void *data); /* Get the governor/hotplug instance according to enum pass_gov_type */ struct pass_governor* pass_get_governor(struct pass_policy *policy, diff --git a/src/pass/pass-pmqos.c b/src/pass/pass-pmqos.c index 47417d9..8558418 100644 --- a/src/pass/pass-pmqos.c +++ b/src/pass/pass-pmqos.c @@ -23,6 +23,7 @@ #include "pass.h" #include "pass-gov.h" +#include "pass-rescon.h" #include "core/device-notifier.h" #include "core/config-parser.h" @@ -189,8 +190,8 @@ int pass_notifier_pmqos_func(struct pass_policy *policy, void *data) } } - pass_governor_change_level_scope(policy, new_level, - min_level, max_level, data); + pass_rescon_set_level_scope(policy, new_level, + min_level, max_level, data); if (scn->locked) { _I("Lock '%s' scenario for '%s' resource\n", diff --git a/src/pass/pass-rescon.c b/src/pass/pass-rescon.c new file mode 100644 index 0000000..f025d75 --- /dev/null +++ b/src/pass/pass-rescon.c @@ -0,0 +1,184 @@ +/* + * PASS (Power Aware System Service) Governor + * + * Copyright (c) 2012 - 2017 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the License); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include +#include + +#include "pass.h" +#include "pass-hal.h" + +/* + * pass_hotplug_set_online - Change the minimum number of online cpu + * + * @policy: the instance of struct pass_policy + * @min_num: the minimum number of online cpu + */ +static void hotplug_set_online(struct pass_policy *policy, + unsigned int min_num) +{ + struct pass_resource *res = to_pass_resource(policy); + struct pass_hotplug *hotplug = policy->hotplug; + int i; + + if (!hotplug || min_num == hotplug->online) + return; + + if (min_num > hotplug->num_cpus) + min_num = hotplug->num_cpus; + + pass_set_online_min_num(res, min_num); + + for (i = 0 ; i < hotplug->num_cpus; i++) { + if (i < min_num) { + pass_set_online_state(res, hotplug->sequence[i], + PASS_CPU_UP); + } else { + pass_set_online_state(res, hotplug->sequence[i], + PASS_CPU_DOWN); + } + } + + /* + _I("- CPU %4s '%d->%d'Core\n", + (hotplug->online > min_num ? "DOWN" : "UP"), + hotplug->online, min_num); + */ + + hotplug->online = min_num; +} + +/* + * pass_rescon_set_level - Change frequency and number of online resources + * + * @policy: the instance of struct pass_policy + * @new_level: the desired pass level + */ +int pass_rescon_set_level(struct pass_policy *policy, int new_level) +{ + struct pass_resource *res = to_pass_resource(policy); + struct pass_conf_data *cdata = &res->cdata; + struct pass_table *table = policy->pass_table; + struct pass_hotplug *hotplug = policy->hotplug; + int curr_level = policy->curr_level; + int limit_max_freq; + int limit_min_freq; + int limit_min_cpu; + int ret; + + if (new_level > policy->max_level) + new_level = policy->max_level; + + if (new_level < policy->min_level) + new_level = policy->min_level; + + if (new_level == curr_level) + return 0; + + /* + * Get the max/min frequency and the number of max online + * according to PASS level. + */ + limit_max_freq = table[new_level].limit_max_freq; + limit_min_freq = table[new_level].limit_min_freq; + + policy->prev_level = curr_level; + policy->curr_level = new_level; + + /* Turn on/off CPUs according the maximum number of online CPU */ + if (hotplug) { + if (hotplug->governor) + limit_min_cpu = hotplug->governor(policy); + else + limit_min_cpu = 1; + + hotplug_set_online(policy, limit_min_cpu); + } + + /* Set maximum frequency */ + if (limit_max_freq) { + ret = pass_set_max_freq(res, limit_max_freq); + if (ret < 0) { + _E("cannot set the maximum frequency of %s", + cdata->res_name); + return -EINVAL; + } + } + + /* Set minimum frequency */ + if (limit_min_freq) { + ret = pass_set_min_freq(res, limit_min_freq); + if (ret < 0) { + _E("cannot set the minimum frequency of %s", + cdata->res_name); + return -EINVAL; + } + } + + /* + _I("[PASS %s] Level %4s '%d->%d' : 'max %d | min %d'Hz/'%d'Core\n", + res->cdata.res_name, + (curr_level > new_level ? "DOWN" : "UP"), + curr_level, new_level, + limit_max_freq, limit_min_freq, limit_min_cpu); + */ + + return 0; +}; + +/* + * pass_rescon_set_level_scope - Change the scope of pass level + * + * @policy: the instance of struct pass_policy + * @new_level: the desirous pass level + * @min_level: the minimum pass level + * @max_level: the maximum pass level + * @data: the PMQoS's data containing the scenario name and lock state + */ +int pass_rescon_set_level_scope(struct pass_policy *policy, int new_level, + int min_level, int max_level, void *data) +{ + if (!policy) + return -EINVAL; + + /* + * FIXME: PMQoS core sends the raw data to the HAL in order to + * support the backwards compatibility. This function call will + * be removed after finding the proper method. + */ + if (data) + pass_set_pmqos_data(to_pass_resource(policy), data); + + if (min_level > max_level) { + _E("min_level(%d) have to be smaller than max_level(%d)\n", + min_level, max_level); + return -EINVAL; + } + + if (min_level == policy->min_level + && max_level == policy->max_level) + return 0; + + /* Change minimum/maximum pass level */ + policy->min_level = min_level; + policy->max_level = max_level; + + pass_rescon_set_level(policy, new_level); + + return 0; +} diff --git a/src/pass/pass-rescon.h b/src/pass/pass-rescon.h new file mode 100644 index 0000000..00bbcce --- /dev/null +++ b/src/pass/pass-rescon.h @@ -0,0 +1,25 @@ +/* + * PASS (Power Aware System Service) Governor + * + * Copyright (c) 2012 - 2017 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the License); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef __PASS_RESCON__ +#define __PASS_RESCON__ + +int pass_rescon_set_level(struct pass_policy *policy, int new_level); +int pass_rescon_set_level_scope(struct pass_policy *policy, int new_level, + int min_level, int max_level, void *data); +#endif /* __PASS_RESCON__ */ -- 2.7.4