History

sched/numa: Allow a floating imbalance between NUMA nodes

Currently, an imbalance is only allowed when a destination node is almost completely idle. This solved one basic class of problems and was the cautious approach. This patch revisits the possibility that NUMA nodes can be imbalanced until 25% of the CPUs are occupied. The reasoning behind 25% is somewhat superficial -- it's half the cores when HT is enabled. At higher utilisations, balancing should continue as normal and keep things even until scheduler domains are fully busy or over utilised. Note that this is not expected to be a universal win. Any benchmark that prefers spreading as wide as possible with limited communication will favour the old behaviour as there is more memory bandwidth. Workloads that communicate heavily in pairs such as netperf or tbench benefit. For the tests I ran, the vast majority of workloads saw a benefit so it seems to be a worthwhile trade-off.

Mel Gorman committed 5 years ago

Commit 7d2b5dd1 parent 5c339001 file · +11 −10Browse files

Unified · Split

kernel/sched/fair.c+11−10
@@ -1559,7 +1559,8 @@ struct task_numa_env { · 1558 unmodified lines
15591559 static unsigned long cpu_load(struct rq *rq);
15601560 static unsigned long cpu_runnable(struct rq *rq);
15611561 static unsigned long cpu_util(int cpu);
1562−static inline long adjust_numa_imbalance(int imbalance, int dst_running);
1562+static inline long adjust_numa_imbalance(int imbalance,
1563+ int dst_running, int dst_weight);
15631564
15641565 static inline enum
15651566 numa_type numa_classify(unsigned int imbalance_pct,
@@ -1939,7 +1940,8 @@ static void task_numa_find_cpu(struct task_numa_env *env, · 373 unmodified lines
19391940 src_running = env->src_stats.nr_running - 1;
19401941 dst_running = env->dst_stats.nr_running + 1;
19411942 imbalance = max(0, dst_running - src_running);
1942− imbalance = adjust_numa_imbalance(imbalance, dst_running);
1943+ imbalance = adjust_numa_imbalance(imbalance, dst_running,
1944+ env->dst_stats.weight);
19431945
19441946 /* Use idle CPU if there is no imbalance */
19451947 if (!imbalance) {
@@ -8995,16 +8997,14 @@ next_group: · 7049 unmodified lines
89958997
89968998 #define NUMA_IMBALANCE_MIN 2
89978999
8998−static inline long adjust_numa_imbalance(int imbalance, int dst_running)
9000+static inline long adjust_numa_imbalance(int imbalance,
9001+ int dst_running, int dst_weight)
89999002 {
9000− unsigned int imbalance_min;
9001−
90029003 /*
90039004 * Allow a small imbalance based on a simple pair of communicating
9004− * tasks that remain local when the source domain is almost idle.
9005+ * tasks that remain local when the destination is lightly loaded.
90059006 */
9006− imbalance_min = NUMA_IMBALANCE_MIN;
9007− if (dst_running <= imbalance_min)
9007+ if (dst_running < (dst_weight >> 2) && imbalance <= NUMA_IMBALANCE_MIN)
90089008 return 0;
90099009
90109010 return imbalance;
@@ -9106,9 +9106,10 @@ static inline void calculate_imbalance(struct lb_env *env, struct sd_lb_stats *s · 95 unmodified lines
91069106 }
91079107
91089108 /* Consider allowing a small imbalance between NUMA groups */
9109− if (env->sd->flags & SD_NUMA)
9109+ if (env->sd->flags & SD_NUMA) {
91109110 env->imbalance = adjust_numa_imbalance(env->imbalance,
9111− busiest->sum_nr_running);
9111+ busiest->sum_nr_running, busiest->group_weight);
9112+ }
91129113
91139114 return;
91149115 }

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t