aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
authorMagnus Damm <damm@opensource.se>2009-10-29 06:51:57 -0400
committerPaul Mundt <lethal@linux-sh.org>2009-10-29 22:55:14 -0400
commitda14909eb0749c2788fc704be6dbdebb620602f6 (patch)
treef5e1c87bde447d5f0fb188d3fcfbee2710ffc5a3 /arch
parent49f42644fd01bc7bd9b6b0a080fee1a89dc66665 (diff)
sh: Add sh7724 notifier for R-standby save/restore
Make use of the recently added notifier chains for sh7724 r-standby register save/restore handling. At this point only the BSC and INTC are handled. Signed-off-by: Magnus Damm <damm@opensource.se> Signed-off-by: Paul Mundt <lethal@linux-sh.org>
Diffstat (limited to 'arch')
-rw-r--r--arch/sh/kernel/cpu/sh4a/setup-sh7724.c167
1 files changed, 167 insertions, 0 deletions
diff --git a/arch/sh/kernel/cpu/sh4a/setup-sh7724.c b/arch/sh/kernel/cpu/sh4a/setup-sh7724.c
index f3851fd757ec..6dc4469434ea 100644
--- a/arch/sh/kernel/cpu/sh4a/setup-sh7724.c
+++ b/arch/sh/kernel/cpu/sh4a/setup-sh7724.c
@@ -20,6 +20,8 @@
20#include <linux/uio_driver.h> 20#include <linux/uio_driver.h>
21#include <linux/sh_timer.h> 21#include <linux/sh_timer.h>
22#include <linux/io.h> 22#include <linux/io.h>
23#include <linux/notifier.h>
24#include <asm/suspend.h>
23#include <asm/clock.h> 25#include <asm/clock.h>
24#include <asm/mmzone.h> 26#include <asm/mmzone.h>
25#include <cpu/sh7724.h> 27#include <cpu/sh7724.h>
@@ -827,3 +829,168 @@ void __init plat_irq_setup(void)
827{ 829{
828 register_intc_controller(&intc_desc); 830 register_intc_controller(&intc_desc);
829} 831}
832
833static struct {
834 /* BSC */
835 unsigned long mmselr;
836 unsigned long cs0bcr;
837 unsigned long cs4bcr;
838 unsigned long cs5abcr;
839 unsigned long cs5bbcr;
840 unsigned long cs6abcr;
841 unsigned long cs6bbcr;
842 unsigned long cs4wcr;
843 unsigned long cs5awcr;
844 unsigned long cs5bwcr;
845 unsigned long cs6awcr;
846 unsigned long cs6bwcr;
847 /* INTC */
848 unsigned short ipra;
849 unsigned short iprb;
850 unsigned short iprc;
851 unsigned short iprd;
852 unsigned short ipre;
853 unsigned short iprf;
854 unsigned short iprg;
855 unsigned short iprh;
856 unsigned short ipri;
857 unsigned short iprj;
858 unsigned short iprk;
859 unsigned short iprl;
860 unsigned char imr0;
861 unsigned char imr1;
862 unsigned char imr2;
863 unsigned char imr3;
864 unsigned char imr4;
865 unsigned char imr5;
866 unsigned char imr6;
867 unsigned char imr7;
868 unsigned char imr8;
869 unsigned char imr9;
870 unsigned char imr10;
871 unsigned char imr11;
872 unsigned char imr12;
873} sh7724_rstandby_state;
874
875static int sh7724_pre_sleep_notifier_call(struct notifier_block *nb,
876 unsigned long flags, void *unused)
877{
878 if (!(flags & SUSP_SH_RSTANDBY))
879 return NOTIFY_DONE;
880
881 /* BCR */
882 sh7724_rstandby_state.mmselr = __raw_readl(0xff800020); /* MMSELR */
883 sh7724_rstandby_state.mmselr |= 0xa5a50000;
884 sh7724_rstandby_state.cs0bcr = __raw_readl(0xfec10004); /* CS0BCR */
885 sh7724_rstandby_state.cs4bcr = __raw_readl(0xfec10010); /* CS4BCR */
886 sh7724_rstandby_state.cs5abcr = __raw_readl(0xfec10014); /* CS5ABCR */
887 sh7724_rstandby_state.cs5bbcr = __raw_readl(0xfec10018); /* CS5BBCR */
888 sh7724_rstandby_state.cs6abcr = __raw_readl(0xfec1001c); /* CS6ABCR */
889 sh7724_rstandby_state.cs6bbcr = __raw_readl(0xfec10020); /* CS6BBCR */
890 sh7724_rstandby_state.cs4wcr = __raw_readl(0xfec10030); /* CS4WCR */
891 sh7724_rstandby_state.cs5awcr = __raw_readl(0xfec10034); /* CS5AWCR */
892 sh7724_rstandby_state.cs5bwcr = __raw_readl(0xfec10038); /* CS5BWCR */
893 sh7724_rstandby_state.cs6awcr = __raw_readl(0xfec1003c); /* CS6AWCR */
894 sh7724_rstandby_state.cs6bwcr = __raw_readl(0xfec10040); /* CS6BWCR */
895
896 /* INTC */
897 sh7724_rstandby_state.ipra = __raw_readw(0xa4080000); /* IPRA */
898 sh7724_rstandby_state.iprb = __raw_readw(0xa4080004); /* IPRB */
899 sh7724_rstandby_state.iprc = __raw_readw(0xa4080008); /* IPRC */
900 sh7724_rstandby_state.iprd = __raw_readw(0xa408000c); /* IPRD */
901 sh7724_rstandby_state.ipre = __raw_readw(0xa4080010); /* IPRE */
902 sh7724_rstandby_state.iprf = __raw_readw(0xa4080014); /* IPRF */
903 sh7724_rstandby_state.iprg = __raw_readw(0xa4080018); /* IPRG */
904 sh7724_rstandby_state.iprh = __raw_readw(0xa408001c); /* IPRH */
905 sh7724_rstandby_state.ipri = __raw_readw(0xa4080020); /* IPRI */
906 sh7724_rstandby_state.iprj = __raw_readw(0xa4080024); /* IPRJ */
907 sh7724_rstandby_state.iprk = __raw_readw(0xa4080028); /* IPRK */
908 sh7724_rstandby_state.iprl = __raw_readw(0xa408002c); /* IPRL */
909 sh7724_rstandby_state.imr0 = __raw_readb(0xa4080080); /* IMR0 */
910 sh7724_rstandby_state.imr1 = __raw_readb(0xa4080084); /* IMR1 */
911 sh7724_rstandby_state.imr2 = __raw_readb(0xa4080088); /* IMR2 */
912 sh7724_rstandby_state.imr3 = __raw_readb(0xa408008c); /* IMR3 */
913 sh7724_rstandby_state.imr4 = __raw_readb(0xa4080090); /* IMR4 */
914 sh7724_rstandby_state.imr5 = __raw_readb(0xa4080094); /* IMR5 */
915 sh7724_rstandby_state.imr6 = __raw_readb(0xa4080098); /* IMR6 */
916 sh7724_rstandby_state.imr7 = __raw_readb(0xa408009c); /* IMR7 */
917 sh7724_rstandby_state.imr8 = __raw_readb(0xa40800a0); /* IMR8 */
918 sh7724_rstandby_state.imr9 = __raw_readb(0xa40800a4); /* IMR9 */
919 sh7724_rstandby_state.imr10 = __raw_readb(0xa40800a8); /* IMR10 */
920 sh7724_rstandby_state.imr11 = __raw_readb(0xa40800ac); /* IMR11 */
921 sh7724_rstandby_state.imr12 = __raw_readb(0xa40800b0); /* IMR12 */
922
923 return NOTIFY_DONE;
924}
925
926static int sh7724_post_sleep_notifier_call(struct notifier_block *nb,
927 unsigned long flags, void *unused)
928{
929 if (!(flags & SUSP_SH_RSTANDBY))
930 return NOTIFY_DONE;
931
932 /* BCR */
933 __raw_writel(sh7724_rstandby_state.mmselr, 0xff800020); /* MMSELR */
934 __raw_writel(sh7724_rstandby_state.cs0bcr, 0xfec10004); /* CS0BCR */
935 __raw_writel(sh7724_rstandby_state.cs4bcr, 0xfec10010); /* CS4BCR */
936 __raw_writel(sh7724_rstandby_state.cs5abcr, 0xfec10014); /* CS5ABCR */
937 __raw_writel(sh7724_rstandby_state.cs5bbcr, 0xfec10018); /* CS5BBCR */
938 __raw_writel(sh7724_rstandby_state.cs6abcr, 0xfec1001c); /* CS6ABCR */
939 __raw_writel(sh7724_rstandby_state.cs6bbcr, 0xfec10020); /* CS6BBCR */
940 __raw_writel(sh7724_rstandby_state.cs4wcr, 0xfec10030); /* CS4WCR */
941 __raw_writel(sh7724_rstandby_state.cs5awcr, 0xfec10034); /* CS5AWCR */
942 __raw_writel(sh7724_rstandby_state.cs5bwcr, 0xfec10038); /* CS5BWCR */
943 __raw_writel(sh7724_rstandby_state.cs6awcr, 0xfec1003c); /* CS6AWCR */
944 __raw_writel(sh7724_rstandby_state.cs6bwcr, 0xfec10040); /* CS6BWCR */
945
946 /* INTC */
947 __raw_writew(sh7724_rstandby_state.ipra, 0xa4080000); /* IPRA */
948 __raw_writew(sh7724_rstandby_state.iprb, 0xa4080004); /* IPRB */
949 __raw_writew(sh7724_rstandby_state.iprc, 0xa4080008); /* IPRC */
950 __raw_writew(sh7724_rstandby_state.iprd, 0xa408000c); /* IPRD */
951 __raw_writew(sh7724_rstandby_state.ipre, 0xa4080010); /* IPRE */
952 __raw_writew(sh7724_rstandby_state.iprf, 0xa4080014); /* IPRF */
953 __raw_writew(sh7724_rstandby_state.iprg, 0xa4080018); /* IPRG */
954 __raw_writew(sh7724_rstandby_state.iprh, 0xa408001c); /* IPRH */
955 __raw_writew(sh7724_rstandby_state.ipri, 0xa4080020); /* IPRI */
956 __raw_writew(sh7724_rstandby_state.iprj, 0xa4080024); /* IPRJ */
957 __raw_writew(sh7724_rstandby_state.iprk, 0xa4080028); /* IPRK */
958 __raw_writew(sh7724_rstandby_state.iprl, 0xa408002c); /* IPRL */
959 __raw_writeb(sh7724_rstandby_state.imr0, 0xa4080080); /* IMR0 */
960 __raw_writeb(sh7724_rstandby_state.imr1, 0xa4080084); /* IMR1 */
961 __raw_writeb(sh7724_rstandby_state.imr2, 0xa4080088); /* IMR2 */
962 __raw_writeb(sh7724_rstandby_state.imr3, 0xa408008c); /* IMR3 */
963 __raw_writeb(sh7724_rstandby_state.imr4, 0xa4080090); /* IMR4 */
964 __raw_writeb(sh7724_rstandby_state.imr5, 0xa4080094); /* IMR5 */
965 __raw_writeb(sh7724_rstandby_state.imr6, 0xa4080098); /* IMR6 */
966 __raw_writeb(sh7724_rstandby_state.imr7, 0xa408009c); /* IMR7 */
967 __raw_writeb(sh7724_rstandby_state.imr8, 0xa40800a0); /* IMR8 */
968 __raw_writeb(sh7724_rstandby_state.imr9, 0xa40800a4); /* IMR9 */
969 __raw_writeb(sh7724_rstandby_state.imr10, 0xa40800a8); /* IMR10 */
970 __raw_writeb(sh7724_rstandby_state.imr11, 0xa40800ac); /* IMR11 */
971 __raw_writeb(sh7724_rstandby_state.imr12, 0xa40800b0); /* IMR12 */
972
973 return NOTIFY_DONE;
974}
975
976static struct notifier_block sh7724_pre_sleep_notifier = {
977 .notifier_call = sh7724_pre_sleep_notifier_call,
978 .priority = SH_MOBILE_PRE(SH_MOBILE_SLEEP_CPU),
979};
980
981static struct notifier_block sh7724_post_sleep_notifier = {
982 .notifier_call = sh7724_post_sleep_notifier_call,
983 .priority = SH_MOBILE_POST(SH_MOBILE_SLEEP_CPU),
984};
985
986static int __init sh7724_sleep_setup(void)
987{
988 atomic_notifier_chain_register(&sh_mobile_pre_sleep_notifier_list,
989 &sh7724_pre_sleep_notifier);
990
991 atomic_notifier_chain_register(&sh_mobile_post_sleep_notifier_list,
992 &sh7724_post_sleep_notifier);
993 return 0;
994}
995arch_initcall(sh7724_sleep_setup);
996