linux/arch/powerpc/kernel/idle.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0-or-later
   2/*
   3 * Idle daemon for PowerPC.  Idle daemon will handle any action
   4 * that needs to be taken when the system becomes idle.
   5 *
   6 * Originally written by Cort Dougan (cort@cs.nmt.edu).
   7 * Subsequent 32-bit hacking by Tom Rini, Armin Kuster,
   8 * Paul Mackerras and others.
   9 *
  10 * iSeries supported added by Mike Corrigan <mikejc@us.ibm.com>
  11 *
  12 * Additional shared processor, SMT, and firmware support
  13 *    Copyright (c) 2003 Dave Engebretsen <engebret@us.ibm.com>
  14 *
  15 * 32-bit and 64-bit versions merged by Paul Mackerras <paulus@samba.org>
  16 */
  17
  18#include <linux/sched.h>
  19#include <linux/kernel.h>
  20#include <linux/smp.h>
  21#include <linux/cpu.h>
  22#include <linux/sysctl.h>
  23#include <linux/tick.h>
  24
  25#include <asm/processor.h>
  26#include <asm/cputable.h>
  27#include <asm/time.h>
  28#include <asm/machdep.h>
  29#include <asm/runlatch.h>
  30#include <asm/smp.h>
  31
  32
  33unsigned long cpuidle_disable = IDLE_NO_OVERRIDE;
  34EXPORT_SYMBOL(cpuidle_disable);
  35
  36static int __init powersave_off(char *arg)
  37{
  38        ppc_md.power_save = NULL;
  39        cpuidle_disable = IDLE_POWERSAVE_OFF;
  40        return 0;
  41}
  42__setup("powersave=off", powersave_off);
  43
  44#ifdef CONFIG_HOTPLUG_CPU
  45void arch_cpu_idle_dead(void)
  46{
  47        sched_preempt_enable_no_resched();
  48        cpu_die();
  49}
  50#endif
  51
  52void arch_cpu_idle(void)
  53{
  54        ppc64_runlatch_off();
  55
  56        if (ppc_md.power_save) {
  57                ppc_md.power_save();
  58                /*
  59                 * Some power_save functions return with
  60                 * interrupts enabled, some don't.
  61                 */
  62                if (irqs_disabled())
  63                        local_irq_enable();
  64        } else {
  65                local_irq_enable();
  66                /*
  67                 * Go into low thread priority and possibly
  68                 * low power mode.
  69                 */
  70                HMT_low();
  71                HMT_very_low();
  72        }
  73
  74        HMT_medium();
  75        ppc64_runlatch_on();
  76}
  77
  78int powersave_nap;
  79
  80#ifdef CONFIG_SYSCTL
  81/*
  82 * Register the sysctl to set/clear powersave_nap.
  83 */
  84static struct ctl_table powersave_nap_ctl_table[] = {
  85        {
  86                .procname       = "powersave-nap",
  87                .data           = &powersave_nap,
  88                .maxlen         = sizeof(int),
  89                .mode           = 0644,
  90                .proc_handler   = proc_dointvec,
  91        },
  92        {}
  93};
  94static struct ctl_table powersave_nap_sysctl_root[] = {
  95        {
  96                .procname       = "kernel",
  97                .mode           = 0555,
  98                .child          = powersave_nap_ctl_table,
  99        },
 100        {}
 101};
 102
 103static int __init
 104register_powersave_nap_sysctl(void)
 105{
 106        register_sysctl_table(powersave_nap_sysctl_root);
 107
 108        return 0;
 109}
 110__initcall(register_powersave_nap_sysctl);
 111#endif
 112