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

Commit 3206cd0e authored by Pavankumar Kondeti's avatar Pavankumar Kondeti
Browse files

sched: core_ctl: Add core_ctl_notifier_register()



Add a notifier API to register for the number of big tasks and default
related thread group load. The notifications are sent when a WALT
window is rolled over. Since the window rollover happens from a IRQ
work, an atomic notifier chain is used.

Change-Id: I74ad038a475cba7282753b6d8079d7414f6d5f87
Signed-off-by: default avatarPavankumar Kondeti <pkondeti@codeaurora.org>
parent 0a3dced5
Loading
Loading
Loading
Loading
+10 −1
Original line number Diff line number Diff line
/*
 * Copyright (c) 2016, The Linux Foundation. All rights reserved.
 * Copyright (c) 2016, 2018, The Linux Foundation. All rights reserved.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 and
@@ -14,14 +14,23 @@
#ifndef __CORE_CTL_H
#define __CORE_CTL_H

struct core_ctl_notif_data {
	unsigned int nr_big;
	unsigned int coloc_load_pct;
};

#ifdef CONFIG_SCHED_CORE_CTL
void core_ctl_check(u64 wallclock);
int core_ctl_set_boost(bool boost);
void core_ctl_notifier_register(struct notifier_block *n);
void core_ctl_notifier_unregister(struct notifier_block *n);
#else
static inline void core_ctl_check(u64 wallclock) {}
static inline int core_ctl_set_boost(bool boost)
{
	return 0;
}
static inline void core_ctl_notifier_register(struct notifier_block *n) {}
static inline void core_ctl_notifier_unregister(struct notifier_block *n) {}
#endif
#endif
+39 −0
Original line number Diff line number Diff line
@@ -21,6 +21,7 @@
#include <linux/sched/rt.h>
#include <linux/syscore_ops.h>
#include <uapi/linux/sched/types.h>
#include <linux/sched/core_ctl.h>

#include <trace/events/sched.h>
#include "sched.h"
@@ -81,6 +82,9 @@ static void apply_need(struct cluster_data *state);
static void wake_up_core_ctl_thread(struct cluster_data *state);
static bool initialized;

ATOMIC_NOTIFIER_HEAD(core_ctl_notifier);
static unsigned int last_nr_big;

static unsigned int get_active_cpu_count(const struct cluster_data *cluster);
static void cpuset_next(struct cluster_data *cluster);

@@ -660,6 +664,7 @@ static void update_running_avg(void)
	}
	spin_unlock_irqrestore(&state_lock, flags);

	last_nr_big = big_avg;
	walt_rotation_checkpoint(big_avg);
}

@@ -851,6 +856,38 @@ int core_ctl_set_boost(bool boost)
}
EXPORT_SYMBOL(core_ctl_set_boost);

void core_ctl_notifier_register(struct notifier_block *n)
{
	atomic_notifier_chain_register(&core_ctl_notifier, n);
}

void core_ctl_notifier_unregister(struct notifier_block *n)
{
	atomic_notifier_chain_unregister(&core_ctl_notifier, n);
}

static void core_ctl_call_notifier(void)
{
	struct core_ctl_notif_data ndata;
	struct notifier_block *nb;

	/*
	 * Don't bother querying the stats when the notifier
	 * chain is empty.
	 */
	rcu_read_lock();
	nb = rcu_dereference_raw(core_ctl_notifier.head);
	rcu_read_unlock();

	if (!nb)
		return;

	ndata.nr_big = last_nr_big;
	ndata.coloc_load_pct = walt_get_default_coloc_group_load();

	atomic_notifier_call_chain(&core_ctl_notifier, 0, &ndata);
}

void core_ctl_check(u64 window_start)
{
	int cpu;
@@ -886,6 +923,8 @@ void core_ctl_check(u64 window_start)
		if (eval_need(cluster))
			wake_up_core_ctl_thread(cluster);
	}

	core_ctl_call_notifier();
}

static void move_cpu_lru(struct cpu_data *cpu_data)