Question

I am looking at the code the update_curr_rt function in /kernel/sched/rt.c of Real Time scheduler. Could someone please explain how it works?

static void update_curr_rt(struct rq *rq)
{
    struct task_struct *curr = rq->curr;
    struct sched_rt_entity *rt_se = &curr->rt;
    struct rt_rq *rt_rq = rt_rq_of_se(rt_se);
    u64 delta_exec; // Time difference (???)

    if (curr->sched_class != &rt_sched_class)
        return;
    // check if sched class is Real-Time sched class
    delta_exec = rq->clock_task - curr->se.exec_start;
    if (unlikely((s64)delta_exec <= 0))
        return;
    // ??? 
    schedstat_set(curr->se.statistics.exec_max,
              max(curr->se.statistics.exec_max, delta_exec));
    // I am assuming that se.sum_exec_runtime is total time task ran
    // and we add time difference to 
    curr->se.sum_exec_runtime += delta_exec;
    // can be skipped, has to do with threads
    account_group_exec_runtime(curr, delta_exec);
    // reset start time
    curr->se.exec_start = rq->clock_task;
    cpuacct_charge(curr, delta_exec);
    // I guess it calculates average ran time of the task
    sched_rt_avg_update(rq, delta_exec);
    // can be skipped
    if (!rt_bandwidth_enabled())
        return;
    // ??? Nothing makes sense for code below
    for_each_sched_rt_entity(rt_se) {
        rt_rq = rt_rq_of_se(rt_se);

        if (sched_rt_runtime(rt_rq) != RUNTIME_INF) {
            raw_spin_lock(&rt_rq->rt_runtime_lock);
            rt_rq->rt_time += delta_exec;
            if (sched_rt_runtime_exceeded(rt_rq))
                resched_task(curr);
            raw_spin_unlock(&rt_rq->rt_runtime_lock);
        }
    }
}
Was it helpful?

Solution

I would highly suggest you explore the wonders of cscope and/or grok. Where you can type in or click on an identifier and see the definition.

This is classic linux code: compact, to the point and pretty readable. The use of some macros makes it a little harder to understand, but everything has meaningful names.

For the part where you said 'nothing makes sense': for_each_sched_rt_entity is a macro that expands to a for loop. It makes the code more compact but harder to understand. Basically, if any of the rq's in our task have run out of run time then the task is tossed back to the scheduler to set it up to run again some other time.

Easy peasy.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top