1/* 2 * Freescale STMP37XX/STMP378X core routines 3 * 4 * Embedded Alley Solutions, Inc <source@embeddedalley.com> 5 * 6 * Copyright 2008 Freescale Semiconductor, Inc. All Rights Reserved. 7 * Copyright 2008 Embedded Alley Solutions, Inc All Rights Reserved. 8 */ 9 10/* 11 * The code contained herein is licensed under the GNU General Public 12 * License. You may obtain a copy of the GNU General Public License 13 * Version 2 or later at the following locations: 14 * 15 * http://www.opensource.org/licenses/gpl-license.html 16 * http://www.gnu.org/copyleft/gpl.html 17 */ 18#include <linux/kernel.h> 19#include <linux/init.h> 20#include <linux/io.h> 21 22#include <mach/stmp3xxx.h> 23#include <mach/platform.h> 24#include <mach/dma.h> 25#include <mach/regs-clkctrl.h> 26 27static int __stmp3xxx_reset_block(void __iomem *hwreg, int just_enable) 28{ 29 u32 c; 30 int timeout; 31 32 /* the process of software reset of IP block is done 33 in several steps: 34 35 - clear SFTRST and wait for block is enabled; 36 - clear clock gating (CLKGATE bit); 37 - set the SFTRST again and wait for block is in reset; 38 - clear SFTRST and wait for reset completion. 39 */ 40 c = __raw_readl(hwreg); 41 c &= ~(1<<31); /* clear SFTRST */ 42 __raw_writel(c, hwreg); 43 for (timeout = 1000000; timeout > 0; timeout--) 44 /* still in SFTRST state ? */ 45 if ((__raw_readl(hwreg) & (1<<31)) == 0) 46 break; 47 if (timeout <= 0) { 48 printk(KERN_ERR"%s(%p): timeout when enabling\n", 49 __func__, hwreg); 50 return -ETIME; 51 } 52 53 c = __raw_readl(hwreg); 54 c &= ~(1<<30); /* clear CLKGATE */ 55 __raw_writel(c, hwreg); 56 57 if (!just_enable) { 58 c = __raw_readl(hwreg); 59 c |= (1<<31); /* now again set SFTRST */ 60 __raw_writel(c, hwreg); 61 for (timeout = 1000000; timeout > 0; timeout--) 62 /* poll until CLKGATE set */ 63 if (__raw_readl(hwreg) & (1<<30)) 64 break; 65 if (timeout <= 0) { 66 printk(KERN_ERR"%s(%p): timeout when resetting\n", 67 __func__, hwreg); 68 return -ETIME; 69 } 70 71 c = __raw_readl(hwreg); 72 c &= ~(1<<31); /* clear SFTRST */ 73 __raw_writel(c, hwreg); 74 for (timeout = 1000000; timeout > 0; timeout--) 75 /* still in SFTRST state ? */ 76 if ((__raw_readl(hwreg) & (1<<31)) == 0) 77 break; 78 if (timeout <= 0) { 79 printk(KERN_ERR"%s(%p): timeout when enabling " 80 "after reset\n", __func__, hwreg); 81 return -ETIME; 82 } 83 84 c = __raw_readl(hwreg); 85 c &= ~(1<<30); /* clear CLKGATE */ 86 __raw_writel(c, hwreg); 87 } 88 for (timeout = 1000000; timeout > 0; timeout--) 89 /* still in SFTRST state ? */ 90 if ((__raw_readl(hwreg) & (1<<30)) == 0) 91 break; 92 93 if (timeout <= 0) { 94 printk(KERN_ERR"%s(%p): timeout when unclockgating\n", 95 __func__, hwreg); 96 return -ETIME; 97 } 98 99 return 0; 100} 101 102int stmp3xxx_reset_block(void __iomem *hwreg, int just_enable) 103{ 104 int try = 10; 105 int r; 106 107 while (try--) { 108 r = __stmp3xxx_reset_block(hwreg, just_enable); 109 if (!r) 110 break; 111 pr_debug("%s: try %d failed\n", __func__, 10 - try); 112 } 113 return r; 114} 115EXPORT_SYMBOL(stmp3xxx_reset_block); 116 117struct platform_device stmp3xxx_dbguart = { 118 .name = "stmp3xxx-dbguart", 119 .id = -1, 120}; 121 122void __init stmp3xxx_init(void) 123{ 124 /* Turn off auto-slow and other tricks */ 125 stmp3xxx_clearl(0x7f00000, REGS_CLKCTRL_BASE + HW_CLKCTRL_HBUS); 126 127 stmp3xxx_dma_init(); 128} 129