E.7.1.1 Task Interface
Keywords: perfbook_html

###
E.7.1.1 Task Interface

When a given CPU enters dynticks-idle mode because it has no more tasks to run, it invokes rcu_enter_nohz():

      1 static inline void rcu_enter_nohz(void)
      2 {
      3   mb();
      4   __get_cpu_var(dynticks_progress_counter)++;
      5   WARN_ON(__get_cpu_var(dynticks_progress_counter) & 0x1);
      6 }

This function simply increments dynticks_progress_counter and checks that the result is even, but first executing a memory barrier to ensure that any other CPU that sees the new value of dynticks_progress_counter will also see the completion of any prior RCU read-side critical sections.

Similarly, when a CPU that is in dynticks-idle mode prepares to start executing a newly runnable task, it invokes rcu_exit_nohz:

      1 static inline void rcu_exit_nohz(void)
      2 {
      3   __get_cpu_var(dynticks_progress_counter)++;
      4   mb();
      5   WARN_ON(!(__get_cpu_var(dynticks_progress_counter) &
      6             0x1));
      7 }

This function again increments dynticks_progress_counter, but follows it with a memory barrier to ensure that if any other CPU sees the result of any subsequent RCU read-side critical section, then that other CPU will also see the incremented value of dynticks_progress_counter. Finally, rcu_exit_nohz() checks that the result of the increment is an odd value.

The rcu_enter_nohz() and rcu_exit_nohz functions handle the case where a CPU enters and exits dynticks-idle mode due to task execution, but does not handle interrupts, which are covered in the following section.