sched: walt: properly account for migrating mvp task

Currently, every time a task migrates while running, the enqueue resets
the slice time accounted thus far, i.e. enqueue resets
sum_exec_snapshot. There is a potential for a frequently active
migrating task to get infinite slice.

Fix this by ensuring total_exec gets updated regardless of SLICE
threshold is crossed. Having a non zero total_exec will make
enqueue skip taking a snapshot.

Also we need to track two snapshots of sum_exec_runtime, one for total
and one for slice. The total snapshot will be taken upon task's enqueue
after it wakes up from sleep while the slice snapshot advances everytime
the SLICE threshold is crossed. This scheme helps us track the total
time the task ran since wakeup and the total time it ran in the slice.

The snapshot however is the origin for accounting time towards SLICE,
hence it should not be updated as long runtime is within SLICE. Once
SLICE is crossed, snapshot should be updated for tracking the runtime
towards the next SLICE period.

Change-Id: I3cf82570c3224b2c9a40b278d2c9baa059216bc3
Signed-off-by: Abhijeet Dharmapurikar <quic_adharmap@quicinc.com>
Signed-off-by: Sai Harshini Nimmala <quic_snimmala@quicinc.com>
This commit is contained in:
Sai Harshini Nimmala 2022-01-31 21:59:23 -08:00 committed by Rishabh Bhatnagar
parent ac78c5792b
commit fb76acffb0
3 changed files with 20 additions and 14 deletions

View File

@ -1,6 +1,7 @@
/* SPDX-License-Identifier: GPL-2.0-only */
/*
* Copyright (c) 2021, The Linux Foundation. All rights reserved.
* Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
*/
#ifndef _LINUX_SCHED_WALT_H
@ -119,7 +120,8 @@ struct walt_task_struct {
int prev_on_rq;
int prev_on_rq_cpu;
struct list_head mvp_list;
u64 sum_exec_snapshot;
u64 sum_exec_snapshot_for_slice;
u64 sum_exec_snapshot_for_total;
u64 total_exec;
int mvp_prio;
int cidx;

View File

@ -2243,7 +2243,8 @@ static void init_new_task_load(struct task_struct *p)
wts->unfilter = sysctl_sched_task_unfilter_period;
INIT_LIST_HEAD(&wts->mvp_list);
wts->sum_exec_snapshot = 0;
wts->sum_exec_snapshot_for_slice = 0;
wts->sum_exec_snapshot_for_total = 0;
wts->total_exec = 0;
wts->mvp_prio = WALT_NOT_MVP;
wts->cidx = 0;

View File

@ -1084,7 +1084,7 @@ static void walt_cfs_account_mvp_runtime(struct rq *rq, struct task_struct *curr
{
struct walt_rq *wrq = (struct walt_rq *) rq->android_vendor_data1;
struct walt_task_struct *wts = (struct walt_task_struct *) curr->android_vendor_data1;
s64 delta;
u64 slice;
unsigned int limit;
lockdep_assert_held(&rq->__lock);
@ -1099,24 +1099,26 @@ static void walt_cfs_account_mvp_runtime(struct rq *rq, struct task_struct *curr
if (!(rq->clock_update_flags & RQCF_UPDATED))
update_rq_clock(rq);
/* sum_exec_snapshot can be ahead. See below increment */
delta = curr->se.sum_exec_runtime - wts->sum_exec_snapshot;
if (delta < 0)
delta = 0;
if (curr->se.sum_exec_runtime > wts->sum_exec_snapshot_for_total)
wts->total_exec = curr->se.sum_exec_runtime - wts->sum_exec_snapshot_for_total;
else
delta += rq_clock_task(rq) - curr->se.exec_start;
wts->total_exec = 0;
if (curr->se.sum_exec_runtime > wts->sum_exec_snapshot_for_slice)
slice = curr->se.sum_exec_runtime - wts->sum_exec_snapshot_for_slice;
else
slice = 0;
/* slice is not expired */
if (delta < WALT_MVP_SLICE)
if (slice < WALT_MVP_SLICE)
return;
wts->sum_exec_snapshot_for_slice = curr->se.sum_exec_runtime;
/*
* slice is expired, check if we have to deactivate the
* MVP task, otherwise requeue the task in the list so
* that other MVP tasks gets a chance.
*/
wts->sum_exec_snapshot += delta;
wts->total_exec += delta;
limit = walt_cfs_mvp_task_limit(curr);
if (wts->total_exec > limit) {
@ -1165,9 +1167,10 @@ void walt_cfs_enqueue_task(struct rq *rq, struct task_struct *p)
* task runtime snapshot. From now onwards we use this point as a
* baseline to enforce the slice and demotion.
*/
if (!wts->total_exec) /* queue after sleep */
wts->sum_exec_snapshot = p->se.sum_exec_runtime;
if (!wts->total_exec) /* queue after sleep */ {
wts->sum_exec_snapshot_for_total = p->se.sum_exec_runtime;
wts->sum_exec_snapshot_for_slice = p->se.sum_exec_runtime;
}
}
void walt_cfs_dequeue_task(struct rq *rq, struct task_struct *p)