1 /*
2  * Arm SCP/MCP Software
3  * Copyright (c) 2022-2023, Arm Limited and Contributors. All rights reserved.
4  *
5  * SPDX-License-Identifier: BSD-3-Clause
6  */
7 
8 #ifndef MOD_THERMAL_MGMT_H
9 #define MOD_THERMAL_MGMT_H
10 
11 #include <fwk_element.h>
12 #include <fwk_id.h>
13 #include <fwk_module_idx.h>
14 
15 #include <stdint.h>
16 
17 /*!
18  * \ingroup GroupModules
19  * \defgroup GroupThermal Thermal Management
20  *
21  * \details Module for controlling/limiting the Performance of a platform based
22  *      on thermal input.
23  *
24  * \{
25  */
26 
27 /*!
28  * \brief Number of defined APIs for Thermal Management Module.
29  */
30 enum mod_thermal_api_idx {
31     /*!
32      * \brief Performance Update API index.
33      *
34      * \note This API implements the ::perf_plugins_api interface.
35      */
36     MOD_THERMAL_API_PERF_UPDATE_IDX,
37 
38     MOD_THERMAL_API_COUNT,
39 };
40 
41 /*!
42  * \brief Thermal Mgmt activity factor configuration.
43  *
44  * \details Configuration structure for activity factor.
45  */
46 struct mod_thermal_mgmt_activity_factor_config {
47     /*! Activity factor driver identifier */
48     fwk_id_t driver_id;
49 
50     /*! Activity factor driver API identifier */
51     fwk_id_t driver_api_id;
52 };
53 
54 /*!
55  * \brief Thermal Mgmt actors configuration.
56  *
57  * \details Configuration structure for individual thermal actors.
58  *      Please refer to the doc section for further details.
59  */
60 struct mod_thermal_mgmt_actor_config {
61     /*! Element identifier of the corresponding power model */
62     fwk_id_t driver_id;
63 
64     /*! Corresponding DVFS Element identifier for this device */
65     fwk_id_t dvfs_domain_id;
66 
67     /*!
68      * \brief Weight coefficient for power distribution.
69      *
70      * \details Its value can be any. It expresses the relative weight to other
71      *      devices.
72      */
73     uint16_t weight;
74 
75     /*! Activity factor configuration */
76     struct mod_thermal_mgmt_activity_factor_config *activity_factor;
77 };
78 
79 /*!
80  * \brief Thermal Mgmt protection configuration.
81  *
82  * \details Configuration structure for thermal protection.
83  */
84 struct mod_thermal_mgmt_protection_config {
85     /*! Thermal protection driver identifier */
86     fwk_id_t driver_id;
87 
88     /*! Thermal protection driver API identifier*/
89     fwk_id_t driver_api_id;
90 
91     /*!
92      * \brief Warning temperature value threshold.
93      *
94      * \details Warning temperature threshold value that activates the thermal
95      *      protection. The corresponding callback is invoked when the
96      *      temperature is above the threshold.
97      */
98     uint32_t warn_temp_threshold;
99 
100     /*!
101      * \brief Critical temperature threshold value.
102      *
103      * \details Critical temperature threshold value that activates the thermal
104      *      protection. It is expected that `warn_temp_threshold` >
105      *      `crit_temp_threshold`. The corresponding callback is invoked when
106      *      the temperature is above the threshold.
107      */
108     uint32_t crit_temp_threshold;
109 };
110 
111 /*!
112  * \brief Thermal Mgmt device configuration.
113  *
114  * \details Configuration structure for individual thermal devices.
115  *      Please refer to the doc section for further details.
116  */
117 struct mod_thermal_mgmt_dev_config {
118     /*!
119      * \brief Slow loop multiplier.
120      *
121      * \details The slow loop time interval is derived as follow:
122      *      slow_loop_period = slow_loop_mult * perf_update_period.
123      */
124     unsigned int slow_loop_mult;
125 
126     /*! The thermal design power (TDP) for all the devices being controlled */
127     uint16_t tdp;
128 
129     /*! The cold state power */
130     uint16_t cold_state_power;
131 
132     /*!
133      * \brief Switch-on temperature threshold.
134      *
135      * \details The temperature above which the PID loop runs. Below this
136      *      threshold the power is allocated only on bias coefficients.
137      */
138     struct {
139         /*!
140          * \brief Switch-on temperature threshold.
141          *
142          * \details The temperature above which the PID loop runs. Below this
143          *      threshold the power is allocated only on bias coefficients.
144          */
145         uint32_t switch_on_temperature;
146 
147         /*!
148          * \brief Control temperature
149          *
150          * \details The temperature that the system will achive once stabilised.
151          *      Due to the PID nature of the controller, some
152          *      overshoot/undershoot may occur. Note that the controller can
153          *      only limit the temperature by placing a limit to the power to
154          *      the heat source. It has no direct control on the heat source
155          *      itself and therefore only the upper limit can be controlled.
156          */
157         uint32_t control_temperature;
158 
159         /*!
160          * \brief Integral cut-off threshold.
161          *
162          * \details Below this value the errors are accumulated. This is useful
163          *      to avoid accumulating errors when the temperature is below the
164          *      target.
165          */
166         int32_t integral_cutoff;
167 
168         /*!
169          * \brief Integral maximum.
170          *
171          * \details This is the upper limit the accumulated errors.
172          */
173         int32_t integral_max;
174 
175         /*! Proportional term when undershooting (PID loop)*/
176         int32_t k_p_undershoot;
177 
178         /*! Proportional term when overhooting (PID loop) */
179         int32_t k_p_overshoot;
180 
181         /*! Integral term (PID loop) */
182         int32_t k_integral;
183 
184         /*! Derivative term (PID loop) */
185         int32_t k_derivative;
186     } pid_controller;
187 
188     /*! Temperature sensor identifier */
189     fwk_id_t sensor_id;
190 
191     /*!
192      * \brief Thermal protection configuration.
193      *
194      * \details It is an optional feature. If it is left NULL it will not
195      *      operate.
196      */
197     struct mod_thermal_mgmt_protection_config *temp_protection;
198 
199     /*! Power Model API identifier */
200     fwk_id_t driver_api_id;
201 
202     /*! Thermal actors lookup table */
203     struct mod_thermal_mgmt_actor_config *thermal_actors_table;
204 
205     /*!
206      * \brief The number of actors in the thermal actors lookup table.
207      *
208      * \details If it is left zero it will not run the PID controller and power
209      *      distribution will not take place.
210      */
211     uint32_t thermal_actors_count;
212 };
213 
214 /*!
215  * \brief Power Model API.
216  *
217  * \details This API must be implemented by the platform.
218  */
219 struct mod_thermal_mgmt_driver_api {
220     /*!
221      * \brief Performance Level to Power conversion.
222      *
223      * \details Convert a performance level into its corresponding power usage.
224      *
225      * \param domain_id Specific power model device id.
226      * \param level Performance level
227      *
228      * \retval power The corresponding power for a given performance level.
229      */
230     uint32_t (*level_to_power)(fwk_id_t domain_id, const uint32_t level);
231 
232     /*!
233      * \brief Power to Performance Level conversion.
234      *
235      * \details Convert a power usage into its corresponding performance level.
236      *
237      * \param domain_id Specific power model device id.
238      * \param power Power
239      *
240      * \retval level The corresponding performance level for a given power.
241      */
242     uint32_t (*power_to_level)(fwk_id_t domain_id, const uint32_t power);
243 };
244 
245 /*!
246  * \brief Thermal management temperature protection API.
247  *
248  * \ details This API must be implemented by the platform.
249  */
250 struct mod_thermal_mgmt_protection_api {
251     /*!
252      * \brief Thermal protection warning alarm callback.
253      *
254      * \details Informs once every time the temperature exceeds
255      *      `warn_temp_threshold` value. The periodicity of this callback
256      *      is not more often than `slow_loop_mult`.
257      *
258      * \param driver_id Specific driver identifier.
259      * \param thermal_id Specific thermal management controller device
260      *      identifier.
261      */
262     void (*warning)(fwk_id_t driver_id, fwk_id_t thermal_id);
263 
264     /*!
265      * \brief Thermal protection critical alarm callback.
266      *
267      * \details Informs once every time the temperature exceeds
268      *      `crit_temp_threshold` value. The periodicity of this callback
269      *      is not more often than `slow_loop_mult`.
270      *
271      * \param driver_id Specific driver identifier.
272      * \param thermal_id Specific thermal management controller device
273      *      identifier.
274      */
275     void (*critical)(fwk_id_t driver_id, fwk_id_t thermal_id);
276 };
277 
278 /*!
279  * \brief Activity counter API.
280  *
281  * \details This API must be implemented by the platform.
282  */
283 struct mod_thermal_mgmt_activity_factor_api {
284     /*!
285      * \brief Gets activity factor from the specified domain.
286      *
287      * \details Activity factor is referred to the corresponding actor and
288      *      implemented by the platform. It must return a 10 bits
289      *      resolution value (0-1023) where 0 corresponds to a complete
290      *      inactivity and 1023 to 100% activity.
291      *
292      * \param domain_id Specific device id.
293      * \param[out] activity activity factor normalized to 10 bits.
294      *
295      * \retval ::FWK_E_PARAM One or more parameters were invalid.
296      * \retval ::FWK_SUCCESS The operation succeeded.
297      *
298      * \return Status code representing the result of the operation.
299      */
300     int (*get_activity_factor)(fwk_id_t domain_id, uint16_t *activity);
301 };
302 
303 /*!
304  * \}
305  */
306 
307 #endif /* MOD_THERMAL_MGMT_H */
308