root/arch/powerpc/platforms/pasemi/idle.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. pasemi_system_reset_exception
  2. pasemi_idle_init
  3. idle_param

   1 // SPDX-License-Identifier: GPL-2.0-only
   2 /*
   3  * Copyright (C) 2006-2007 PA Semi, Inc
   4  *
   5  * Maintained by: Olof Johansson <olof@lixom.net>
   6  */
   7 
   8 #undef DEBUG
   9 
  10 #include <linux/kernel.h>
  11 #include <linux/string.h>
  12 #include <linux/irq.h>
  13 
  14 #include <asm/machdep.h>
  15 #include <asm/reg.h>
  16 #include <asm/smp.h>
  17 
  18 #include "pasemi.h"
  19 
  20 struct sleep_mode {
  21         char *name;
  22         void (*entry)(void);
  23 };
  24 
  25 static struct sleep_mode modes[] = {
  26         { .name = "spin", .entry = &idle_spin },
  27         { .name = "doze", .entry = &idle_doze },
  28 };
  29 
  30 static int current_mode = 0;
  31 
  32 static int pasemi_system_reset_exception(struct pt_regs *regs)
  33 {
  34         /* If we were woken up from power savings, we need to return
  35          * to the calling function, since nip is not saved across
  36          * all modes.
  37          */
  38 
  39         if (regs->msr & SRR1_WAKEMASK)
  40                 regs->nip = regs->link;
  41 
  42         switch (regs->msr & SRR1_WAKEMASK) {
  43         case SRR1_WAKEDEC:
  44                 set_dec(1);
  45         case SRR1_WAKEEE:
  46                 /*
  47                  * Handle these when interrupts get re-enabled and we take
  48                  * them as regular exceptions. We are in an NMI context
  49                  * and can't handle these here.
  50                  */
  51                 break;
  52         default:
  53                 /* do system reset */
  54                 return 0;
  55         }
  56 
  57         /* Set higher astate since we come out of power savings at 0 */
  58         restore_astate(hard_smp_processor_id());
  59 
  60         /* everything handled */
  61         regs->msr |= MSR_RI;
  62         return 1;
  63 }
  64 
  65 static int __init pasemi_idle_init(void)
  66 {
  67 #ifndef CONFIG_PPC_PASEMI_CPUFREQ
  68         pr_warn("No cpufreq driver, powersavings modes disabled\n");
  69         current_mode = 0;
  70 #endif
  71 
  72         ppc_md.system_reset_exception = pasemi_system_reset_exception;
  73         ppc_md.power_save = modes[current_mode].entry;
  74         pr_info("Using PA6T idle loop (%s)\n", modes[current_mode].name);
  75 
  76         return 0;
  77 }
  78 machine_late_initcall(pasemi, pasemi_idle_init);
  79 
  80 static int __init idle_param(char *p)
  81 {
  82         int i;
  83         for (i = 0; i < ARRAY_SIZE(modes); i++) {
  84                 if (!strcmp(modes[i].name, p)) {
  85                         current_mode = i;
  86                         break;
  87                 }
  88         }
  89         return 0;
  90 }
  91 
  92 early_param("idle", idle_param);

/* [<][>][^][v][top][bottom][index][help] */