linuxppc-dev.lists.ozlabs.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 1/2] cpufreq/powernv: Fix use-after-free
@ 2020-02-06  6:26 Oliver O'Halloran
  2020-02-06  6:26 ` [PATCH 2/2] cpufreq/powernv: Fix unsafe notifiers Oliver O'Halloran
                   ` (3 more replies)
  0 siblings, 4 replies; 7+ messages in thread
From: Oliver O'Halloran @ 2020-02-06  6:26 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: Vaidyanathan Srinivasan, Oliver O'Halloran

The cpufreq driver has a use-after-free that we can hit if:

a) There's an OCC message pending when the notifier is registered, and
b) The cpufreq driver fails to register with the core.

When a) occurs the notifier schedules a workqueue item to handle the
message. The backing work_struct is located on chips[].throttle and when b)
happens we clean up by freeing the array. Once we get to the (now free)
queued item and the kernel crashes.

Cc: Vaidyanathan Srinivasan <svaidy@linux.vnet.ibm.com>
Fixes: c5e29ea ("cpufreq: powernv: Fix bugs in powernv_cpufreq_{init/exit}")
Signed-off-by: Oliver O'Halloran <oohall@gmail.com>
---
 drivers/cpufreq/powernv-cpufreq.c | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/drivers/cpufreq/powernv-cpufreq.c b/drivers/cpufreq/powernv-cpufreq.c
index 56f4bc0..1806b1d 100644
--- a/drivers/cpufreq/powernv-cpufreq.c
+++ b/drivers/cpufreq/powernv-cpufreq.c
@@ -1080,6 +1080,12 @@ static int init_chip_info(void)
 
 static inline void clean_chip_info(void)
 {
+	int i;
+
+	/* flush any pending work items */
+	if (chips)
+		for (i = 0; i < nr_chips; i++)
+			cancel_work_sync(&chips[i].throttle);
 	kfree(chips);
 }
 
-- 
2.9.5


^ permalink raw reply related	[flat|nested] 7+ messages in thread

* [PATCH 2/2] cpufreq/powernv: Fix unsafe notifiers
  2020-02-06  6:26 [PATCH 1/2] cpufreq/powernv: Fix use-after-free Oliver O'Halloran
@ 2020-02-06  6:26 ` Oliver O'Halloran
  2020-02-25  6:45   ` Gautham R Shenoy
  2020-02-25  6:42 ` [PATCH 1/2] cpufreq/powernv: Fix use-after-free Gautham R Shenoy
                   ` (2 subsequent siblings)
  3 siblings, 1 reply; 7+ messages in thread
From: Oliver O'Halloran @ 2020-02-06  6:26 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: Vaidyanathan Srinivasan, Oliver O'Halloran

The PowerNV cpufreq driver registers two notifiers: one to catch throttle
messages from the OCC and one to bump the CPU frequency back to normal
before a reboot. Both require the cpufreq driver to be registered in order
to function since the notifier callbacks use various cpufreq_*() functions.

Right now we register both notifiers before we've initialised the driver.
This seems to work, but we should head off any protential problems by
registering the notifiers after the driver is initialised.

Cc: Vaidyanathan Srinivasan <svaidy@linux.vnet.ibm.com>
Signed-off-by: Oliver O'Halloran <oohall@gmail.com>
---
 drivers/cpufreq/powernv-cpufreq.c | 11 +++++------
 1 file changed, 5 insertions(+), 6 deletions(-)

diff --git a/drivers/cpufreq/powernv-cpufreq.c b/drivers/cpufreq/powernv-cpufreq.c
index 1806b1d..03798c4 100644
--- a/drivers/cpufreq/powernv-cpufreq.c
+++ b/drivers/cpufreq/powernv-cpufreq.c
@@ -1114,9 +1114,6 @@ static int __init powernv_cpufreq_init(void)
 	if (rc)
 		goto out;
 
-	register_reboot_notifier(&powernv_cpufreq_reboot_nb);
-	opal_message_notifier_register(OPAL_MSG_OCC, &powernv_cpufreq_opal_nb);
-
 	if (powernv_pstate_info.wof_enabled)
 		powernv_cpufreq_driver.boost_enabled = true;
 	else
