From: Lukasz Luba <lukasz.luba@arm.com>
To: Daniel Lezcano <daniel.lezcano@linaro.org>
Cc: linux-pm@vger.kernel.org, quic_manafm@quicinc.com, rafael@kernel.org
Subject: Re: [PATCH v5 3/4] tools/lib/thermal: Add the threshold netlink ABI
Date: Tue, 22 Oct 2024 10:50:33 +0100 [thread overview]
Message-ID: <e7fcd734-53a2-4650-8657-2eadd58fbf92@arm.com> (raw)
In-Reply-To: <b648f0b6-2df3-43ca-880e-a5290d0b8381@linaro.org>
On 10/22/24 08:49, Daniel Lezcano wrote:
> On 21/10/2024 22:47, Lukasz Luba wrote:
>>
>>
>> On 10/14/24 10:43, Daniel Lezcano wrote:
>>> The thermal framework supports the thresholds and allows the userspace
>>> to create, delete, flush, get the list of the thresholds as well as
>>> getting the list of the thresholds set for a specific thermal zone.
>>>
>>> Add the netlink abstraction in the thermal library to take full
>>> advantage of thresholds for the userspace program.
>>>
>>> Signed-off-by: Daniel Lezcano <daniel.lezcano@linaro.org>
>>> ---
>>> tools/lib/thermal/commands.c | 128 +++++++++++++++++++++++++++-
>>> tools/lib/thermal/events.c | 55 +++++++++---
>>> tools/lib/thermal/include/thermal.h | 40 +++++++++
>>> tools/lib/thermal/libthermal.map | 5 ++
>>> tools/lib/thermal/thermal.c | 17 ++++
>>> tools/thermal/lib/Makefile | 2 +-
>>> 6 files changed, 232 insertions(+), 15 deletions(-)
>>>
>>> diff --git a/tools/lib/thermal/commands.c b/tools/lib/thermal/commands.c
>>> index a9223df91dcf..9d5e3e891628 100644
>>> --- a/tools/lib/thermal/commands.c
>>> +++ b/tools/lib/thermal/commands.c
>>> @@ -5,6 +5,7 @@
>>> #include <stdio.h>
>>> #include <stdlib.h>
>>> #include <unistd.h>
>>> +#include <limits.h>
>>> #include <thermal.h>
>>> #include "thermal_nl.h"
>>> @@ -33,6 +34,11 @@ static struct nla_policy
>>> thermal_genl_policy[THERMAL_GENL_ATTR_MAX + 1] = {
>>> [THERMAL_GENL_ATTR_CDEV_CUR_STATE] = { .type = NLA_U32 },
>>> [THERMAL_GENL_ATTR_CDEV_MAX_STATE] = { .type = NLA_U32 },
>>> [THERMAL_GENL_ATTR_CDEV_NAME] = { .type = NLA_STRING },
>>> +
>>> + /* Thresholds */
>>> + [THERMAL_GENL_ATTR_THRESHOLD] = { .type =
>>> NLA_NESTED },
>>> + [THERMAL_GENL_ATTR_THRESHOLD_TEMP] = { .type = NLA_U32 },
>>> + [THERMAL_GENL_ATTR_THRESHOLD_DIRECTION] = { .type = NLA_U32 },
>>> };
>>> static int parse_tz_get(struct genl_info *info, struct thermal_zone
>>> **tz)
>>> @@ -182,6 +188,38 @@ static int parse_tz_get_gov(struct genl_info
>>> *info, struct thermal_zone *tz)
>>> return THERMAL_SUCCESS;
>>> }
>>> +static int parse_threshold_get(struct genl_info *info, struct
>>> thermal_zone *tz)
>>> +{
>>> + struct nlattr *attr;
>>> + struct thermal_threshold *__tt = NULL;
>>> + size_t size = 0;
>>
>> why not simply 'int' ?
>
> Because it is used with realloc where the function definition is:
>
> void *realloc(void *_Nullable ptr, size_t size);
>
> and sizeof() return a size_t type.
>
> So in order to not mix the types, size_t is used which I believe is a
> good practice :)
>
>> also: size=0 which has some impact mentioned below.
>>
>>> + int rem;
>>
>> I would make them a descending order, those lines.
>>
>>> +
>>> + nla_for_each_nested(attr, info-
>>> >attrs[THERMAL_GENL_ATTR_THRESHOLD], rem) {
>>> +
>>> + if (nla_type(attr) == THERMAL_GENL_ATTR_THRESHOLD_TEMP) {
>>> +
>>> + size++;
>>> +
>>> + __tt = realloc(__tt, sizeof(*__tt) * (size + 2));
>>> + if (!__tt)
>>> + return THERMAL_ERROR;
>>> +
>>> + __tt[size - 1].temperature = nla_get_u32(attr);
>>> + }
>>> +
>>> + if (nla_type(attr) == THERMAL_GENL_ATTR_THRESHOLD_DIRECTION)
>>> + __tt[size - 1].direction = nla_get_u32(attr);
>>
>> We probably relay on some order here, because the 'size -1' needs to be
>> done after first 'size++'.
>> If that the case then maybe it's worth a comment. Or if it wasn't
>> intended and there are no strong guarantees, then this needs a fix.
>
> The size contains the size of the array and we want to access the last
> element, size - 1
>
> I will add this sentence above as a comment if it is ok for you
Yes, please add some comment e.g. that size=0 will be then
first modified by the 1st 'if()' so 'size++' will happen
and there is no way that the 2nd 'if()' will trigger before that.
Those 2 'if()' are kind of independent in the code and it's
not obvious from that part of code, why the 2nd 'if()' won't
run at the beginning. The dangerous situation would be:
'__tt[0 - 1].direction = ' assignment, which is due to
'size=0' init value.
>
>>> + }
>>> +
>>> + if (__tt)
>>> + __tt[size].temperature = INT_MAX;
>>> +
>>> + tz->thresholds = __tt;
>>
>> I wonder what would happen to the previous 'tz->thresholds' when
>> we just put new one here... I cannot find other place when it's set.
>>
>> Since we have '*__tt = NULL' then one of the solutions would be
>> to simply call:
>> free(tz->thresholds);
>> tz->thresholds = __tt;
>>
>> Am I missing something, when it might be cleaned in different place?
>
> The caller is supposed to pass a clean empty structure.
>
> Usually, this function is to discover the current configuration, so it
> is a one shot call keeping the structure in memory for the libthermal
> lifecycle.
>
> The events sends updates of the thermal zones. So with the events and
> the initial configuration from the discovery, the userspace is always
> up-to-date with the thermal setup.
So we cannot receive that we have new thresholds?
I thought we will get that information, even in runtime, so the old
memory should be just freed.
>
>
>>> +
>>> + return THERMAL_SUCCESS;
>>> +}
>>> +
>>> static int handle_netlink(struct nl_cache_ops *unused,
>>> struct genl_cmd *cmd,
>>> struct genl_info *info, void *arg)
>>> @@ -210,6 +248,10 @@ static int handle_netlink(struct nl_cache_ops
>>> *unused,
>>> ret = parse_tz_get_gov(info, arg);
>>> break;
>>> + case THERMAL_GENL_CMD_THRESHOLD_GET:
>>> + ret = parse_threshold_get(info, arg);
>>> + break;
>>> +
>>
>> I can see in the kernel part in the funciton:
>> thermal_genl_cmd_doit()
>> that there add, delete, flush also send a response
>> message. Shouldn't be handled here gently, otherwise
>
> No, those are commands and the transaction is done at the netlink level
> to say if the command was successful or not.
Thanks, I see.
>
>>> default:
>>> return THERMAL_ERROR;
>>
>> that 'default' might capture them?
>
> [ ... ]
>
>>> int for_each_thermal_cdev(struct thermal_cdev *cdev, cb_tc_t cb,
>>> void *arg)
>>> {
>>> int i, ret = 0;
>>> @@ -80,6 +94,9 @@ static int __thermal_zone_discover(struct
>>> thermal_zone *tz, void *th)
>>> if (thermal_cmd_get_trip(th, tz) < 0)
>>> return -1;
>>> + if (thermal_cmd_threshold_get(th, tz) < 0)
>>
>> There are only 2 definitions in the enum thermal_error_t.
>> I would just simply checked if it's not 0:
>
>
> Ok
>
> Thanks for the review
>
We're welcome.
next prev parent reply other threads:[~2024-10-22 9:49 UTC|newest]
Thread overview: 26+ messages / expand[flat|nested] mbox.gz Atom feed top
2024-10-14 9:43 [PATCH v5 0/4] Add thermal user thresholds support Daniel Lezcano
2024-10-14 9:43 ` [PATCH v5 1/4] thermal/netlink: Add the commands and the events for the thresholds Daniel Lezcano
2024-10-21 10:58 ` Rafael J. Wysocki
2024-10-21 19:42 ` Lukasz Luba
2024-10-21 19:47 ` Rafael J. Wysocki
2024-10-21 19:51 ` Lukasz Luba
2024-10-21 22:02 ` Lukasz Luba
2024-10-22 7:09 ` Daniel Lezcano
2024-10-22 9:40 ` Lukasz Luba
2024-10-22 10:01 ` Rafael J. Wysocki
2024-10-22 10:20 ` Lukasz Luba
2024-10-14 9:43 ` [PATCH v5 2/4] tools/lib/thermal: Make more generic the command encoding function Daniel Lezcano
2024-10-21 19:49 ` Lukasz Luba
2024-10-22 7:12 ` Daniel Lezcano
2024-10-22 9:43 ` Lukasz Luba
2024-10-14 9:43 ` [PATCH v5 3/4] tools/lib/thermal: Add the threshold netlink ABI Daniel Lezcano
2024-10-21 20:47 ` Lukasz Luba
2024-10-22 7:49 ` Daniel Lezcano
2024-10-22 9:50 ` Lukasz Luba [this message]
2024-10-22 13:21 ` Daniel Lezcano
2024-10-14 9:43 ` [PATCH v5 4/4] tools/thermal/thermal-engine: Take into account the thresholds API Daniel Lezcano
2024-10-21 20:10 ` Lukasz Luba
2024-10-22 7:52 ` Daniel Lezcano
2024-10-21 8:28 ` [PATCH v5 0/4] Add thermal user thresholds support Daniel Lezcano
2024-10-21 8:43 ` Lukasz Luba
2024-10-21 11:02 ` Rafael J. Wysocki
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=e7fcd734-53a2-4650-8657-2eadd58fbf92@arm.com \
--to=lukasz.luba@arm.com \
--cc=daniel.lezcano@linaro.org \
--cc=linux-pm@vger.kernel.org \
--cc=quic_manafm@quicinc.com \
--cc=rafael@kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox