diff options
-rw-r--r-- | kernel/sched/fair.c | 22 | ||||
-rw-r--r-- | kernel/sched/sched.h | 1 |
2 files changed, 23 insertions, 0 deletions
diff --git a/kernel/sched/fair.c b/kernel/sched/fair.c index f808ddf2a868..3b0b75de1141 100644 --- a/kernel/sched/fair.c +++ b/kernel/sched/fair.c | |||
@@ -1514,6 +1514,21 @@ struct task_numa_env { | |||
1514 | static void task_numa_assign(struct task_numa_env *env, | 1514 | static void task_numa_assign(struct task_numa_env *env, |
1515 | struct task_struct *p, long imp) | 1515 | struct task_struct *p, long imp) |
1516 | { | 1516 | { |
1517 | struct rq *rq = cpu_rq(env->dst_cpu); | ||
1518 | |||
1519 | /* Bail out if run-queue part of active NUMA balance. */ | ||
1520 | if (xchg(&rq->numa_migrate_on, 1)) | ||
1521 | return; | ||
1522 | |||
1523 | /* | ||
1524 | * Clear previous best_cpu/rq numa-migrate flag, since task now | ||
1525 | * found a better CPU to move/swap. | ||
1526 | */ | ||
1527 | if (env->best_cpu != -1) { | ||
1528 | rq = cpu_rq(env->best_cpu); | ||
1529 | WRITE_ONCE(rq->numa_migrate_on, 0); | ||
1530 | } | ||
1531 | |||
1517 | if (env->best_task) | 1532 | if (env->best_task) |
1518 | put_task_struct(env->best_task); | 1533 | put_task_struct(env->best_task); |
1519 | if (p) | 1534 | if (p) |
@@ -1569,6 +1584,9 @@ static void task_numa_compare(struct task_numa_env *env, | |||
1569 | long moveimp = imp; | 1584 | long moveimp = imp; |
1570 | int dist = env->dist; | 1585 | int dist = env->dist; |
1571 | 1586 | ||
1587 | if (READ_ONCE(dst_rq->numa_migrate_on)) | ||
1588 | return; | ||
1589 | |||
1572 | rcu_read_lock(); | 1590 | rcu_read_lock(); |
1573 | cur = task_rcu_dereference(&dst_rq->curr); | 1591 | cur = task_rcu_dereference(&dst_rq->curr); |
1574 | if (cur && ((cur->flags & PF_EXITING) || is_idle_task(cur))) | 1592 | if (cur && ((cur->flags & PF_EXITING) || is_idle_task(cur))) |
@@ -1710,6 +1728,7 @@ static int task_numa_migrate(struct task_struct *p) | |||
1710 | .best_cpu = -1, | 1728 | .best_cpu = -1, |
1711 | }; | 1729 | }; |
1712 | struct sched_domain *sd; | 1730 | struct sched_domain *sd; |
1731 | struct rq *best_rq; | ||
1713 | unsigned long taskweight, groupweight; | 1732 | unsigned long taskweight, groupweight; |
1714 | int nid, ret, dist; | 1733 | int nid, ret, dist; |
1715 | long taskimp, groupimp; | 1734 | long taskimp, groupimp; |
@@ -1811,14 +1830,17 @@ static int task_numa_migrate(struct task_struct *p) | |||
1811 | */ | 1830 | */ |
1812 | p->numa_scan_period = task_scan_start(p); | 1831 | p->numa_scan_period = task_scan_start(p); |
1813 | 1832 | ||
1833 | best_rq = cpu_rq(env.best_cpu); | ||
1814 | if (env.best_task == NULL) { | 1834 | if (env.best_task == NULL) { |
1815 | ret = migrate_task_to(p, env.best_cpu); | 1835 | ret = migrate_task_to(p, env.best_cpu); |
1836 | WRITE_ONCE(best_rq->numa_migrate_on, 0); | ||
1816 | if (ret != 0) | 1837 | if (ret != 0) |
1817 | trace_sched_stick_numa(p, env.src_cpu, env.best_cpu); | 1838 | trace_sched_stick_numa(p, env.src_cpu, env.best_cpu); |
1818 | return ret; | 1839 | return ret; |
1819 | } | 1840 | } |
1820 | 1841 | ||
1821 | ret = migrate_swap(p, env.best_task, env.best_cpu, env.src_cpu); | 1842 | ret = migrate_swap(p, env.best_task, env.best_cpu, env.src_cpu); |
1843 | WRITE_ONCE(best_rq->numa_migrate_on, 0); | ||
1822 | 1844 | ||
1823 | if (ret != 0) | 1845 | if (ret != 0) |
1824 | trace_sched_stick_numa(p, env.src_cpu, task_cpu(env.best_task)); | 1846 | trace_sched_stick_numa(p, env.src_cpu, task_cpu(env.best_task)); |
diff --git a/kernel/sched/sched.h b/kernel/sched/sched.h index 4a2e8cae63c4..0b9161241bda 100644 --- a/kernel/sched/sched.h +++ b/kernel/sched/sched.h | |||
@@ -783,6 +783,7 @@ struct rq { | |||
783 | #ifdef CONFIG_NUMA_BALANCING | 783 | #ifdef CONFIG_NUMA_BALANCING |
784 | unsigned int nr_numa_running; | 784 | unsigned int nr_numa_running; |
785 | unsigned int nr_preferred_running; | 785 | unsigned int nr_preferred_running; |
786 | unsigned int numa_migrate_on; | ||
786 | #endif | 787 | #endif |
787 | #define CPU_LOAD_IDX_MAX 5 | 788 | #define CPU_LOAD_IDX_MAX 5 |
788 | unsigned long cpu_load[CPU_LOAD_IDX_MAX]; | 789 | unsigned long cpu_load[CPU_LOAD_IDX_MAX]; |