* [PATCH 07/22] mm/vmstat: Drop get_online_cpus() from init_cpu_node_state/vmstat_cpu_dead()
[not found] <20161126231350.10321-1-bigeasy@linutronix.de>
@ 2016-11-26 23:13 ` Sebastian Andrzej Siewior
2016-11-28 9:24 ` Michal Hocko
2016-11-26 23:13 ` [PATCH 08/22] mm/vmstat: Avoid on each online CPU loops Sebastian Andrzej Siewior
` (5 subsequent siblings)
6 siblings, 1 reply; 14+ messages in thread
From: Sebastian Andrzej Siewior @ 2016-11-26 23:13 UTC (permalink / raw)
To: linux-kernel
Cc: rt, tglx, Sebastian Andrzej Siewior, Andrew Morton,
Vlastimil Babka, Mel Gorman, Johannes Weiner, linux-mm
Both functions are called with protection against cpu hotplug already so
*_online_cpus() could be dropped.
Cc: Andrew Morton <akpm@linux-foundation.org>
Cc: Vlastimil Babka <vbabka@suse.cz>
Cc: Mel Gorman <mgorman@techsingularity.net>
Cc: Johannes Weiner <hannes@cmpxchg.org>
Cc: linux-mm@kvack.org
Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
---
mm/vmstat.c | 7 +------
1 file changed, 1 insertion(+), 6 deletions(-)
diff --git a/mm/vmstat.c b/mm/vmstat.c
index 604f26a4f696..0b63ffb5c407 100644
--- a/mm/vmstat.c
+++ b/mm/vmstat.c
@@ -1722,24 +1722,19 @@ static void __init init_cpu_node_state(void)
{
int cpu;
- get_online_cpus();
for_each_online_cpu(cpu)
node_set_state(cpu_to_node(cpu), N_CPU);
- put_online_cpus();
}
static void vmstat_cpu_dead(int node)
{
int cpu;
- get_online_cpus();
for_each_online_cpu(cpu)
if (cpu_to_node(cpu) == node)
- goto end;
+ return;
node_clear_state(node, N_CPU);
-end:
- put_online_cpus();
}
/*
--
2.10.2
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply related [flat|nested] 14+ messages in thread
* Re: [PATCH 07/22] mm/vmstat: Drop get_online_cpus() from init_cpu_node_state/vmstat_cpu_dead()
2016-11-26 23:13 ` [PATCH 07/22] mm/vmstat: Drop get_online_cpus() from init_cpu_node_state/vmstat_cpu_dead() Sebastian Andrzej Siewior
@ 2016-11-28 9:24 ` Michal Hocko
0 siblings, 0 replies; 14+ messages in thread
From: Michal Hocko @ 2016-11-28 9:24 UTC (permalink / raw)
To: Sebastian Andrzej Siewior
Cc: linux-kernel, rt, tglx, Andrew Morton, Vlastimil Babka,
Mel Gorman, Johannes Weiner, linux-mm
On Sun 27-11-16 00:13:35, Sebastian Andrzej Siewior wrote:
> Both functions are called with protection against cpu hotplug already so
> *_online_cpus() could be dropped.
>
> Cc: Andrew Morton <akpm@linux-foundation.org>
> Cc: Vlastimil Babka <vbabka@suse.cz>
> Cc: Mel Gorman <mgorman@techsingularity.net>
> Cc: Johannes Weiner <hannes@cmpxchg.org>
> Cc: linux-mm@kvack.org
> Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
Acked-by: Michal Hocko <mhocko@suse.com>
> ---
> mm/vmstat.c | 7 +------
> 1 file changed, 1 insertion(+), 6 deletions(-)
>
> diff --git a/mm/vmstat.c b/mm/vmstat.c
> index 604f26a4f696..0b63ffb5c407 100644
> --- a/mm/vmstat.c
> +++ b/mm/vmstat.c
> @@ -1722,24 +1722,19 @@ static void __init init_cpu_node_state(void)
> {
> int cpu;
>
> - get_online_cpus();
> for_each_online_cpu(cpu)
> node_set_state(cpu_to_node(cpu), N_CPU);
> - put_online_cpus();
> }
>
> static void vmstat_cpu_dead(int node)
> {
> int cpu;
>
> - get_online_cpus();
> for_each_online_cpu(cpu)
> if (cpu_to_node(cpu) == node)
> - goto end;
> + return;
>
> node_clear_state(node, N_CPU);
> -end:
> - put_online_cpus();
> }
>
> /*
> --
> 2.10.2
>
> --
> To unsubscribe, send a message with 'unsubscribe linux-mm' in
> the body to majordomo@kvack.org. For more info on Linux MM,
> see: http://www.linux-mm.org/ .
> Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
--
Michal Hocko
SUSE Labs
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply [flat|nested] 14+ messages in thread
* [PATCH 08/22] mm/vmstat: Avoid on each online CPU loops
[not found] <20161126231350.10321-1-bigeasy@linutronix.de>
2016-11-26 23:13 ` [PATCH 07/22] mm/vmstat: Drop get_online_cpus() from init_cpu_node_state/vmstat_cpu_dead() Sebastian Andrzej Siewior
@ 2016-11-26 23:13 ` Sebastian Andrzej Siewior
2016-11-28 9:28 ` Michal Hocko
2016-11-26 23:13 ` [PATCH 09/22] mm/vmstat: Convert to hotplug state machine Sebastian Andrzej Siewior
` (4 subsequent siblings)
6 siblings, 1 reply; 14+ messages in thread
From: Sebastian Andrzej Siewior @ 2016-11-26 23:13 UTC (permalink / raw)
To: linux-kernel
Cc: rt, tglx, Sebastian Andrzej Siewior, Andrew Morton,
Vlastimil Babka, Mel Gorman, Johannes Weiner, linux-mm
Both iterations over online cpus can be replaced by the proper node
specific functions.
Cc: Andrew Morton <akpm@linux-foundation.org>
Cc: Vlastimil Babka <vbabka@suse.cz>
Cc: Mel Gorman <mgorman@techsingularity.net>
Cc: Johannes Weiner <hannes@cmpxchg.org>
Cc: linux-mm@kvack.org
Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
---
mm/vmstat.c | 14 +++++++-------
1 file changed, 7 insertions(+), 7 deletions(-)
diff --git a/mm/vmstat.c b/mm/vmstat.c
index 0b63ffb5c407..b96dcec7e7d7 100644
--- a/mm/vmstat.c
+++ b/mm/vmstat.c
@@ -1720,19 +1720,19 @@ static void __init start_shepherd_timer(void)
static void __init init_cpu_node_state(void)
{
- int cpu;
+ int node;
- for_each_online_cpu(cpu)
- node_set_state(cpu_to_node(cpu), N_CPU);
+ for_each_online_node(node)
+ node_set_state(node, N_CPU);
}
static void vmstat_cpu_dead(int node)
{
- int cpu;
+ const struct cpumask *node_cpus;
- for_each_online_cpu(cpu)
- if (cpu_to_node(cpu) == node)
- return;
+ node_cpus = cpumask_of_node(node);
+ if (cpumask_weight(node_cpus) > 0)
+ return;
node_clear_state(node, N_CPU);
}
--
2.10.2
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply related [flat|nested] 14+ messages in thread
* Re: [PATCH 08/22] mm/vmstat: Avoid on each online CPU loops
2016-11-26 23:13 ` [PATCH 08/22] mm/vmstat: Avoid on each online CPU loops Sebastian Andrzej Siewior
@ 2016-11-28 9:28 ` Michal Hocko
2016-11-29 14:08 ` Thomas Gleixner
0 siblings, 1 reply; 14+ messages in thread
From: Michal Hocko @ 2016-11-28 9:28 UTC (permalink / raw)
To: Sebastian Andrzej Siewior
Cc: linux-kernel, rt, tglx, Andrew Morton, Vlastimil Babka,
Mel Gorman, Johannes Weiner, linux-mm
On Sun 27-11-16 00:13:36, Sebastian Andrzej Siewior wrote:
[...]
> static void __init init_cpu_node_state(void)
> {
> - int cpu;
> + int node;
>
> - for_each_online_cpu(cpu)
> - node_set_state(cpu_to_node(cpu), N_CPU);
> + for_each_online_node(node)
> + node_set_state(node, N_CPU);
Is this really correct? The point of the original code was to mark only
those nodes which have at least one CPU. Or am I missing something?
> }
>
> static void vmstat_cpu_dead(int node)
> {
> - int cpu;
> + const struct cpumask *node_cpus;
>
> - for_each_online_cpu(cpu)
> - if (cpu_to_node(cpu) == node)
> - return;
> + node_cpus = cpumask_of_node(node);
> + if (cpumask_weight(node_cpus) > 0)
> + return;
This looks OK
>
> node_clear_state(node, N_CPU);
> }
> --
> 2.10.2
>
> --
> To unsubscribe, send a message with 'unsubscribe linux-mm' in
> the body to majordomo@kvack.org. For more info on Linux MM,
> see: http://www.linux-mm.org/ .
> Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
--
Michal Hocko
SUSE Labs
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH 08/22] mm/vmstat: Avoid on each online CPU loops
2016-11-28 9:28 ` Michal Hocko
@ 2016-11-29 14:08 ` Thomas Gleixner
2016-11-29 14:44 ` Michal Hocko
2016-11-29 14:51 ` [PATCH 08/22 v2] " Sebastian Andrzej Siewior
0 siblings, 2 replies; 14+ messages in thread
From: Thomas Gleixner @ 2016-11-29 14:08 UTC (permalink / raw)
To: Michal Hocko
Cc: Sebastian Andrzej Siewior, linux-kernel, rt, Andrew Morton,
Vlastimil Babka, Mel Gorman, Johannes Weiner, linux-mm
On Mon, 28 Nov 2016, Michal Hocko wrote:
> On Sun 27-11-16 00:13:36, Sebastian Andrzej Siewior wrote:
> [...]
> > static void __init init_cpu_node_state(void)
> > {
> > - int cpu;
> > + int node;
> >
> > - for_each_online_cpu(cpu)
> > - node_set_state(cpu_to_node(cpu), N_CPU);
> > + for_each_online_node(node)
> > + node_set_state(node, N_CPU);
>
> Is this really correct? The point of the original code was to mark only
> those nodes which have at least one CPU. Or am I missing something?
You're right. An online node does not necessarily have an online CPU.
for_each_online_node(node) {
if (cpumask_weight(cpumask_of_node(node)) > 0)
node_set_state(node, N_CPU);
}
is probably more correct.
Thanks,
tglx
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply [flat|nested] 14+ messages in thread
* Re: [PATCH 08/22] mm/vmstat: Avoid on each online CPU loops
2016-11-29 14:08 ` Thomas Gleixner
@ 2016-11-29 14:44 ` Michal Hocko
2016-11-29 14:51 ` [PATCH 08/22 v2] " Sebastian Andrzej Siewior
1 sibling, 0 replies; 14+ messages in thread
From: Michal Hocko @ 2016-11-29 14:44 UTC (permalink / raw)
To: Thomas Gleixner
Cc: Sebastian Andrzej Siewior, linux-kernel, rt, Andrew Morton,
Vlastimil Babka, Mel Gorman, Johannes Weiner, linux-mm
On Tue 29-11-16 15:08:10, Thomas Gleixner wrote:
> On Mon, 28 Nov 2016, Michal Hocko wrote:
> > On Sun 27-11-16 00:13:36, Sebastian Andrzej Siewior wrote:
> > [...]
> > > static void __init init_cpu_node_state(void)
> > > {
> > > - int cpu;
> > > + int node;
> > >
> > > - for_each_online_cpu(cpu)
> > > - node_set_state(cpu_to_node(cpu), N_CPU);
> > > + for_each_online_node(node)
> > > + node_set_state(node, N_CPU);
> >
> > Is this really correct? The point of the original code was to mark only
> > those nodes which have at least one CPU. Or am I missing something?
>
> You're right. An online node does not necessarily have an online CPU.
>
> for_each_online_node(node) {
> if (cpumask_weight(cpumask_of_node(node)) > 0)
> node_set_state(node, N_CPU);
> }
>
> is probably more correct.
Yes, this looks correct. Considering that the same cpumask_weight is
used in another function I guess a small helper would be nice. E.g.
bool node_has_cpus(int node)
{
return cpumask_weight(cpumask_of_node(node)) > 0;
}
--
Michal Hocko
SUSE Labs
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply [flat|nested] 14+ messages in thread
* [PATCH 08/22 v2] mm/vmstat: Avoid on each online CPU loops
2016-11-29 14:08 ` Thomas Gleixner
2016-11-29 14:44 ` Michal Hocko
@ 2016-11-29 14:51 ` Sebastian Andrzej Siewior
2016-11-29 15:20 ` Michal Hocko
1 sibling, 1 reply; 14+ messages in thread
From: Sebastian Andrzej Siewior @ 2016-11-29 14:51 UTC (permalink / raw)
To: Thomas Gleixner
Cc: Michal Hocko, linux-kernel, rt, Andrew Morton, Vlastimil Babka,
Mel Gorman, Johannes Weiner, linux-mm
Both iterations over online cpus can be replaced by the proper node
specific functions.
Cc: Andrew Morton <akpm@linux-foundation.org>
Cc: Vlastimil Babka <vbabka@suse.cz>
Cc: Mel Gorman <mgorman@techsingularity.net>
Cc: Johannes Weiner <hannes@cmpxchg.org>
Cc: linux-mm@kvack.org
Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
---
v1…v2: take into account that we may have online nodes with no CPUs.
mm/vmstat.c | 16 +++++++++-------
1 file changed, 9 insertions(+), 7 deletions(-)
diff --git a/mm/vmstat.c b/mm/vmstat.c
index 0b63ffb5c407..5152cd1c490f 100644
--- a/mm/vmstat.c
+++ b/mm/vmstat.c
@@ -1720,19 +1720,21 @@ static void __init start_shepherd_timer(void)
static void __init init_cpu_node_state(void)
{
- int cpu;
+ int node;
- for_each_online_cpu(cpu)
- node_set_state(cpu_to_node(cpu), N_CPU);
+ for_each_online_node(node) {
+ if (cpumask_weight(cpumask_of_node(node)) > 0)
+ node_set_state(node, N_CPU);
+ }
}
static void vmstat_cpu_dead(int node)
{
- int cpu;
+ const struct cpumask *node_cpus;
- for_each_online_cpu(cpu)
- if (cpu_to_node(cpu) == node)
- return;
+ node_cpus = cpumask_of_node(node);
+ if (cpumask_weight(node_cpus) > 0)
+ return;
node_clear_state(node, N_CPU);
}
--
2.10.2
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply related [flat|nested] 14+ messages in thread
* Re: [PATCH 08/22 v2] mm/vmstat: Avoid on each online CPU loops
2016-11-29 14:51 ` [PATCH 08/22 v2] " Sebastian Andrzej Siewior
@ 2016-11-29 15:20 ` Michal Hocko
0 siblings, 0 replies; 14+ messages in thread
From: Michal Hocko @ 2016-11-29 15:20 UTC (permalink / raw)
To: Sebastian Andrzej Siewior
Cc: Thomas Gleixner, linux-kernel, rt, Andrew Morton,
Vlastimil Babka, Mel Gorman, Johannes Weiner, linux-mm
On Tue 29-11-16 15:51:14, Sebastian Andrzej Siewior wrote:
> Both iterations over online cpus can be replaced by the proper node
> specific functions.
>
> Cc: Andrew Morton <akpm@linux-foundation.org>
> Cc: Vlastimil Babka <vbabka@suse.cz>
> Cc: Mel Gorman <mgorman@techsingularity.net>
> Cc: Johannes Weiner <hannes@cmpxchg.org>
> Cc: linux-mm@kvack.org
> Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
Acked-by: Michal Hocko <mhocko@suse.com>
> ---
> v1a?|v2: take into account that we may have online nodes with no CPUs.
>
> mm/vmstat.c | 16 +++++++++-------
> 1 file changed, 9 insertions(+), 7 deletions(-)
>
> diff --git a/mm/vmstat.c b/mm/vmstat.c
> index 0b63ffb5c407..5152cd1c490f 100644
> --- a/mm/vmstat.c
> +++ b/mm/vmstat.c
> @@ -1720,19 +1720,21 @@ static void __init start_shepherd_timer(void)
>
> static void __init init_cpu_node_state(void)
> {
> - int cpu;
> + int node;
>
> - for_each_online_cpu(cpu)
> - node_set_state(cpu_to_node(cpu), N_CPU);
> + for_each_online_node(node) {
> + if (cpumask_weight(cpumask_of_node(node)) > 0)
> + node_set_state(node, N_CPU);
> + }
> }
>
> static void vmstat_cpu_dead(int node)
> {
> - int cpu;
> + const struct cpumask *node_cpus;
>
> - for_each_online_cpu(cpu)
> - if (cpu_to_node(cpu) == node)
> - return;
> + node_cpus = cpumask_of_node(node);
> + if (cpumask_weight(node_cpus) > 0)
> + return;
>
> node_clear_state(node, N_CPU);
> }
> --
> 2.10.2
--
Michal Hocko
SUSE Labs
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply [flat|nested] 14+ messages in thread
* [PATCH 09/22] mm/vmstat: Convert to hotplug state machine
[not found] <20161126231350.10321-1-bigeasy@linutronix.de>
2016-11-26 23:13 ` [PATCH 07/22] mm/vmstat: Drop get_online_cpus() from init_cpu_node_state/vmstat_cpu_dead() Sebastian Andrzej Siewior
2016-11-26 23:13 ` [PATCH 08/22] mm/vmstat: Avoid on each online CPU loops Sebastian Andrzej Siewior
@ 2016-11-26 23:13 ` Sebastian Andrzej Siewior
2016-11-29 14:52 ` [PATCH 09/22 v2] " Sebastian Andrzej Siewior
2016-11-26 23:13 ` [PATCH 10/22] mm/zsmalloc: " Sebastian Andrzej Siewior
` (3 subsequent siblings)
6 siblings, 1 reply; 14+ messages in thread
From: Sebastian Andrzej Siewior @ 2016-11-26 23:13 UTC (permalink / raw)
To: linux-kernel
Cc: rt, tglx, Sebastian Andrzej Siewior, Andrew Morton,
Vlastimil Babka, Mel Gorman, Johannes Weiner, linux-mm
Install the callbacks via the state machine, but do not invoke them as we
can initialize the node state without calling the callbacks on all online
CPUs.
start_shepherd_timer() is now called outside the get_online_cpus() block
which is safe as it only operates on cpu possible mask.
Cc: Andrew Morton <akpm@linux-foundation.org>
Cc: Vlastimil Babka <vbabka@suse.cz>
Cc: Mel Gorman <mgorman@techsingularity.net>
Cc: Johannes Weiner <hannes@cmpxchg.org>
Cc: linux-mm@kvack.org
Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
---
include/linux/cpuhotplug.h | 1 +
mm/vmstat.c | 76 +++++++++++++++++++++-------------------------
2 files changed, 36 insertions(+), 41 deletions(-)
diff --git a/include/linux/cpuhotplug.h b/include/linux/cpuhotplug.h
index 18bcfeb2463e..4ebd1bc27f8d 100644
--- a/include/linux/cpuhotplug.h
+++ b/include/linux/cpuhotplug.h
@@ -20,6 +20,7 @@ enum cpuhp_state {
CPUHP_VIRT_NET_DEAD,
CPUHP_SLUB_DEAD,
CPUHP_MM_WRITEBACK_DEAD,
+ CPUHP_MM_VMSTAT_DEAD,
CPUHP_SOFTIRQ_DEAD,
CPUHP_NET_MVNETA_DEAD,
CPUHP_CPUIDLE_DEAD,
diff --git a/mm/vmstat.c b/mm/vmstat.c
index b96dcec7e7d7..dfe3cb9f2c36 100644
--- a/mm/vmstat.c
+++ b/mm/vmstat.c
@@ -1726,64 +1726,58 @@ static void __init init_cpu_node_state(void)
node_set_state(node, N_CPU);
}
-static void vmstat_cpu_dead(int node)
+static int vmstat_cpu_online(unsigned int cpu)
+{
+ refresh_zone_stat_thresholds();
+ node_set_state(cpu_to_node(cpu), N_CPU);
+ return 0;
+}
+
+static int vmstat_cpu_down_prep(unsigned int cpu)
+{
+ cancel_delayed_work_sync(&per_cpu(vmstat_work, cpu));
+ return 0;
+}
+
+static int vmstat_cpu_dead(unsigned int cpu)
{
const struct cpumask *node_cpus;
+ int node;
+ node = cpu_to_node(cpu);
+
+ refresh_zone_stat_thresholds();
node_cpus = cpumask_of_node(node);
if (cpumask_weight(node_cpus) > 0)
- return;
+ return 0;
node_clear_state(node, N_CPU);
+ return 0;
}
-/*
- * Use the cpu notifier to insure that the thresholds are recalculated
- * when necessary.
- */
-static int vmstat_cpuup_callback(struct notifier_block *nfb,
- unsigned long action,
- void *hcpu)
-{
- long cpu = (long)hcpu;
-
- switch (action) {
- case CPU_ONLINE:
- case CPU_ONLINE_FROZEN:
- refresh_zone_stat_thresholds();
- node_set_state(cpu_to_node(cpu), N_CPU);
- break;
- case CPU_DOWN_PREPARE:
- case CPU_DOWN_PREPARE_FROZEN:
- cancel_delayed_work_sync(&per_cpu(vmstat_work, cpu));
- break;
- case CPU_DOWN_FAILED:
- case CPU_DOWN_FAILED_FROZEN:
- break;
- case CPU_DEAD:
- case CPU_DEAD_FROZEN:
- refresh_zone_stat_thresholds();
- vmstat_cpu_dead(cpu_to_node(cpu));
- break;
- default:
- break;
- }
- return NOTIFY_OK;
-}
-
-static struct notifier_block vmstat_notifier =
- { &vmstat_cpuup_callback, NULL, 0 };
#endif
static int __init setup_vmstat(void)
{
#ifdef CONFIG_SMP
- cpu_notifier_register_begin();
- __register_cpu_notifier(&vmstat_notifier);
+ int ret;
+
+ ret = cpuhp_setup_state_nocalls(CPUHP_MM_VMSTAT_DEAD, "mm/vmstat:dead",
+ NULL, vmstat_cpu_dead);
+ if (ret < 0)
+ pr_err("vmstat: failed to register 'dead' hotplug state\n");
+
+ ret = cpuhp_setup_state_nocalls(CPUHP_AP_ONLINE_DYN, "mm/vmstat:online",
+ vmstat_cpu_online,
+ vmstat_cpu_down_prep);
+ if (ret < 0)
+ pr_err("vmstat: failed to register 'online' hotplug state\n");
+
+ get_online_cpus();
init_cpu_node_state();
+ put_online_cpus();
start_shepherd_timer();
- cpu_notifier_register_done();
#endif
#ifdef CONFIG_PROC_FS
proc_create("buddyinfo", S_IRUGO, NULL, &fragmentation_file_operations);
--
2.10.2
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply related [flat|nested] 14+ messages in thread
* [PATCH 09/22 v2] mm/vmstat: Convert to hotplug state machine
2016-11-26 23:13 ` [PATCH 09/22] mm/vmstat: Convert to hotplug state machine Sebastian Andrzej Siewior
@ 2016-11-29 14:52 ` Sebastian Andrzej Siewior
0 siblings, 0 replies; 14+ messages in thread
From: Sebastian Andrzej Siewior @ 2016-11-29 14:52 UTC (permalink / raw)
To: linux-kernel
Cc: rt, tglx, Andrew Morton, Vlastimil Babka, Mel Gorman,
Johannes Weiner, linux-mm
Install the callbacks via the state machine, but do not invoke them as we
can initialize the node state without calling the callbacks on all online
CPUs.
start_shepherd_timer() is now called outside the get_online_cpus() block
which is safe as it only operates on cpu possible mask.
Cc: Andrew Morton <akpm@linux-foundation.org>
Cc: Vlastimil Babka <vbabka@suse.cz>
Cc: Mel Gorman <mgorman@techsingularity.net>
Cc: Johannes Weiner <hannes@cmpxchg.org>
Cc: linux-mm@kvack.org
Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
---
v1…v2: rebase on top of PATCH 08/22 v2.
include/linux/cpuhotplug.h | 1 +
mm/vmstat.c | 76 +++++++++++++++++++++-------------------------
2 files changed, 36 insertions(+), 41 deletions(-)
diff --git a/include/linux/cpuhotplug.h b/include/linux/cpuhotplug.h
index 18bcfeb2463e..4ebd1bc27f8d 100644
--- a/include/linux/cpuhotplug.h
+++ b/include/linux/cpuhotplug.h
@@ -20,6 +20,7 @@ enum cpuhp_state {
CPUHP_VIRT_NET_DEAD,
CPUHP_SLUB_DEAD,
CPUHP_MM_WRITEBACK_DEAD,
+ CPUHP_MM_VMSTAT_DEAD,
CPUHP_SOFTIRQ_DEAD,
CPUHP_NET_MVNETA_DEAD,
CPUHP_CPUIDLE_DEAD,
diff --git a/mm/vmstat.c b/mm/vmstat.c
index 5152cd1c490f..7c28df36f50f 100644
--- a/mm/vmstat.c
+++ b/mm/vmstat.c
@@ -1728,64 +1728,58 @@ static void __init init_cpu_node_state(void)
}
}
-static void vmstat_cpu_dead(int node)
+static int vmstat_cpu_online(unsigned int cpu)
+{
+ refresh_zone_stat_thresholds();
+ node_set_state(cpu_to_node(cpu), N_CPU);
+ return 0;
+}
+
+static int vmstat_cpu_down_prep(unsigned int cpu)
+{
+ cancel_delayed_work_sync(&per_cpu(vmstat_work, cpu));
+ return 0;
+}
+
+static int vmstat_cpu_dead(unsigned int cpu)
{
const struct cpumask *node_cpus;
+ int node;
+ node = cpu_to_node(cpu);
+
+ refresh_zone_stat_thresholds();
node_cpus = cpumask_of_node(node);
if (cpumask_weight(node_cpus) > 0)
- return;
+ return 0;
node_clear_state(node, N_CPU);
+ return 0;
}
-/*
- * Use the cpu notifier to insure that the thresholds are recalculated
- * when necessary.
- */
-static int vmstat_cpuup_callback(struct notifier_block *nfb,
- unsigned long action,
- void *hcpu)
-{
- long cpu = (long)hcpu;
-
- switch (action) {
- case CPU_ONLINE:
- case CPU_ONLINE_FROZEN:
- refresh_zone_stat_thresholds();
- node_set_state(cpu_to_node(cpu), N_CPU);
- break;
- case CPU_DOWN_PREPARE:
- case CPU_DOWN_PREPARE_FROZEN:
- cancel_delayed_work_sync(&per_cpu(vmstat_work, cpu));
- break;
- case CPU_DOWN_FAILED:
- case CPU_DOWN_FAILED_FROZEN:
- break;
- case CPU_DEAD:
- case CPU_DEAD_FROZEN:
- refresh_zone_stat_thresholds();
- vmstat_cpu_dead(cpu_to_node(cpu));
- break;
- default:
- break;
- }
- return NOTIFY_OK;
-}
-
-static struct notifier_block vmstat_notifier =
- { &vmstat_cpuup_callback, NULL, 0 };
#endif
static int __init setup_vmstat(void)
{
#ifdef CONFIG_SMP
- cpu_notifier_register_begin();
- __register_cpu_notifier(&vmstat_notifier);
+ int ret;
+
+ ret = cpuhp_setup_state_nocalls(CPUHP_MM_VMSTAT_DEAD, "mm/vmstat:dead",
+ NULL, vmstat_cpu_dead);
+ if (ret < 0)
+ pr_err("vmstat: failed to register 'dead' hotplug state\n");
+
+ ret = cpuhp_setup_state_nocalls(CPUHP_AP_ONLINE_DYN, "mm/vmstat:online",
+ vmstat_cpu_online,
+ vmstat_cpu_down_prep);
+ if (ret < 0)
+ pr_err("vmstat: failed to register 'online' hotplug state\n");
+
+ get_online_cpus();
init_cpu_node_state();
+ put_online_cpus();
start_shepherd_timer();
- cpu_notifier_register_done();
#endif
#ifdef CONFIG_PROC_FS
proc_create("buddyinfo", S_IRUGO, NULL, &fragmentation_file_operations);
--
2.10.2
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply related [flat|nested] 14+ messages in thread
* [PATCH 10/22] mm/zsmalloc: Convert to hotplug state machine
[not found] <20161126231350.10321-1-bigeasy@linutronix.de>
` (2 preceding siblings ...)
2016-11-26 23:13 ` [PATCH 09/22] mm/vmstat: Convert to hotplug state machine Sebastian Andrzej Siewior
@ 2016-11-26 23:13 ` Sebastian Andrzej Siewior
2016-11-26 23:13 ` [PATCH 11/22] mm/zswap: Convert dst-mem " Sebastian Andrzej Siewior
` (2 subsequent siblings)
6 siblings, 0 replies; 14+ messages in thread
From: Sebastian Andrzej Siewior @ 2016-11-26 23:13 UTC (permalink / raw)
To: linux-kernel
Cc: rt, tglx, Sebastian Andrzej Siewior, Minchan Kim, Nitin Gupta,
Sergey Senozhatsky, linux-mm
Install the callbacks via the state machine and let the core invoke
the callbacks on the already online CPUs.
Cc: Minchan Kim <minchan@kernel.org>
Cc: Nitin Gupta <ngupta@vflare.org>
Cc: Sergey Senozhatsky <sergey.senozhatsky.work@gmail.com>
CC: linux-mm@kvack.org
Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
---
include/linux/cpuhotplug.h | 1 +
mm/zsmalloc.c | 67 +++++++++-------------------------------------
2 files changed, 14 insertions(+), 54 deletions(-)
diff --git a/include/linux/cpuhotplug.h b/include/linux/cpuhotplug.h
index 4ebd1bc27f8d..9f29dd996088 100644
--- a/include/linux/cpuhotplug.h
+++ b/include/linux/cpuhotplug.h
@@ -64,6 +64,7 @@ enum cpuhp_state {
CPUHP_NET_IUCV_PREPARE,
CPUHP_ARM_BL_PREPARE,
CPUHP_TRACE_RB_PREPARE,
+ CPUHP_MM_ZS_PREPARE,
CPUHP_TIMERS_DEAD,
CPUHP_NOTF_ERR_INJ_PREPARE,
CPUHP_MIPS_SOC_PREPARE,
diff --git a/mm/zsmalloc.c b/mm/zsmalloc.c
index b0bc023d25c5..9cc3c0b2c2c1 100644
--- a/mm/zsmalloc.c
+++ b/mm/zsmalloc.c
@@ -1284,61 +1284,21 @@ static void __zs_unmap_object(struct mapping_area *area,
#endif /* CONFIG_PGTABLE_MAPPING */
-static int zs_cpu_notifier(struct notifier_block *nb, unsigned long action,
- void *pcpu)
+static int zs_cpu_prepare(unsigned int cpu)
{
- int ret, cpu = (long)pcpu;
struct mapping_area *area;
- switch (action) {
- case CPU_UP_PREPARE:
- area = &per_cpu(zs_map_area, cpu);
- ret = __zs_cpu_up(area);
- if (ret)
- return notifier_from_errno(ret);
- break;
- case CPU_DEAD:
- case CPU_UP_CANCELED:
- area = &per_cpu(zs_map_area, cpu);
- __zs_cpu_down(area);
- break;
- }
-
- return NOTIFY_OK;
+ area = &per_cpu(zs_map_area, cpu);
+ return __zs_cpu_up(area);
}
-static struct notifier_block zs_cpu_nb = {
- .notifier_call = zs_cpu_notifier
-};
-
-static int zs_register_cpu_notifier(void)
+static int zs_cpu_dead(unsigned int cpu)
{
- int cpu, uninitialized_var(ret);
+ struct mapping_area *area;
- cpu_notifier_register_begin();
-
- __register_cpu_notifier(&zs_cpu_nb);
- for_each_online_cpu(cpu) {
- ret = zs_cpu_notifier(NULL, CPU_UP_PREPARE, (void *)(long)cpu);
- if (notifier_to_errno(ret))
- break;
- }
-
- cpu_notifier_register_done();
- return notifier_to_errno(ret);
-}
-
-static void zs_unregister_cpu_notifier(void)
-{
- int cpu;
-
- cpu_notifier_register_begin();
-
- for_each_online_cpu(cpu)
- zs_cpu_notifier(NULL, CPU_DEAD, (void *)(long)cpu);
- __unregister_cpu_notifier(&zs_cpu_nb);
-
- cpu_notifier_register_done();
+ area = &per_cpu(zs_map_area, cpu);
+ __zs_cpu_down(area);
+ return 0;
}
static void __init init_zs_size_classes(void)
@@ -2534,10 +2494,10 @@ static int __init zs_init(void)
if (ret)
goto out;
- ret = zs_register_cpu_notifier();
-
+ ret = cpuhp_setup_state(CPUHP_MM_ZS_PREPARE, "mm/zsmalloc:prepare",
+ zs_cpu_prepare, zs_cpu_dead);
if (ret)
- goto notifier_fail;
+ goto hp_setup_fail;
init_zs_size_classes();
@@ -2549,8 +2509,7 @@ static int __init zs_init(void)
return 0;
-notifier_fail:
- zs_unregister_cpu_notifier();
+hp_setup_fail:
zsmalloc_unmount();
out:
return ret;
@@ -2562,7 +2521,7 @@ static void __exit zs_exit(void)
zpool_unregister_driver(&zs_zpool_driver);
#endif
zsmalloc_unmount();
- zs_unregister_cpu_notifier();
+ cpuhp_remove_state(CPUHP_MM_ZS_PREPARE);
zs_stat_exit();
}
--
2.10.2
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply related [flat|nested] 14+ messages in thread
* [PATCH 11/22] mm/zswap: Convert dst-mem to hotplug state machine
[not found] <20161126231350.10321-1-bigeasy@linutronix.de>
` (3 preceding siblings ...)
2016-11-26 23:13 ` [PATCH 10/22] mm/zsmalloc: " Sebastian Andrzej Siewior
@ 2016-11-26 23:13 ` Sebastian Andrzej Siewior
2016-11-26 23:13 ` [PATCH 12/22] mm/zswap: Convert pool " Sebastian Andrzej Siewior
2016-11-26 23:13 ` [PATCH 14/22] mm/compaction: Convert " Sebastian Andrzej Siewior
6 siblings, 0 replies; 14+ messages in thread
From: Sebastian Andrzej Siewior @ 2016-11-26 23:13 UTC (permalink / raw)
To: linux-kernel; +Cc: rt, tglx, Sebastian Andrzej Siewior, Seth Jennings, linux-mm
Install the callbacks via the state machine and let the core invoke
the callbacks on the already online CPUs.
Cc: Seth Jennings <sjenning@redhat.com>
Cc: linux-mm@kvack.org
Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
---
include/linux/cpuhotplug.h | 1 +
mm/zswap.c | 75 +++++++++++-----------------------------------
2 files changed, 19 insertions(+), 57 deletions(-)
diff --git a/include/linux/cpuhotplug.h b/include/linux/cpuhotplug.h
index 9f29dd996088..62f51a4e8676 100644
--- a/include/linux/cpuhotplug.h
+++ b/include/linux/cpuhotplug.h
@@ -65,6 +65,7 @@ enum cpuhp_state {
CPUHP_ARM_BL_PREPARE,
CPUHP_TRACE_RB_PREPARE,
CPUHP_MM_ZS_PREPARE,
+ CPUHP_MM_ZSWP_MEM_PREPARE,
CPUHP_TIMERS_DEAD,
CPUHP_NOTF_ERR_INJ_PREPARE,
CPUHP_MIPS_SOC_PREPARE,
diff --git a/mm/zswap.c b/mm/zswap.c
index 275b22cc8df4..b13aa5706348 100644
--- a/mm/zswap.c
+++ b/mm/zswap.c
@@ -352,70 +352,28 @@ static struct zswap_entry *zswap_entry_find_get(struct rb_root *root,
**********************************/
static DEFINE_PER_CPU(u8 *, zswap_dstmem);
-static int __zswap_cpu_dstmem_notifier(unsigned long action, unsigned long cpu)
+static int zswap_dstmem_prepare(unsigned int cpu)
{
u8 *dst;
- switch (action) {
- case CPU_UP_PREPARE:
- dst = kmalloc_node(PAGE_SIZE * 2, GFP_KERNEL, cpu_to_node(cpu));
- if (!dst) {
- pr_err("can't allocate compressor buffer\n");
- return NOTIFY_BAD;
- }
- per_cpu(zswap_dstmem, cpu) = dst;
- break;
- case CPU_DEAD:
- case CPU_UP_CANCELED:
- dst = per_cpu(zswap_dstmem, cpu);
- kfree(dst);
- per_cpu(zswap_dstmem, cpu) = NULL;
- break;
- default:
- break;
+ dst = kmalloc_node(PAGE_SIZE * 2, GFP_KERNEL, cpu_to_node(cpu));
+ if (!dst) {
+ pr_err("can't allocate compressor buffer\n");
+ return -ENOMEM;
}
- return NOTIFY_OK;
-}
-
-static int zswap_cpu_dstmem_notifier(struct notifier_block *nb,
- unsigned long action, void *pcpu)
-{
- return __zswap_cpu_dstmem_notifier(action, (unsigned long)pcpu);
-}
-
-static struct notifier_block zswap_dstmem_notifier = {
- .notifier_call = zswap_cpu_dstmem_notifier,
-};
-
-static int __init zswap_cpu_dstmem_init(void)
-{
- unsigned long cpu;
-
- cpu_notifier_register_begin();
- for_each_online_cpu(cpu)
- if (__zswap_cpu_dstmem_notifier(CPU_UP_PREPARE, cpu) ==
- NOTIFY_BAD)
- goto cleanup;
- __register_cpu_notifier(&zswap_dstmem_notifier);
- cpu_notifier_register_done();
+ per_cpu(zswap_dstmem, cpu) = dst;
return 0;
-
-cleanup:
- for_each_online_cpu(cpu)
- __zswap_cpu_dstmem_notifier(CPU_UP_CANCELED, cpu);
- cpu_notifier_register_done();
- return -ENOMEM;
}
-static void zswap_cpu_dstmem_destroy(void)
+static int zswap_dstmem_dead(unsigned int cpu)
{
- unsigned long cpu;
+ u8 *dst;
- cpu_notifier_register_begin();
- for_each_online_cpu(cpu)
- __zswap_cpu_dstmem_notifier(CPU_UP_CANCELED, cpu);
- __unregister_cpu_notifier(&zswap_dstmem_notifier);
- cpu_notifier_register_done();
+ dst = per_cpu(zswap_dstmem, cpu);
+ kfree(dst);
+ per_cpu(zswap_dstmem, cpu) = NULL;
+
+ return 0;
}
static int __zswap_cpu_comp_notifier(struct zswap_pool *pool,
@@ -1238,6 +1196,7 @@ static void __exit zswap_debugfs_exit(void) { }
static int __init init_zswap(void)
{
struct zswap_pool *pool;
+ int ret;
zswap_init_started = true;
@@ -1246,7 +1205,9 @@ static int __init init_zswap(void)
goto cache_fail;
}
- if (zswap_cpu_dstmem_init()) {
+ ret = cpuhp_setup_state(CPUHP_MM_ZSWP_MEM_PREPARE, "mm/zswap:prepare",
+ zswap_dstmem_prepare, zswap_dstmem_dead);
+ if (ret) {
pr_err("dstmem alloc failed\n");
goto dstmem_fail;
}
@@ -1267,7 +1228,7 @@ static int __init init_zswap(void)
return 0;
pool_fail:
- zswap_cpu_dstmem_destroy();
+ cpuhp_remove_state(CPUHP_MM_ZSWP_MEM_PREPARE);
dstmem_fail:
zswap_entry_cache_destroy();
cache_fail:
--
2.10.2
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply related [flat|nested] 14+ messages in thread
* [PATCH 12/22] mm/zswap: Convert pool to hotplug state machine
[not found] <20161126231350.10321-1-bigeasy@linutronix.de>
` (4 preceding siblings ...)
2016-11-26 23:13 ` [PATCH 11/22] mm/zswap: Convert dst-mem " Sebastian Andrzej Siewior
@ 2016-11-26 23:13 ` Sebastian Andrzej Siewior
2016-11-26 23:13 ` [PATCH 14/22] mm/compaction: Convert " Sebastian Andrzej Siewior
6 siblings, 0 replies; 14+ messages in thread
From: Sebastian Andrzej Siewior @ 2016-11-26 23:13 UTC (permalink / raw)
To: linux-kernel; +Cc: rt, tglx, Sebastian Andrzej Siewior, Seth Jennings, linux-mm
Install the callbacks via the state machine. Multi state is used to address the
per-pool notifier. Uppon adding of the intance the callback is invoked for all
online CPUs so the manual init can go.
Cc: Seth Jennings <sjenning@redhat.com>
Cc: linux-mm@kvack.org
Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
---
include/linux/cpuhotplug.h | 1 +
mm/zswap.c | 99 ++++++++++++++++------------------------------
2 files changed, 35 insertions(+), 65 deletions(-)
diff --git a/include/linux/cpuhotplug.h b/include/linux/cpuhotplug.h
index 62f51a4e8676..c7d0d76ef0ee 100644
--- a/include/linux/cpuhotplug.h
+++ b/include/linux/cpuhotplug.h
@@ -66,6 +66,7 @@ enum cpuhp_state {
CPUHP_TRACE_RB_PREPARE,
CPUHP_MM_ZS_PREPARE,
CPUHP_MM_ZSWP_MEM_PREPARE,
+ CPUHP_MM_ZSWP_POOL_PREPARE,
CPUHP_TIMERS_DEAD,
CPUHP_NOTF_ERR_INJ_PREPARE,
CPUHP_MIPS_SOC_PREPARE,
diff --git a/mm/zswap.c b/mm/zswap.c
index b13aa5706348..067a0d62f318 100644
--- a/mm/zswap.c
+++ b/mm/zswap.c
@@ -118,7 +118,7 @@ struct zswap_pool {
struct kref kref;
struct list_head list;
struct work_struct work;
- struct notifier_block notifier;
+ struct hlist_node node;
char tfm_name[CRYPTO_MAX_ALG_NAME];
};
@@ -376,77 +376,34 @@ static int zswap_dstmem_dead(unsigned int cpu)
return 0;
}
-static int __zswap_cpu_comp_notifier(struct zswap_pool *pool,
- unsigned long action, unsigned long cpu)
+static int zswap_cpu_comp_prepare(unsigned int cpu, struct hlist_node *node)
{
+ struct zswap_pool *pool = hlist_entry(node, struct zswap_pool, node);
struct crypto_comp *tfm;
- switch (action) {
- case CPU_UP_PREPARE:
- if (WARN_ON(*per_cpu_ptr(pool->tfm, cpu)))
- break;
- tfm = crypto_alloc_comp(pool->tfm_name, 0, 0);
- if (IS_ERR_OR_NULL(tfm)) {
- pr_err("could not alloc crypto comp %s : %ld\n",
- pool->tfm_name, PTR_ERR(tfm));
- return NOTIFY_BAD;
- }
- *per_cpu_ptr(pool->tfm, cpu) = tfm;
- break;
- case CPU_DEAD:
- case CPU_UP_CANCELED:
- tfm = *per_cpu_ptr(pool->tfm, cpu);
- if (!IS_ERR_OR_NULL(tfm))
- crypto_free_comp(tfm);
- *per_cpu_ptr(pool->tfm, cpu) = NULL;
- break;
- default:
- break;
+ if (WARN_ON(*per_cpu_ptr(pool->tfm, cpu)))
+ return 0;
+
+ tfm = crypto_alloc_comp(pool->tfm_name, 0, 0);
+ if (IS_ERR_OR_NULL(tfm)) {
+ pr_err("could not alloc crypto comp %s : %ld\n",
+ pool->tfm_name, PTR_ERR(tfm));
+ return -ENOMEM;
}
- return NOTIFY_OK;
-}
-
-static int zswap_cpu_comp_notifier(struct notifier_block *nb,
- unsigned long action, void *pcpu)
-{
- unsigned long cpu = (unsigned long)pcpu;
- struct zswap_pool *pool = container_of(nb, typeof(*pool), notifier);
-
- return __zswap_cpu_comp_notifier(pool, action, cpu);
-}
-
-static int zswap_cpu_comp_init(struct zswap_pool *pool)
-{
- unsigned long cpu;
-
- memset(&pool->notifier, 0, sizeof(pool->notifier));
- pool->notifier.notifier_call = zswap_cpu_comp_notifier;
-
- cpu_notifier_register_begin();
- for_each_online_cpu(cpu)
- if (__zswap_cpu_comp_notifier(pool, CPU_UP_PREPARE, cpu) ==
- NOTIFY_BAD)
- goto cleanup;
- __register_cpu_notifier(&pool->notifier);
- cpu_notifier_register_done();
+ *per_cpu_ptr(pool->tfm, cpu) = tfm;
return 0;
-
-cleanup:
- for_each_online_cpu(cpu)
- __zswap_cpu_comp_notifier(pool, CPU_UP_CANCELED, cpu);
- cpu_notifier_register_done();
- return -ENOMEM;
}
-static void zswap_cpu_comp_destroy(struct zswap_pool *pool)
+static int zswap_cpu_comp_dead(unsigned int cpu, struct hlist_node *node)
{
- unsigned long cpu;
+ struct zswap_pool *pool = hlist_entry(node, struct zswap_pool, node);
+ struct crypto_comp *tfm;
- cpu_notifier_register_begin();
- for_each_online_cpu(cpu)
- __zswap_cpu_comp_notifier(pool, CPU_UP_CANCELED, cpu);
- __unregister_cpu_notifier(&pool->notifier);
- cpu_notifier_register_done();
+ tfm = *per_cpu_ptr(pool->tfm, cpu);
+ if (!IS_ERR_OR_NULL(tfm))
+ crypto_free_comp(tfm);
+ *per_cpu_ptr(pool->tfm, cpu) = NULL;
+ return 0;
}
/*********************************
@@ -527,6 +484,7 @@ static struct zswap_pool *zswap_pool_create(char *type, char *compressor)
struct zswap_pool *pool;
char name[38]; /* 'zswap' + 32 char (max) num + \0 */
gfp_t gfp = __GFP_NORETRY | __GFP_NOWARN | __GFP_KSWAPD_RECLAIM;
+ int ret;
pool = kzalloc(sizeof(*pool), GFP_KERNEL);
if (!pool) {
@@ -551,7 +509,9 @@ static struct zswap_pool *zswap_pool_create(char *type, char *compressor)
goto error;
}
- if (zswap_cpu_comp_init(pool))
+ ret = cpuhp_state_add_instance(CPUHP_MM_ZSWP_POOL_PREPARE,
+ &pool->node);
+ if (ret)
goto error;
pr_debug("using %s compressor\n", pool->tfm_name);
@@ -605,7 +565,7 @@ static void zswap_pool_destroy(struct zswap_pool *pool)
{
zswap_pool_debug("destroying", pool);
- zswap_cpu_comp_destroy(pool);
+ cpuhp_state_remove_instance(CPUHP_MM_ZSWP_POOL_PREPARE, &pool->node);
free_percpu(pool->tfm);
zpool_destroy_pool(pool->zpool);
kfree(pool);
@@ -1212,6 +1172,13 @@ static int __init init_zswap(void)
goto dstmem_fail;
}
+ ret = cpuhp_setup_state_multi(CPUHP_MM_ZSWP_POOL_PREPARE,
+ "mm/zswap_pool:prepare",
+ zswap_cpu_comp_prepare,
+ zswap_cpu_comp_dead);
+ if (ret)
+ goto hp_fail;
+
pool = __zswap_pool_create_fallback();
if (!pool) {
pr_err("pool creation failed\n");
@@ -1228,6 +1195,8 @@ static int __init init_zswap(void)
return 0;
pool_fail:
+ cpuhp_remove_state_nocalls(CPUHP_MM_ZSWP_POOL_PREPARE);
+hp_fail:
cpuhp_remove_state(CPUHP_MM_ZSWP_MEM_PREPARE);
dstmem_fail:
zswap_entry_cache_destroy();
--
2.10.2
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply related [flat|nested] 14+ messages in thread
* [PATCH 14/22] mm/compaction: Convert to hotplug state machine
[not found] <20161126231350.10321-1-bigeasy@linutronix.de>
` (5 preceding siblings ...)
2016-11-26 23:13 ` [PATCH 12/22] mm/zswap: Convert pool " Sebastian Andrzej Siewior
@ 2016-11-26 23:13 ` Sebastian Andrzej Siewior
6 siblings, 0 replies; 14+ messages in thread
From: Sebastian Andrzej Siewior @ 2016-11-26 23:13 UTC (permalink / raw)
To: linux-kernel
Cc: rt, tglx, Anna-Maria Gleixner, Andrew Morton, Vlastimil Babka,
Michal Hocko, Mel Gorman, linux-mm, Sebastian Andrzej Siewior
From: Anna-Maria Gleixner <anna-maria@linutronix.de>
Install the callbacks via the state machine. Should the hotplug init fail then
no threads are spawned.
Cc: Andrew Morton <akpm@linux-foundation.org>
Cc: Vlastimil Babka <vbabka@suse.cz>
Cc: Michal Hocko <mhocko@suse.com>
Cc: Mel Gorman <mgorman@techsingularity.net>
Cc: linux-mm@kvack.org
Signed-off-by: Anna-Maria Gleixner <anna-maria@linutronix.de>
Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
---
mm/compaction.c | 31 ++++++++++++++++++-------------
1 file changed, 18 insertions(+), 13 deletions(-)
diff --git a/mm/compaction.c b/mm/compaction.c
index 0409a4ad6ea1..0d37192d9423 100644
--- a/mm/compaction.c
+++ b/mm/compaction.c
@@ -2043,33 +2043,38 @@ void kcompactd_stop(int nid)
* away, we get changed to run anywhere: as the first one comes back,
* restore their cpu bindings.
*/
-static int cpu_callback(struct notifier_block *nfb, unsigned long action,
- void *hcpu)
+static int kcompactd_cpu_online(unsigned int cpu)
{
int nid;
- if (action == CPU_ONLINE || action == CPU_ONLINE_FROZEN) {
- for_each_node_state(nid, N_MEMORY) {
- pg_data_t *pgdat = NODE_DATA(nid);
- const struct cpumask *mask;
+ for_each_node_state(nid, N_MEMORY) {
+ pg_data_t *pgdat = NODE_DATA(nid);
+ const struct cpumask *mask;
- mask = cpumask_of_node(pgdat->node_id);
+ mask = cpumask_of_node(pgdat->node_id);
- if (cpumask_any_and(cpu_online_mask, mask) < nr_cpu_ids)
- /* One of our CPUs online: restore mask */
- set_cpus_allowed_ptr(pgdat->kcompactd, mask);
- }
+ if (cpumask_any_and(cpu_online_mask, mask) < nr_cpu_ids)
+ /* One of our CPUs online: restore mask */
+ set_cpus_allowed_ptr(pgdat->kcompactd, mask);
}
- return NOTIFY_OK;
+ return 0;
}
static int __init kcompactd_init(void)
{
int nid;
+ int ret;
+
+ ret = cpuhp_setup_state_nocalls(CPUHP_AP_ONLINE_DYN,
+ "mm/compaction:online",
+ kcompactd_cpu_online, NULL);
+ if (ret < 0) {
+ pr_err("kcompactd: failed to register hotplug callbacks.\n");
+ return ret;
+ }
for_each_node_state(nid, N_MEMORY)
kcompactd_run(nid);
- hotcpu_notifier(cpu_callback, 0);
return 0;
}
subsys_initcall(kcompactd_init)
--
2.10.2
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in
the body to majordomo@kvack.org. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"dont@kvack.org"> email@kvack.org </a>
^ permalink raw reply related [flat|nested] 14+ messages in thread