197a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King/* 297a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * linux/arch/arm/mach-realview/hotplug.c 397a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * 497a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * Copyright (C) 2002 ARM Ltd. 597a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * All Rights Reserved 697a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * 797a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * This program is free software; you can redistribute it and/or modify 897a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * it under the terms of the GNU General Public License version 2 as 997a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * published by the Free Software Foundation. 1097a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King */ 1197a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King#include <linux/kernel.h> 1297a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King#include <linux/errno.h> 1397a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King#include <linux/smp.h> 1497a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King 1515d07dc9c59eae51219c40253bdf920f62bb10f2Russell King#include <asm/cp15.h> 16eb50439b92b6298bf209a982f295ba9c0f7cb30bWill Deacon#include <asm/smp_plat.h> 178aa2da872a492a2196397603ed756a4c48677122Harry Fearnhamm 1897a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell Kingstatic inline void cpu_enter_lowpower(void) 1997a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King{ 2097a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King unsigned int v; 2197a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King 228aa2da872a492a2196397603ed756a4c48677122Harry Fearnhamm asm volatile( 2397a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " mcr p15, 0, %1, c7, c5, 0\n" 2497a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " mcr p15, 0, %1, c7, c10, 4\n" 2597a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King /* 2697a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * Turn off coherency 2797a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King */ 2897a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " mrc p15, 0, %0, c1, c0, 1\n" 2997a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " bic %0, %0, #0x20\n" 3097a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " mcr p15, 0, %0, c1, c0, 1\n" 3197a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " mrc p15, 0, %0, c1, c0, 0\n" 32e3d9c625f5e4158014e041f492b46e38ad10987eRussell King " bic %0, %0, %2\n" 3397a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " mcr p15, 0, %0, c1, c0, 0\n" 3497a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King : "=&r" (v) 35e3d9c625f5e4158014e041f492b46e38ad10987eRussell King : "r" (0), "Ir" (CR_C) 3697a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King : "cc"); 3797a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King} 3897a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King 3997a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell Kingstatic inline void cpu_leave_lowpower(void) 4097a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King{ 4197a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King unsigned int v; 4297a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King 4397a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King asm volatile( "mrc p15, 0, %0, c1, c0, 0\n" 44e3d9c625f5e4158014e041f492b46e38ad10987eRussell King " orr %0, %0, %1\n" 4597a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " mcr p15, 0, %0, c1, c0, 0\n" 4697a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " mrc p15, 0, %0, c1, c0, 1\n" 4797a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " orr %0, %0, #0x20\n" 4897a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King " mcr p15, 0, %0, c1, c0, 1\n" 4997a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King : "=&r" (v) 50e3d9c625f5e4158014e041f492b46e38ad10987eRussell King : "Ir" (CR_C) 5197a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King : "cc"); 5297a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King} 5397a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King 54d4450261e546953c4a1ce8b48e29164a57c6ed33Russell Kingstatic inline void platform_do_lowpower(unsigned int cpu, int *spurious) 5597a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King{ 5697a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King /* 5797a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * there is no power-control hardware on this platform, so all 5897a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * we can do is put the core into WFI; this is safe as the calling 5997a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * code will have already disabled interrupts 6097a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King */ 6197a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King for (;;) { 6297a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King /* 6397a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * here's the WFI 6497a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King */ 6597a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King asm(".word 0xe320f003\n" 6697a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King : 6797a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King : 6897a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King : "memory", "cc"); 6997a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King 704a139b64703115e41e1a4e16ebf7eb93d0a0e349Will Deacon if (pen_release == cpu_logical_map(cpu)) { 7197a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King /* 7297a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * OK, proper wakeup, we're done 7397a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King */ 7497a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King break; 7597a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King } 7697a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King 7797a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King /* 78d4450261e546953c4a1ce8b48e29164a57c6ed33Russell King * Getting here, means that we have come out of WFI without 7997a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * having been woken up - this shouldn't happen 8097a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * 81d4450261e546953c4a1ce8b48e29164a57c6ed33Russell King * Just note it happening - when we're woken, we can report 82d4450261e546953c4a1ce8b48e29164a57c6ed33Russell King * its occurrence. 8397a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King */ 84d4450261e546953c4a1ce8b48e29164a57c6ed33Russell King (*spurious)++; 8597a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King } 8697a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King} 8797a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King 8897a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King/* 8997a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * platform-specific code to shutdown a CPU 9097a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * 9197a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * Called with IRQs disabled 9297a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King */ 933695adc2fdaf3ad1881e0dd3e3422e5e141abd7dMarc Zyngiervoid __ref realview_cpu_die(unsigned int cpu) 9497a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King{ 95d4450261e546953c4a1ce8b48e29164a57c6ed33Russell King int spurious = 0; 96d4450261e546953c4a1ce8b48e29164a57c6ed33Russell King 9797a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King /* 9897a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * we're ready for shutdown now, so do it 9997a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King */ 10097a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King cpu_enter_lowpower(); 101d4450261e546953c4a1ce8b48e29164a57c6ed33Russell King platform_do_lowpower(cpu, &spurious); 10297a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King 10397a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King /* 10497a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * bring this CPU back into the world of cache 10597a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King * coherency, and then restore interrupts 10697a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King */ 10797a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King cpu_leave_lowpower(); 108d4450261e546953c4a1ce8b48e29164a57c6ed33Russell King 109d4450261e546953c4a1ce8b48e29164a57c6ed33Russell King if (spurious) 110d4450261e546953c4a1ce8b48e29164a57c6ed33Russell King pr_warn("CPU%u: %u spurious wakeup calls\n", cpu, spurious); 11197a63ecff4bd06da5d8feb8c0394a4d020f2d34dRussell King} 112