Message ID | 20210703005416.2668319-2-bjorn.andersson@linaro.org |
---|---|
State | Accepted |
Commit | d43b3a989bc8c06fd4bbb69a7500d180db2d68e8 |
Headers | show |
Series | soc: qcom: rpmhpd: Improve rpmhpd enable handling | expand |
On 7/3/2021 6:24 AM, Bjorn Andersson wrote: > rpmhpd_aggregate_corner() takes a corner as parameter, but in > rpmhpd_power_off() the code requests the level of the first corner > instead. > > In all (known) current cases the first corner has level 0, so this > change should be a nop, but in case that there's a power domain with a > non-zero lowest level this makes sure that rpmhpd_power_off() actually > requests the lowest level - which is the closest to "power off" we can > get. > > While touching the code, also skip the unnecessary zero-initialization > of "ret". > > Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") > Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> > --- > drivers/soc/qcom/rpmhpd.c | 5 ++--- > 1 file changed, 2 insertions(+), 3 deletions(-) > > diff --git a/drivers/soc/qcom/rpmhpd.c b/drivers/soc/qcom/rpmhpd.c > index 2daa17ba54a3..fa209b479ab3 100644 > --- a/drivers/soc/qcom/rpmhpd.c > +++ b/drivers/soc/qcom/rpmhpd.c > @@ -403,12 +403,11 @@ static int rpmhpd_power_on(struct generic_pm_domain *domain) > static int rpmhpd_power_off(struct generic_pm_domain *domain) > { > struct rpmhpd *pd = domain_to_rpmhpd(domain); > - int ret = 0; > + int ret; > > mutex_lock(&rpmhpd_lock); > > - ret = rpmhpd_aggregate_corner(pd, pd->level[0]); > - > + ret = rpmhpd_aggregate_corner(pd, 0); This won't work for cases where pd->level[0] != 0, rpmh would just ignore this and keep the resource at whatever corner it was previously at. (unless command DB tells you a 0 is 'valid' for a resource, sending a 0 is a nop) The right thing to do is to send in whatever command DB tells you is the lowest level that's valid, which is pd->level[0]. > if (!ret) > pd->enabled = false; > > -- QUALCOMM INDIA, on behalf of Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by The Linux Foundation
On Sun, Jul 4, 2021 at 11:27 PM Rajendra Nayak <rnayak@codeaurora.org> wrote: > > > > On 7/3/2021 6:24 AM, Bjorn Andersson wrote: > > rpmhpd_aggregate_corner() takes a corner as parameter, but in > > rpmhpd_power_off() the code requests the level of the first corner > > instead. > > > > In all (known) current cases the first corner has level 0, so this > > change should be a nop, but in case that there's a power domain with a > > non-zero lowest level this makes sure that rpmhpd_power_off() actually > > requests the lowest level - which is the closest to "power off" we can > > get. > > > > While touching the code, also skip the unnecessary zero-initialization > > of "ret". > > > > Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") > > Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> > > --- > > drivers/soc/qcom/rpmhpd.c | 5 ++--- > > 1 file changed, 2 insertions(+), 3 deletions(-) > > > > diff --git a/drivers/soc/qcom/rpmhpd.c b/drivers/soc/qcom/rpmhpd.c > > index 2daa17ba54a3..fa209b479ab3 100644 > > --- a/drivers/soc/qcom/rpmhpd.c > > +++ b/drivers/soc/qcom/rpmhpd.c > > @@ -403,12 +403,11 @@ static int rpmhpd_power_on(struct generic_pm_domain *domain) > > static int rpmhpd_power_off(struct generic_pm_domain *domain) > > { > > struct rpmhpd *pd = domain_to_rpmhpd(domain); > > - int ret = 0; > > + int ret; > > > > mutex_lock(&rpmhpd_lock); > > > > - ret = rpmhpd_aggregate_corner(pd, pd->level[0]); > > - > > + ret = rpmhpd_aggregate_corner(pd, 0); > > This won't work for cases where pd->level[0] != 0, rpmh would just ignore this and keep the > resource at whatever corner it was previously at. > (unless command DB tells you a 0 is 'valid' for a resource, sending a 0 is a nop) > The right thing to do is to send in whatever command DB tells you is the lowest level that's valid, > which is pd->level[0]. > I'm afraid this doesn't make sense to me. In rpmh_power_on() if cmd-db tells us that we have [0, 64, ...] and we request 64 we rpmhpd_aggregate_corner(pd, 1); but in power off, if cmd-db would provide [64, ...] we would end up sending rpmhpd_aggregate_corner(pd, 64); So in power_on we request the corner (i.e. index in the array provided in cmd-db) and in power-off the same function takes the level? Can you please help me understand what the actual number we're supposed to send to the RPMh is? Is it numbers in the range [0-15] or is it numbers such as {0, 64, 128, ...}? Afaict it's the prior (i.e. [0-15]), as this is what we currently do in both power_on and set_performance_state, and it happens to be what we send in power_off as long as the first level from cmd-db is 0. Regards, Bjorn > > > if (!ret) > > pd->enabled = false; > > > > > > -- > QUALCOMM INDIA, on behalf of Qualcomm Innovation Center, Inc. is a member > of Code Aurora Forum, hosted by The Linux Foundation
On 7/5/2021 10:36 AM, Bjorn Andersson wrote: > On Sun, Jul 4, 2021 at 11:27 PM Rajendra Nayak <rnayak@codeaurora.org> wrote: >> >> >> >> On 7/3/2021 6:24 AM, Bjorn Andersson wrote: >>> rpmhpd_aggregate_corner() takes a corner as parameter, but in >>> rpmhpd_power_off() the code requests the level of the first corner >>> instead. >>> >>> In all (known) current cases the first corner has level 0, so this >>> change should be a nop, but in case that there's a power domain with a >>> non-zero lowest level this makes sure that rpmhpd_power_off() actually >>> requests the lowest level - which is the closest to "power off" we can >>> get. >>> >>> While touching the code, also skip the unnecessary zero-initialization >>> of "ret". >>> >>> Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") >>> Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> >>> --- >>> drivers/soc/qcom/rpmhpd.c | 5 ++--- >>> 1 file changed, 2 insertions(+), 3 deletions(-) >>> >>> diff --git a/drivers/soc/qcom/rpmhpd.c b/drivers/soc/qcom/rpmhpd.c >>> index 2daa17ba54a3..fa209b479ab3 100644 >>> --- a/drivers/soc/qcom/rpmhpd.c >>> +++ b/drivers/soc/qcom/rpmhpd.c >>> @@ -403,12 +403,11 @@ static int rpmhpd_power_on(struct generic_pm_domain *domain) >>> static int rpmhpd_power_off(struct generic_pm_domain *domain) >>> { >>> struct rpmhpd *pd = domain_to_rpmhpd(domain); >>> - int ret = 0; >>> + int ret; >>> >>> mutex_lock(&rpmhpd_lock); >>> >>> - ret = rpmhpd_aggregate_corner(pd, pd->level[0]); >>> - >>> + ret = rpmhpd_aggregate_corner(pd, 0); >> >> This won't work for cases where pd->level[0] != 0, rpmh would just ignore this and keep the >> resource at whatever corner it was previously at. >> (unless command DB tells you a 0 is 'valid' for a resource, sending a 0 is a nop) >> The right thing to do is to send in whatever command DB tells you is the lowest level that's valid, >> which is pd->level[0]. >> > > I'm afraid this doesn't make sense to me. > > In rpmh_power_on() if cmd-db tells us that we have [0, 64, ...] and we > request 64 we rpmhpd_aggregate_corner(pd, 1); but in power off, if > cmd-db would provide [64, ...] we would end up sending > rpmhpd_aggregate_corner(pd, 64); > So in power_on we request the corner (i.e. index in the array provided > in cmd-db) and in power-off the same function takes the level? ah that's right, I did not read the commit log properly and got confused. Looks like this bug existed from the day this driver for merged :/, thanks for catching it. Does it make sense to also mark this fix for stable? > > Can you please help me understand what the actual number we're > supposed to send to the RPMh is? Is it numbers in the range [0-15] or > is it numbers such as {0, 64, 128, ...}? > > Afaict it's the prior (i.e. [0-15]), as this is what we currently do > in both power_on and set_performance_state, and it happens to be what > we send in power_off as long as the first level from cmd-db is 0. > > Regards, > Bjorn > >> >>> if (!ret) >>> pd->enabled = false; >>> >>> >> >> -- >> QUALCOMM INDIA, on behalf of Qualcomm Innovation Center, Inc. is a member >> of Code Aurora Forum, hosted by The Linux Foundation -- QUALCOMM INDIA, on behalf of Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by The Linux Foundation
On Mon 05 Jul 00:40 CDT 2021, Rajendra Nayak wrote: > On 7/5/2021 10:36 AM, Bjorn Andersson wrote: > > On Sun, Jul 4, 2021 at 11:27 PM Rajendra Nayak <rnayak@codeaurora.org> wrote: > > > > > > > > > > > > On 7/3/2021 6:24 AM, Bjorn Andersson wrote: > > > > rpmhpd_aggregate_corner() takes a corner as parameter, but in > > > > rpmhpd_power_off() the code requests the level of the first corner > > > > instead. > > > > > > > > In all (known) current cases the first corner has level 0, so this > > > > change should be a nop, but in case that there's a power domain with a > > > > non-zero lowest level this makes sure that rpmhpd_power_off() actually > > > > requests the lowest level - which is the closest to "power off" we can > > > > get. > > > > > > > > While touching the code, also skip the unnecessary zero-initialization > > > > of "ret". > > > > > > > > Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") > > > > Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> > > > > --- > > > > drivers/soc/qcom/rpmhpd.c | 5 ++--- > > > > 1 file changed, 2 insertions(+), 3 deletions(-) > > > > > > > > diff --git a/drivers/soc/qcom/rpmhpd.c b/drivers/soc/qcom/rpmhpd.c > > > > index 2daa17ba54a3..fa209b479ab3 100644 > > > > --- a/drivers/soc/qcom/rpmhpd.c > > > > +++ b/drivers/soc/qcom/rpmhpd.c > > > > @@ -403,12 +403,11 @@ static int rpmhpd_power_on(struct generic_pm_domain *domain) > > > > static int rpmhpd_power_off(struct generic_pm_domain *domain) > > > > { > > > > struct rpmhpd *pd = domain_to_rpmhpd(domain); > > > > - int ret = 0; > > > > + int ret; > > > > > > > > mutex_lock(&rpmhpd_lock); > > > > > > > > - ret = rpmhpd_aggregate_corner(pd, pd->level[0]); > > > > - > > > > + ret = rpmhpd_aggregate_corner(pd, 0); > > > > > > This won't work for cases where pd->level[0] != 0, rpmh would just ignore this and keep the > > > resource at whatever corner it was previously at. > > > (unless command DB tells you a 0 is 'valid' for a resource, sending a 0 is a nop) > > > The right thing to do is to send in whatever command DB tells you is the lowest level that's valid, > > > which is pd->level[0]. > > > > > > > I'm afraid this doesn't make sense to me. > > > > In rpmh_power_on() if cmd-db tells us that we have [0, 64, ...] and we > > request 64 we rpmhpd_aggregate_corner(pd, 1); but in power off, if > > cmd-db would provide [64, ...] we would end up sending > > rpmhpd_aggregate_corner(pd, 64); > > So in power_on we request the corner (i.e. index in the array provided > > in cmd-db) and in power-off the same function takes the level? > > ah that's right, I did not read the commit log properly and got confused. Thanks for confirming my understanding. > Looks like this bug existed from the day this driver for merged :/, thanks > for catching it. > Does it make sense to also mark this fix for stable? > I can certainly add a Cc: stable@ as I'm applying this. May I have your R-b? PS. Do you have any input on patch 2/2? That actually solves a practical problem we're seeing. Would it perhaps aid in your need for the new "assigned-opp-level" property? Regards, Bjorn
On 7/7/2021 10:19 AM, Bjorn Andersson wrote: > On Mon 05 Jul 00:40 CDT 2021, Rajendra Nayak wrote: >> On 7/5/2021 10:36 AM, Bjorn Andersson wrote: >>> On Sun, Jul 4, 2021 at 11:27 PM Rajendra Nayak <rnayak@codeaurora.org> wrote: >>>> >>>> >>>> >>>> On 7/3/2021 6:24 AM, Bjorn Andersson wrote: >>>>> rpmhpd_aggregate_corner() takes a corner as parameter, but in >>>>> rpmhpd_power_off() the code requests the level of the first corner >>>>> instead. >>>>> >>>>> In all (known) current cases the first corner has level 0, so this >>>>> change should be a nop, but in case that there's a power domain with a >>>>> non-zero lowest level this makes sure that rpmhpd_power_off() actually >>>>> requests the lowest level - which is the closest to "power off" we can >>>>> get. >>>>> >>>>> While touching the code, also skip the unnecessary zero-initialization >>>>> of "ret". >>>>> >>>>> Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") >>>>> Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> >>>>> --- >>>>> drivers/soc/qcom/rpmhpd.c | 5 ++--- >>>>> 1 file changed, 2 insertions(+), 3 deletions(-) >>>>> >>>>> diff --git a/drivers/soc/qcom/rpmhpd.c b/drivers/soc/qcom/rpmhpd.c >>>>> index 2daa17ba54a3..fa209b479ab3 100644 >>>>> --- a/drivers/soc/qcom/rpmhpd.c >>>>> +++ b/drivers/soc/qcom/rpmhpd.c >>>>> @@ -403,12 +403,11 @@ static int rpmhpd_power_on(struct generic_pm_domain *domain) >>>>> static int rpmhpd_power_off(struct generic_pm_domain *domain) >>>>> { >>>>> struct rpmhpd *pd = domain_to_rpmhpd(domain); >>>>> - int ret = 0; >>>>> + int ret; >>>>> >>>>> mutex_lock(&rpmhpd_lock); >>>>> >>>>> - ret = rpmhpd_aggregate_corner(pd, pd->level[0]); >>>>> - >>>>> + ret = rpmhpd_aggregate_corner(pd, 0); >>>> >>>> This won't work for cases where pd->level[0] != 0, rpmh would just ignore this and keep the >>>> resource at whatever corner it was previously at. >>>> (unless command DB tells you a 0 is 'valid' for a resource, sending a 0 is a nop) >>>> The right thing to do is to send in whatever command DB tells you is the lowest level that's valid, >>>> which is pd->level[0]. >>>> >>> >>> I'm afraid this doesn't make sense to me. >>> >>> In rpmh_power_on() if cmd-db tells us that we have [0, 64, ...] and we >>> request 64 we rpmhpd_aggregate_corner(pd, 1); but in power off, if >>> cmd-db would provide [64, ...] we would end up sending >>> rpmhpd_aggregate_corner(pd, 64); >>> So in power_on we request the corner (i.e. index in the array provided >>> in cmd-db) and in power-off the same function takes the level? >> >> ah that's right, I did not read the commit log properly and got confused. > > Thanks for confirming my understanding. > >> Looks like this bug existed from the day this driver for merged :/, thanks >> for catching it. >> Does it make sense to also mark this fix for stable? >> > > I can certainly add a Cc: stable@ as I'm applying this. sure, sounds good > May I have your R-b? Reviewed-by: Rajendra Nayak <rnayak@codeaurora.org> > > PS. Do you have any input on patch 2/2? That actually solves a practical > problem we're seeing. Would it perhaps aid in your need for the new > "assigned-opp-level" property? We would perhaps still need the 'assigned-opp-level' or equivalent since the default requirement of devices is not always the least level supported, in some cases it might be slightly higher corner which would then need to be set explicitly. I was hoping on getting some more testing done with that patch especially for any regression on the sc7180 and sc7280 devices, which I haven't got to yet. Are you getting these patches ready for merge for the -rc cycle or for the next merge window? -- QUALCOMM INDIA, on behalf of Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by The Linux Foundation
On Wed 07 Jul 01:31 CDT 2021, Rajendra Nayak wrote: > > > On 7/7/2021 10:19 AM, Bjorn Andersson wrote: > > On Mon 05 Jul 00:40 CDT 2021, Rajendra Nayak wrote: > > > On 7/5/2021 10:36 AM, Bjorn Andersson wrote: > > > > On Sun, Jul 4, 2021 at 11:27 PM Rajendra Nayak <rnayak@codeaurora.org> wrote: > > > > > > > > > > > > > > > > > > > > On 7/3/2021 6:24 AM, Bjorn Andersson wrote: > > > > > > rpmhpd_aggregate_corner() takes a corner as parameter, but in > > > > > > rpmhpd_power_off() the code requests the level of the first corner > > > > > > instead. > > > > > > > > > > > > In all (known) current cases the first corner has level 0, so this > > > > > > change should be a nop, but in case that there's a power domain with a > > > > > > non-zero lowest level this makes sure that rpmhpd_power_off() actually > > > > > > requests the lowest level - which is the closest to "power off" we can > > > > > > get. > > > > > > > > > > > > While touching the code, also skip the unnecessary zero-initialization > > > > > > of "ret". > > > > > > > > > > > > Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") > > > > > > Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> > > > > > > --- > > > > > > drivers/soc/qcom/rpmhpd.c | 5 ++--- > > > > > > 1 file changed, 2 insertions(+), 3 deletions(-) > > > > > > > > > > > > diff --git a/drivers/soc/qcom/rpmhpd.c b/drivers/soc/qcom/rpmhpd.c > > > > > > index 2daa17ba54a3..fa209b479ab3 100644 > > > > > > --- a/drivers/soc/qcom/rpmhpd.c > > > > > > +++ b/drivers/soc/qcom/rpmhpd.c > > > > > > @@ -403,12 +403,11 @@ static int rpmhpd_power_on(struct generic_pm_domain *domain) > > > > > > static int rpmhpd_power_off(struct generic_pm_domain *domain) > > > > > > { > > > > > > struct rpmhpd *pd = domain_to_rpmhpd(domain); > > > > > > - int ret = 0; > > > > > > + int ret; > > > > > > > > > > > > mutex_lock(&rpmhpd_lock); > > > > > > > > > > > > - ret = rpmhpd_aggregate_corner(pd, pd->level[0]); > > > > > > - > > > > > > + ret = rpmhpd_aggregate_corner(pd, 0); > > > > > > > > > > This won't work for cases where pd->level[0] != 0, rpmh would just ignore this and keep the > > > > > resource at whatever corner it was previously at. > > > > > (unless command DB tells you a 0 is 'valid' for a resource, sending a 0 is a nop) > > > > > The right thing to do is to send in whatever command DB tells you is the lowest level that's valid, > > > > > which is pd->level[0]. > > > > > > > > > > > > > I'm afraid this doesn't make sense to me. > > > > > > > > In rpmh_power_on() if cmd-db tells us that we have [0, 64, ...] and we > > > > request 64 we rpmhpd_aggregate_corner(pd, 1); but in power off, if > > > > cmd-db would provide [64, ...] we would end up sending > > > > rpmhpd_aggregate_corner(pd, 64); > > > > So in power_on we request the corner (i.e. index in the array provided > > > > in cmd-db) and in power-off the same function takes the level? > > > > > > ah that's right, I did not read the commit log properly and got confused. > > > > Thanks for confirming my understanding. > > > > > Looks like this bug existed from the day this driver for merged :/, thanks > > > for catching it. > > > Does it make sense to also mark this fix for stable? > > > > > > > I can certainly add a Cc: stable@ as I'm applying this. > > sure, sounds good > > May I have your R-b? > > Reviewed-by: Rajendra Nayak <rnayak@codeaurora.org> > Thank you. > > > > PS. Do you have any input on patch 2/2? That actually solves a practical > > problem we're seeing. Would it perhaps aid in your need for the new > > "assigned-opp-level" property? > > We would perhaps still need the 'assigned-opp-level' or equivalent since > the default requirement of devices is not always the least level supported, > in some cases it might be slightly higher corner which would then need to > be set explicitly. > Right, for situations where we use assign-clock-rates to drive up the clock rate this mechanism might be needed in order to keep things stable. But I presume as soon as you have some sort of dynamic nature to that you'll be back to an opp-table and the means we already have. > I was hoping on getting some more testing done with that patch especially for > any regression on the sc7180 and sc7280 devices, which I haven't got to yet. > Are you getting these patches ready for merge for the -rc cycle or for the > next merge window? > That would be much appreciated, I've not done extensive testing myself, mostly just booted a few different boards. But I would like to see us correct the MDSS_GDSC->MMCX setup in time for v5.15, in particular since we have a few new users of the mmcx power-domain-regulator arriving in this cycle. Regards, Bjorn
On 07/07/2021 18:48, Bjorn Andersson wrote: > On Wed 07 Jul 01:31 CDT 2021, Rajendra Nayak wrote: > >> >> >> On 7/7/2021 10:19 AM, Bjorn Andersson wrote: >>> On Mon 05 Jul 00:40 CDT 2021, Rajendra Nayak wrote: >>>> On 7/5/2021 10:36 AM, Bjorn Andersson wrote: >>>>> On Sun, Jul 4, 2021 at 11:27 PM Rajendra Nayak <rnayak@codeaurora.org> wrote: >>>>>> >>>>>> >>>>>> >>>>>> On 7/3/2021 6:24 AM, Bjorn Andersson wrote: >>>>>>> rpmhpd_aggregate_corner() takes a corner as parameter, but in >>>>>>> rpmhpd_power_off() the code requests the level of the first corner >>>>>>> instead. >>>>>>> >>>>>>> In all (known) current cases the first corner has level 0, so this >>>>>>> change should be a nop, but in case that there's a power domain with a >>>>>>> non-zero lowest level this makes sure that rpmhpd_power_off() actually >>>>>>> requests the lowest level - which is the closest to "power off" we can >>>>>>> get. >>>>>>> >>>>>>> While touching the code, also skip the unnecessary zero-initialization >>>>>>> of "ret". >>>>>>> >>>>>>> Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") >>>>>>> Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> >>>>>>> --- >>>>>>> drivers/soc/qcom/rpmhpd.c | 5 ++--- >>>>>>> 1 file changed, 2 insertions(+), 3 deletions(-) >>>>>>> >>>>>>> diff --git a/drivers/soc/qcom/rpmhpd.c b/drivers/soc/qcom/rpmhpd.c >>>>>>> index 2daa17ba54a3..fa209b479ab3 100644 >>>>>>> --- a/drivers/soc/qcom/rpmhpd.c >>>>>>> +++ b/drivers/soc/qcom/rpmhpd.c >>>>>>> @@ -403,12 +403,11 @@ static int rpmhpd_power_on(struct generic_pm_domain *domain) >>>>>>> static int rpmhpd_power_off(struct generic_pm_domain *domain) >>>>>>> { >>>>>>> struct rpmhpd *pd = domain_to_rpmhpd(domain); >>>>>>> - int ret = 0; >>>>>>> + int ret; >>>>>>> >>>>>>> mutex_lock(&rpmhpd_lock); >>>>>>> >>>>>>> - ret = rpmhpd_aggregate_corner(pd, pd->level[0]); >>>>>>> - >>>>>>> + ret = rpmhpd_aggregate_corner(pd, 0); >>>>>> >>>>>> This won't work for cases where pd->level[0] != 0, rpmh would just ignore this and keep the >>>>>> resource at whatever corner it was previously at. >>>>>> (unless command DB tells you a 0 is 'valid' for a resource, sending a 0 is a nop) >>>>>> The right thing to do is to send in whatever command DB tells you is the lowest level that's valid, >>>>>> which is pd->level[0]. >>>>>> >>>>> >>>>> I'm afraid this doesn't make sense to me. >>>>> >>>>> In rpmh_power_on() if cmd-db tells us that we have [0, 64, ...] and we >>>>> request 64 we rpmhpd_aggregate_corner(pd, 1); but in power off, if >>>>> cmd-db would provide [64, ...] we would end up sending >>>>> rpmhpd_aggregate_corner(pd, 64); >>>>> So in power_on we request the corner (i.e. index in the array provided >>>>> in cmd-db) and in power-off the same function takes the level? >>>> >>>> ah that's right, I did not read the commit log properly and got confused. >>> >>> Thanks for confirming my understanding. >>> >>>> Looks like this bug existed from the day this driver for merged :/, thanks >>>> for catching it. >>>> Does it make sense to also mark this fix for stable? >>>> >>> >>> I can certainly add a Cc: stable@ as I'm applying this. >> >> sure, sounds good >>> May I have your R-b? >> >> Reviewed-by: Rajendra Nayak <rnayak@codeaurora.org> >> > > Thank you. > >>> >>> PS. Do you have any input on patch 2/2? That actually solves a practical >>> problem we're seeing. Would it perhaps aid in your need for the new >>> "assigned-opp-level" property? >> >> We would perhaps still need the 'assigned-opp-level' or equivalent since >> the default requirement of devices is not always the least level supported, >> in some cases it might be slightly higher corner which would then need to >> be set explicitly. >> > > Right, for situations where we use assign-clock-rates to drive up the > clock rate this mechanism might be needed in order to keep things > stable. > > But I presume as soon as you have some sort of dynamic nature to that > you'll be back to an opp-table and the means we already have. > >> I was hoping on getting some more testing done with that patch especially for >> any regression on the sc7180 and sc7280 devices, which I haven't got to yet. >> Are you getting these patches ready for merge for the -rc cycle or for the >> next merge window? >> > > That would be much appreciated, I've not done extensive testing myself, > mostly just booted a few different boards. > > But I would like to see us correct the MDSS_GDSC->MMCX setup in time for > v5.15, in particular since we have a few new users of the mmcx > power-domain-regulator arriving in this cycle. I will rebase my patches on top of this patch series and submit soon. -- With best wishes Dmitry
Quoting Bjorn Andersson (2021-07-02 17:54:15) > rpmhpd_aggregate_corner() takes a corner as parameter, but in > rpmhpd_power_off() the code requests the level of the first corner > instead. > > In all (known) current cases the first corner has level 0, so this > change should be a nop, but in case that there's a power domain with a > non-zero lowest level this makes sure that rpmhpd_power_off() actually > requests the lowest level - which is the closest to "power off" we can > get. > > While touching the code, also skip the unnecessary zero-initialization > of "ret". > > Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") > Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> > --- I think this is why qcom folks talk about "virtual corner" and "physical corner" because there's the one in command DB and the one in hardware. Maybe we should change rpmhpd_aggregate_corner() to call the argument 'vcorner'? Unfortunately we can't really build a type system here to make this problem easy to catch with a mismatched type, unless there's some sort of typedef trick we can play? Reviewed-by: Stephen Boyd <swboyd@chromium.org>
On Wed 07 Jul 19:21 CDT 2021, Stephen Boyd wrote: > Quoting Bjorn Andersson (2021-07-02 17:54:15) > > rpmhpd_aggregate_corner() takes a corner as parameter, but in > > rpmhpd_power_off() the code requests the level of the first corner > > instead. > > > > In all (known) current cases the first corner has level 0, so this > > change should be a nop, but in case that there's a power domain with a > > non-zero lowest level this makes sure that rpmhpd_power_off() actually > > requests the lowest level - which is the closest to "power off" we can > > get. > > > > While touching the code, also skip the unnecessary zero-initialization > > of "ret". > > > > Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") > > Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> > > --- > > I think this is why qcom folks talk about "virtual corner" and "physical > corner" because there's the one in command DB and the one in hardware. I think the driver uses "level" and "corner" to denote the two different number spaces, so I think we're good...now that we after this patch don't pass a "level" as "corner" during power_off ;) > Maybe we should change rpmhpd_aggregate_corner() to call the argument > 'vcorner'? So "virtual corner" is "corner" and "physical corner" is level? I.e. 256 is a "physical corner"? Or did you get the suggestion backwards? > Unfortunately we can't really build a type system here to > make this problem easy to catch with a mismatched type, unless there's > some sort of typedef trick we can play? > s/i/corner/ in rpmhpd_set_performance_state() would further enforce the naming scheme used and reduce the risk for future confusion. But we did just squash the final bug... ;) > Reviewed-by: Stephen Boyd <swboyd@chromium.org> Thanks, Bjorn
On 7/8/2021 10:05 AM, Bjorn Andersson wrote: > On Wed 07 Jul 19:21 CDT 2021, Stephen Boyd wrote: > >> Quoting Bjorn Andersson (2021-07-02 17:54:15) >>> rpmhpd_aggregate_corner() takes a corner as parameter, but in >>> rpmhpd_power_off() the code requests the level of the first corner >>> instead. >>> >>> In all (known) current cases the first corner has level 0, so this >>> change should be a nop, but in case that there's a power domain with a >>> non-zero lowest level this makes sure that rpmhpd_power_off() actually >>> requests the lowest level - which is the closest to "power off" we can >>> get. >>> >>> While touching the code, also skip the unnecessary zero-initialization >>> of "ret". >>> >>> Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") >>> Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> >>> --- >> >> I think this is why qcom folks talk about "virtual corner" and "physical >> corner" because there's the one in command DB and the one in hardware. > > I think the driver uses "level" and "corner" to denote the two different > number spaces, so I think we're good...now that we after this patch > don't pass a "level" as "corner" during power_off ;) > >> Maybe we should change rpmhpd_aggregate_corner() to call the argument >> 'vcorner'? > > So "virtual corner" is "corner" and "physical corner" is level? I.e. 256 > is a "physical corner"? I haven't heard of anything called a 'physical corner'. These were always referred to as virtual corners, on older platforms it was just one contiguous number space, on newer ones we added another higher level sparse number space just for more fun :) Command DB refers to these as hlvl and vlvl, I haven;t yet figured out what their full forms are :/ > > Or did you get the suggestion backwards? > >> Unfortunately we can't really build a type system here to >> make this problem easy to catch with a mismatched type, unless there's >> some sort of typedef trick we can play? >> > > s/i/corner/ in rpmhpd_set_performance_state() would further enforce the > naming scheme used and reduce the risk for future confusion. > > But we did just squash the final bug... ;) > >> Reviewed-by: Stephen Boyd <swboyd@chromium.org> > > Thanks, > Bjorn > -- QUALCOMM INDIA, on behalf of Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by The Linux Foundation
Quoting Rajendra Nayak (2021-07-07 22:03:53) > > > On 7/8/2021 10:05 AM, Bjorn Andersson wrote: > > On Wed 07 Jul 19:21 CDT 2021, Stephen Boyd wrote: > > > >> Quoting Bjorn Andersson (2021-07-02 17:54:15) > >>> rpmhpd_aggregate_corner() takes a corner as parameter, but in > >>> rpmhpd_power_off() the code requests the level of the first corner > >>> instead. > >>> > >>> In all (known) current cases the first corner has level 0, so this > >>> change should be a nop, but in case that there's a power domain with a > >>> non-zero lowest level this makes sure that rpmhpd_power_off() actually > >>> requests the lowest level - which is the closest to "power off" we can > >>> get. > >>> > >>> While touching the code, also skip the unnecessary zero-initialization > >>> of "ret". > >>> > >>> Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") > >>> Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> > >>> --- > >> > >> I think this is why qcom folks talk about "virtual corner" and "physical > >> corner" because there's the one in command DB and the one in hardware. > > > > I think the driver uses "level" and "corner" to denote the two different > > number spaces, so I think we're good...now that we after this patch > > don't pass a "level" as "corner" during power_off ;) Alright then nothing to do. Yay? > > > >> Maybe we should change rpmhpd_aggregate_corner() to call the argument > >> 'vcorner'? > > > > So "virtual corner" is "corner" and "physical corner" is level? I.e. 256 > > is a "physical corner"? > > I haven't heard of anything called a 'physical corner'. These were always > referred to as virtual corners, on older platforms it was just one contiguous > number space, on newer ones we added another higher level sparse number space > just for more fun :) > Command DB refers to these as hlvl and vlvl, I haven;t yet figured out what their > full forms are :/ Ah maybe I'm mixing up CPR terms with this stuff. I suspect hlvl is "hardware level" and vlvl is "virtual level", but probably should have been "software level". As far as I remember, the command DB layer was stacked on top so that they could insert more levels in between two levels in the hardware number space and not have to change all the rpmh clients out there (of which there could be many considering all the independent operating systems running on the SoC). For example, [0, 128, 256] maps to [0, 1, 2] and then they realize they need to jam another level between 1 and 2 so they remap 256 to 3 so everyone keeps considering 256 as the previous vlvl to clear the way for 2 to be reused as 198 or something like that. I don't think this ever really changes after the device ships, but it lets them decouple rpmh firmware updates from the rest of the system. As long as they're kept as far apart in vlvl space as there are numbers in hlvl space they can easily do this remap trick and hardware can treat it as levels that bounce around physical voltages that are monotonically increasing.
On 2021-07-03 06:24, Bjorn Andersson wrote: > rpmhpd_aggregate_corner() takes a corner as parameter, but in > rpmhpd_power_off() the code requests the level of the first corner > instead. > > In all (known) current cases the first corner has level 0, so this > change should be a nop, but in case that there's a power domain with a > non-zero lowest level this makes sure that rpmhpd_power_off() actually > requests the lowest level - which is the closest to "power off" we can > get. > > While touching the code, also skip the unnecessary zero-initialization > of "ret". > > Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") > Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> Reviewed-by: Sibi Sankar <sibis@codeaurora.org> Tested-by: Sibi Sankar <sibis@codeaurora.org> > --- > drivers/soc/qcom/rpmhpd.c | 5 ++--- > 1 file changed, 2 insertions(+), 3 deletions(-) > > diff --git a/drivers/soc/qcom/rpmhpd.c b/drivers/soc/qcom/rpmhpd.c > index 2daa17ba54a3..fa209b479ab3 100644 > --- a/drivers/soc/qcom/rpmhpd.c > +++ b/drivers/soc/qcom/rpmhpd.c > @@ -403,12 +403,11 @@ static int rpmhpd_power_on(struct > generic_pm_domain *domain) > static int rpmhpd_power_off(struct generic_pm_domain *domain) > { > struct rpmhpd *pd = domain_to_rpmhpd(domain); > - int ret = 0; > + int ret; > > mutex_lock(&rpmhpd_lock); > > - ret = rpmhpd_aggregate_corner(pd, pd->level[0]); > - > + ret = rpmhpd_aggregate_corner(pd, 0); > if (!ret) > pd->enabled = false; -- Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, a Linux Foundation Collaborative Project.
diff --git a/drivers/soc/qcom/rpmhpd.c b/drivers/soc/qcom/rpmhpd.c index 2daa17ba54a3..fa209b479ab3 100644 --- a/drivers/soc/qcom/rpmhpd.c +++ b/drivers/soc/qcom/rpmhpd.c @@ -403,12 +403,11 @@ static int rpmhpd_power_on(struct generic_pm_domain *domain) static int rpmhpd_power_off(struct generic_pm_domain *domain) { struct rpmhpd *pd = domain_to_rpmhpd(domain); - int ret = 0; + int ret; mutex_lock(&rpmhpd_lock); - ret = rpmhpd_aggregate_corner(pd, pd->level[0]); - + ret = rpmhpd_aggregate_corner(pd, 0); if (!ret) pd->enabled = false;
rpmhpd_aggregate_corner() takes a corner as parameter, but in rpmhpd_power_off() the code requests the level of the first corner instead. In all (known) current cases the first corner has level 0, so this change should be a nop, but in case that there's a power domain with a non-zero lowest level this makes sure that rpmhpd_power_off() actually requests the lowest level - which is the closest to "power off" we can get. While touching the code, also skip the unnecessary zero-initialization of "ret". Fixes: 279b7e8a62cc ("soc: qcom: rpmhpd: Add RPMh power domain driver") Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org> --- drivers/soc/qcom/rpmhpd.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) -- 2.29.2