Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit ded4c87a authored by Linux Build Service Account's avatar Linux Build Service Account Committed by Gerrit - the friendly Code Review server
Browse files

Merge "sched: Avoid pulling big tasks to the little cluster during load balance"

parents 76736228 70f7aae2
Loading
Loading
Loading
Loading
+24 −4
Original line number Diff line number Diff line
@@ -5774,6 +5774,7 @@ static unsigned long __read_mostly max_load_balance_interval = HZ/10;
#define LBF_IGNORE_SMALL_TASKS 0x08
#define LBF_PWR_ACTIVE_BALANCE 0x10
#define LBF_SCHED_BOOST 0x20
#define LBF_IGNORE_BIG_TASKS 0x40

struct lb_env {
	struct sched_domain	*sd;
@@ -5856,6 +5857,7 @@ static
int can_migrate_task(struct task_struct *p, struct lb_env *env)
{
	int tsk_cache_hot = 0;
	int twf;
	/*
	 * We do not migrate tasks that are:
	 * 1) throttled_lb_pair, or
@@ -5874,8 +5876,22 @@ int can_migrate_task(struct task_struct *p, struct lb_env *env)
	if (env->flags & LBF_IGNORE_SMALL_TASKS && is_small_task(p))
		return 0;

	if (!task_will_fit(p, env->dst_cpu) &&
			env->busiest_nr_running <= env->busiest_grp_capacity)
	twf = task_will_fit(p, env->dst_cpu);

	/*
	 * Attempt to not pull tasks that don't fit. We may get lucky and find
	 * one that actually fits.
	 */
	if (env->flags & LBF_IGNORE_BIG_TASKS && !twf)
		return 0;

	/*
	 * Group imbalance can sometimes cause work to be pulled across groups
	 * even though the group could have managed the imbalance on its own.
	 * Prevent inter-cluster migrations for big tasks when the number of
	 * tasks is lower than the capacity of the group.
	 */
	if (!twf && env->busiest_nr_running <= env->busiest_grp_capacity)
		return 0;

	if (!cpumask_test_cpu(env->dst_cpu, tsk_cpus_allowed(p))) {
@@ -5989,6 +6005,9 @@ static int move_tasks(struct lb_env *env)

	if (capacity(env->dst_rq) > capacity(env->src_rq))
		env->flags |= LBF_IGNORE_SMALL_TASKS;
	else if (capacity(env->dst_rq) < capacity(env->src_rq) &&
							!sched_boost())
		env->flags |= LBF_IGNORE_BIG_TASKS;

redo:
	while (!list_empty(tasks)) {
@@ -6044,9 +6063,10 @@ next:
		list_move_tail(&p->se.group_node, tasks);
	}

	if (env->flags & LBF_IGNORE_SMALL_TASKS && !pulled) {
	if (env->flags & (LBF_IGNORE_SMALL_TASKS | LBF_IGNORE_BIG_TASKS)
							     && !pulled) {
		tasks = &env->src_rq->cfs_tasks;
		env->flags &= ~LBF_IGNORE_SMALL_TASKS;
		env->flags &= ~(LBF_IGNORE_SMALL_TASKS | LBF_IGNORE_BIG_TASKS);
		env->loop = orig_loop;
		goto redo;
	}