@@ -1125,15 +1122,17 @@ static int __init powernv_cpufreq_init(void)
 	rc = cpufreq_register_driver(&powernv_cpufreq_driver);
 	if (rc) {
 		pr_info("Failed to register the cpufreq driver (%d)\n", rc);
-		goto cleanup_notifiers;
+		goto cleanup;
 	}
 
 	if (powernv_pstate_info.wof_enabled)
 		cpufreq_enable_boost_support();
 
+	register_reboot_notifier(&powernv_cpufreq_reboot_nb);
+	opal_message_notifier_register(OPAL_MSG_OCC, &powernv_cpufreq_opal_nb);
+
 	return 0;
-cleanup_notifiers:
-	unregister_all_notifiers();
+cleanup:
 	clean_chip_info();
 out:
 	pr_info("Platform driver disabled. System does not support PState control\n");
-- 
2.9.5


^ permalink raw reply related	[flat|nested] 7+ messages in thread

* Re: [PATCH 1/2] cpufreq/powernv: Fix use-after-free
  2020-02-06  6:26 [PATCH 1/2] cpufreq/powernv: Fix use-after-free Oliver O'Halloran
  2020-02-06  6:26 ` [PATCH 2/2] cpufreq/powernv: Fix unsafe notifiers Oliver O'Halloran
@ 2020-02-25  6:42 ` Gautham R Shenoy
  2020-02-25  7:03 ` Andrew Donnellan
  2020-03-17 13:14 ` Michael Ellerman
  3 siblings, 0 replies; 7+ messages in thread
From: Gautham R Shenoy @ 2020-02-25  6:42 UTC (permalink / raw)
  To: Oliver O'Halloran; +Cc: Viresh Kumar, svaidy, linuxppc-dev, linux-pm

On Thu, Feb 06, 2020 at 05:26:21PM +1100, Oliver O'Halloran wrote:
> The cpufreq driver has a use-after-free that we can hit if:
> 
> a) There's an OCC message pending when the notifier is registered, and
> b) The cpufreq driver fails to register with the core.
> 
> When a) occurs the notifier schedules a workqueue item to handle the
> message. The backing work_struct is located on chips[].throttle and when b)
> happens we clean up by freeing the array. Once we get to the (now free)
> queued item and the kernel crashes.
> 
> Cc: Vaidyanathan Srinivasan <svaidy@linux.vnet.ibm.com>
> Fixes: c5e29ea ("cpufreq: powernv: Fix bugs in powernv_cpufreq_{init/exit}")
> Signed-off-by: Oliver O'Halloran <oohall@gmail.com>

Thanks for this fix Oliver.

Reviewed-by: Gautham R. Shenoy <ego@linux.vnet.ibm.com>

> ---
>  drivers/cpufreq/powernv-cpufreq.c | 6 ++++++
>  1 file changed, 6 insertions(+)
> 
> diff --git a/drivers/cpufreq/powernv-cpufreq.c b/drivers/cpufreq/powernv-cpufreq.c
> index 56f4bc0..1806b1d 100644
> --- a/drivers/cpufreq/powernv-cpufreq.c
> +++ b/drivers/cpufreq/powernv-cpufreq.c
> @@ -1080,6 +1080,12 @@ static int init_chip_info(void)
> 
>  static inline void clean_chip_info(void)
>  {
> +	int i;
> +
> +	/* flush any pending work items */
> +	if (chips)
> +		for (i = 0; i < nr_chips; i++)
> +			cancel_work_sync(&chips[i].throttle);
>  	kfree(chips);
>  }
> 
> -- 
> 2.9.5
> 

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [PATCH 2/2] cpufreq/powernv: Fix unsafe notifiers
  2020-02-06  6:26 ` [PATCH 2/2] cpufreq/powernv: Fix unsafe notifiers Oliver O'Halloran
@ 2020-02-25  6:45   ` Gautham R Shenoy
  0 siblings, 0 replies; 7+ messages in thread
From: Gautham R Shenoy @ 2020-02-25  6:45 UTC (permalink / raw)
  To: Oliver O'Halloran
  Cc: Viresh Kumar, Vaidyanathan Srinivasan, linuxppc-dev, linux-pm

On Thu, Feb 06, 2020 at 05:26:22PM +1100, Oliver O'Halloran wrote:
> The PowerNV cpufreq driver registers two notifiers: one to catch throttle
> messages from the OCC and one to bump the CPU frequency back to normal
> before a reboot. Both require the cpufreq driver to be registered in order
> to function since the notifier callbacks use various cpufreq_*() functions.
> 
> Right now we register both notifiers before we've initialised the driver.
> This seems to work, but we should head off any protential problems by
> registering the notifiers after the driver is initialised.
> 
> Cc: Vaidyanathan Srinivasan <svaidy@linux.vnet.ibm.com>
> Signed-off-by: Oliver O'Halloran <oohall@gmail.com>

Reviewed-by: Gautham R. Shenoy <ego@linux.vnet.ibm.com>

> ---
>  drivers/cpufreq/powernv-cpufreq.c | 11 +++++------
>  1 file changed, 5 insertions(+), 6 deletions(-)
> 
> diff --git a/drivers/cpufreq/powernv-cpufreq.c b/drivers/cpufreq/powernv-cpufreq.c
> index 1806b1d..03798c4 100644
> --- a/drivers/cpufreq/powernv-cpufreq.c
> +++ b/drivers/cpufreq/powernv-cpufreq.c
> @@ -1114,9 +1114,6 @@ static int __init powernv_cpufreq_init(void)
>  	if (rc)
>  		goto out;
> 
> -	register_reboot_notifier(&powernv_cpufreq_reboot_nb);
> -	opal_message_notifier_register(OPAL_MSG_OCC, &powernv_cpufreq_opal_nb);
> -
>  	if (powernv_pstate_info.wof_enabled)
>  		powernv_cpufreq_driver.boost_enabled = true;
>  	else
> @@ -1125,15 +1122,17 @@ static int __init powernv_cpufreq_init(void)
>  	rc = cpufreq_register_driver(&powernv_cpufreq_driver);
>  	if (rc) {
>  		pr_info("Failed to register the cpufreq driver (%d)\n", rc);
> -		goto cleanup_notifiers;
> +		goto cleanup;
>  	}
> 
>  	if (powernv_pstate_info.wof_enabled)
>  		cpufreq_enable_boost_support();
> 
> +	register_reboot_notifier(&powernv_cpufreq_reboot_nb);
> +	opal_message_notifier_register(OPAL_MSG_OCC, &powernv_cpufreq_opal_nb);
> +
>  	return 0;
> -cleanup_notifiers:
> -	unregister_all_notifiers();
> +cleanup:
>  	clean_chip_info();
>  out:
>  	pr_info("Platform driver disabled. System does not support PState control\n");
> -- 
> 2.9.5
> 

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [PATCH 1/2] cpufreq/powernv: Fix use-after-free
  2020-02-06  6:26 [PATCH 1/2] cpufreq/powernv: Fix use-after-free Oliver O'Halloran
  2020-02-06  6:26 ` [PATCH 2/2] cpufreq/powernv: Fix unsafe notifiers Oliver O'Halloran
  2020-02-25  6:42 ` [PATCH 1/2] cpufreq/powernv: Fix use-after-free Gautham R Shenoy
@ 2020-02-25  7:03 ` Andrew Donnellan
  2020-02-27  1:31   ` Michael Ellerman
  2020-03-17 13:14 ` Michael Ellerman
  3 siblings, 1 reply; 7+ messages in thread
From: Andrew Donnellan @ 2020-02-25  7:03 UTC (permalink / raw)
  To: Oliver O'Halloran, linuxppc-dev; +Cc: Vaidyanathan Srinivasan

On 6/2/20 5:26 pm, Oliver O'Halloran wrote:
> The cpufreq driver has a use-after-free that we can hit if:
> 
> a) There's an OCC message pending when the notifier is registered, and
> b) The cpufreq driver fails to register with the core.
> 
> When a) occurs the notifier schedules a workqueue item to handle the
> message. The backing work_struct is located on chips[].throttle and when b)
> happens we clean up by freeing the array. Once we get to the (now free)
> queued item and the kernel crashes.
> 
> Cc: Vaidyanathan Srinivasan <svaidy@linux.vnet.ibm.com>
> Fixes: c5e29ea ("cpufreq: powernv: Fix bugs in powernv_cpufreq_{init/exit}")
> Signed-off-by: Oliver O'Halloran <oohall@gmail.com>

This sounds like it needs to go to stable.


-- 
Andrew Donnellan              OzLabs, ADL Canberra
ajd@linux.ibm.com             IBM Australia Limited


^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [PATCH 1/2] cpufreq/powernv: Fix use-after-free
  2020-02-25  7:03 ` Andrew Donnellan
@ 2020-02-27  1:31   ` Michael Ellerman
  0 siblings, 0 replies; 7+ messages in thread
From: Michael Ellerman @ 2020-02-27  1:31 UTC (permalink / raw)
  To: Andrew Donnellan, Oliver O'Halloran, linuxppc-dev
  Cc: Vaidyanathan Srinivasan

Andrew Donnellan <ajd@linux.ibm.com> writes:
> On 6/2/20 5:26 pm, Oliver O'Halloran wrote:
>> The cpufreq driver has a use-after-free that we can hit if:
>> 
>> a) There's an OCC message pending when the notifier is registered, and
>> b) The cpufreq driver fails to register with the core.
>> 
>> When a) occurs the notifier schedules a workqueue item to handle the
>> message. The backing work_struct is located on chips[].throttle and when b)
>> happens we clean up by freeing the array. Once we get to the (now free)
>> queued item and the kernel crashes.
>> 
>> Cc: Vaidyanathan Srinivasan <svaidy@linux.vnet.ibm.com>
>> Fixes: c5e29ea ("cpufreq: powernv: Fix bugs in powernv_cpufreq_{init/exit}")
>> Signed-off-by: Oliver O'Halloran <oohall@gmail.com>
>
> This sounds like it needs to go to stable.

I tagged it for stable when applying.

cheers

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [PATCH 1/2] cpufreq/powernv: Fix use-after-free
  2020-02-06  6:26 [PATCH 1/2] cpufreq/powernv: Fix use-after-free Oliver O'Halloran
                   ` (2 preceding siblings ...)
  2020-02-25  7:03 ` Andrew Donnellan
@ 2020-03-17 13:14 ` Michael Ellerman
  3 siblings, 0 replies; 7+ messages in thread
From: Michael Ellerman @ 2020-03-17 13:14 UTC (permalink / raw)
  To: Oliver O'Halloran, linuxppc-dev
  Cc: Vaidyanathan Srinivasan, Oliver O'Halloran

On Thu, 2020-02-06 at 06:26:21 UTC, Oliver O'Halloran wrote:
> The cpufreq driver has a use-after-free that we can hit if:
> 
> a) There's an OCC message pending when the notifier is registered, and
> b) The cpufreq driver fails to register with the core.
> 
> When a) occurs the notifier schedules a workqueue item to handle the
> message. The backing work_struct is located on chips[].throttle and when b)
> happens we clean up by freeing the array. Once we get to the (now free)
> queued item and the kernel crashes.
> 
> Cc: Vaidyanathan Srinivasan <svaidy@linux.vnet.ibm.com>
> Fixes: c5e29ea ("cpufreq: powernv: Fix bugs in powernv_cpufreq_{init/exit}")
> Signed-off-by: Oliver O'Halloran <oohall@gmail.com>

Series applied to powerpc next, thanks.

https://git.kernel.org/powerpc/c/d0a72efac89d1c35ac55197895201b7b94c5e6ef

cheers

^ permalink raw reply	[flat|nested] 7+ messages in thread

end of thread, other threads:[~2020-03-17 13:33 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2020-02-06  6:26 [PATCH 1/2] cpufreq/powernv: Fix use-after-free Oliver O'Halloran
2020-02-06  6:26 ` [PATCH 2/2] cpufreq/powernv: Fix unsafe notifiers Oliver O'Halloran
2020-02-25  6:45   ` Gautham R Shenoy
2020-02-25  6:42 ` [PATCH 1/2] cpufreq/powernv: Fix use-after-free Gautham R Shenoy
2020-02-25  7:03 ` Andrew Donnellan
2020-02-27  1:31   ` Michael Ellerman
2020-03-17 13:14 ` Michael Ellerman

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).