Merge branch 'upstream' of git://git.linux-mips.org/pub/scm/ralf/upstream-linus

Pull MIPS updates from Ralf Baechle:
 "This is the main pull request for 3.17.  It contains:

   - misc Cavium Octeon, BCM47xx, BCM63xx and Alchemy  updates
   - MIPS ptrace updates and cleanups
   - various fixes that will also go to -stable
   - a number of cleanups and small non-critical fixes.
   - NUMA support for the Loongson 3.
   - more support for MSA
   - support for MAAR
   - various FP enhancements and fixes"

* 'upstream' of git://git.linux-mips.org/pub/scm/ralf/upstream-linus: (139 commits)
  MIPS: jz4740: remove unnecessary null test before debugfs_remove
  MIPS: Octeon: remove unnecessary null test before debugfs_remove_recursive
  MIPS: ZBOOT: implement stack protector in compressed boot phase
  MIPS: mipsreg: remove duplicate MIPS_CONF4_FTLBSETS_SHIFT
  MIPS: Bonito64: remove a duplicate define
  MIPS: Malta: initialise MAARs
  MIPS: Initialise MAARs
  MIPS: detect presence of MAARs
  MIPS: define MAAR register accessors & bits
  MIPS: mark MSA experimental
  MIPS: Don't build MSA support unless it can be used
  MIPS: consistently clear MSA flags when starting & copying threads
  MIPS: 16 byte align MSA vector context
  MIPS: disable preemption whilst initialising MSA
  MIPS: ensure MSA gets disabled during boot
  MIPS: fix read_msa_* & write_msa_* functions on non-MSA toolchains
  MIPS: fix MSA context for tasks which don't use FP first
  MIPS: init upper 64b of vector registers when MSA is first used
  MIPS: save/disable MSA in lose_fpu
  MIPS: preserve scalar FP CSR when switching vector context
  ...
This commit is contained in:
Linus Torvalds
2014-08-07 08:47:00 -07:00
156 changed files with 5487 additions and 3037 deletions

View File

@@ -571,6 +571,12 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
trust validation.
format: { id:<keyid> | builtin }
cca= [MIPS] Override the kernel pages' cache coherency
algorithm. Accepted values range from 0 to 7
inclusive. See arch/mips/include/asm/pgtable-bits.h
for platform specific values (SB1, Loongson3 and
others).
ccw_timeout_log [S390]
See Documentation/s390/CommonIO for details.

View File

@@ -71,6 +71,7 @@ config MIPS_ALCHEMY
select SYS_SUPPORTS_APM_EMULATION
select ARCH_REQUIRE_GPIOLIB
select SYS_SUPPORTS_ZBOOT
select COMMON_CLK
config AR7
bool "Texas Instruments AR7"
@@ -129,6 +130,8 @@ config BCM47XX
select SYS_SUPPORTS_MIPS16
select SYS_HAS_EARLY_PRINTK
select USE_GENERIC_EARLY_PRINTK_8250
select GPIOLIB
select LEDS_GPIO_REGISTER
help
Support for BCM47XX based boards
@@ -137,6 +140,7 @@ config BCM63XX
select BOOT_RAW
select CEVT_R4K
select CSRC_R4K
select SYNC_R4K
select DMA_NONCOHERENT
select IRQ_CPU
select SYS_SUPPORTS_32BIT_KERNEL
@@ -2056,6 +2060,7 @@ config MIPS_CPS
support is unavailable.
config MIPS_CPS_PM
select MIPS_CPC
bool
config MIPS_GIC_IPI
@@ -2109,9 +2114,9 @@ config CPU_MICROMIPS
microMIPS ISA
config CPU_HAS_MSA
bool "Support for the MIPS SIMD Architecture"
bool "Support for the MIPS SIMD Architecture (EXPERIMENTAL)"
depends on CPU_SUPPORTS_MSA
default y
depends on 64BIT || MIPS_O32_FP64_SUPPORT
help
MIPS SIMD Architecture (MSA) introduces 128 bit wide vector registers
and a set of SIMD instructions to operate on them. When this option

View File

@@ -151,8 +151,10 @@ cflags-$(CONFIG_CPU_NEVADA) += $(call cc-option,-march=rm5200,-march=r5000) \
-Wa,--trap
cflags-$(CONFIG_CPU_RM7000) += $(call cc-option,-march=rm7000,-march=r5000) \
-Wa,--trap
cflags-$(CONFIG_CPU_SB1) += $(call cc-option,-march=sb1 -mno-mdmx -mno-mips3d,-march=r5000) \
cflags-$(CONFIG_CPU_SB1) += $(call cc-option,-march=sb1,-march=r5000) \
-Wa,--trap
cflags-$(CONFIG_CPU_SB1) += $(call cc-option,-mno-mdmx)
cflags-$(CONFIG_CPU_SB1) += $(call cc-option,-mno-mips3d)
cflags-$(CONFIG_CPU_R8000) += -march=r8000 -Wa,--trap
cflags-$(CONFIG_CPU_R10000) += $(call cc-option,-march=r10000,-march=r8000) \
-Wa,--trap

View File

@@ -85,10 +85,10 @@ void __init board_setup(void)
#endif /* IS_ENABLED(CONFIG_USB_OHCI_HCD) */
/* Initialize sys_pinfunc */
au_writel(SYS_PF_NI2, SYS_PINFUNC);
alchemy_wrsys(SYS_PF_NI2, AU1000_SYS_PINFUNC);
/* Initialize GPIO */
au_writel(~0, KSEG1ADDR(AU1000_SYS_PHYS_ADDR) + SYS_TRIOUTCLR);
alchemy_wrsys(~0, AU1000_SYS_TRIOUTCLR);
alchemy_gpio_direction_output(0, 0); /* Disable M66EN (PCI 66MHz) */
alchemy_gpio_direction_output(3, 1); /* Disable PCI CLKRUN# */
alchemy_gpio_direction_output(1, 1); /* Enable EXT_IO3 */

View File

@@ -87,9 +87,9 @@ void __init board_setup(void)
alchemy_gpio2_enable();
/* Set multiple use pins (UART3/GPIO) to UART (it's used as UART too) */
pin_func = au_readl(SYS_PINFUNC) & ~SYS_PF_UR3;
pin_func = alchemy_rdsys(AU1000_SYS_PINFUNC) & ~SYS_PF_UR3;
pin_func |= SYS_PF_UR3;
au_writel(pin_func, SYS_PINFUNC);
alchemy_wrsys(pin_func, AU1000_SYS_PINFUNC);
/* Enable UART */
alchemy_uart_enable(AU1000_UART3_PHYS_ADDR);

View File

@@ -5,8 +5,8 @@
# Makefile for the Alchemy Au1xx0 CPUs, generic files.
#
obj-y += prom.o time.o clocks.o platform.o power.o setup.o \
sleeper.o dma.o dbdma.o vss.o irq.o usb.o
obj-y += prom.o time.o clock.o platform.o power.o \
setup.o sleeper.o dma.o dbdma.o vss.o irq.o usb.o
# optional gpiolib support
ifeq ($(CONFIG_ALCHEMY_GPIO_INDIRECT),)

File diff suppressed because it is too large Load Diff

View File

@@ -1,105 +0,0 @@
/*
* BRIEF MODULE DESCRIPTION
* Simple Au1xx0 clocks routines.
*
* Copyright 2001, 2008 MontaVista Software Inc.
* Author: MontaVista Software, Inc. <source@mvista.com>
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
* Free Software Foundation; either version 2 of the License, or (at your
* option) any later version.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN
* NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <linux/module.h>
#include <linux/spinlock.h>
#include <asm/time.h>
#include <asm/mach-au1x00/au1000.h>
/*
* I haven't found anyone that doesn't use a 12 MHz source clock,
* but just in case.....
*/
#define AU1000_SRC_CLK 12000000
static unsigned int au1x00_clock; /* Hz */
static unsigned long uart_baud_base;
/*
* Set the au1000_clock
*/
void set_au1x00_speed(unsigned int new_freq)
{
au1x00_clock = new_freq;
}
unsigned int get_au1x00_speed(void)
{
return au1x00_clock;
}
EXPORT_SYMBOL(get_au1x00_speed);
/*
* The UART baud base is not known at compile time ... if
* we want to be able to use the same code on different
* speed CPUs.
*/
unsigned long get_au1x00_uart_baud_base(void)
{
return uart_baud_base;
}
void set_au1x00_uart_baud_base(unsigned long new_baud_base)
{
uart_baud_base = new_baud_base;
}
/*
* We read the real processor speed from the PLL. This is important
* because it is more accurate than computing it from the 32 KHz
* counter, if it exists. If we don't have an accurate processor
* speed, all of the peripherals that derive their clocks based on
* this advertised speed will introduce error and sometimes not work
* properly. This function is further convoluted to still allow configurations
* to do that in case they have really, really old silicon with a
* write-only PLL register. -- Dan
*/
unsigned long au1xxx_calc_clock(void)
{
unsigned long cpu_speed;
/*
* On early Au1000, sys_cpupll was write-only. Since these
* silicon versions of Au1000 are not sold by AMD, we don't bend
* over backwards trying to determine the frequency.
*/
if (au1xxx_cpu_has_pll_wo())
cpu_speed = 396000000;
else
cpu_speed = (au_readl(SYS_CPUPLL) & 0x0000003f) * AU1000_SRC_CLK;
/* On Alchemy CPU:counter ratio is 1:1 */
mips_hpt_frequency = cpu_speed;
/* Equation: Baudrate = CPU / (SD * 2 * CLKDIV * 16) */
set_au1x00_uart_baud_base(cpu_speed / (2 * ((int)(au_readl(SYS_POWERCTRL)
& 0x03) + 2) * 16));
set_au1x00_speed(cpu_speed);
return cpu_speed;
}

View File

@@ -341,7 +341,7 @@ u32 au1xxx_dbdma_chan_alloc(u32 srcid, u32 destid,
(dtp->dev_flags & DEV_FLAGS_SYNC))
i |= DDMA_CFG_SYNC;
cp->ddma_cfg = i;
au_sync();
wmb(); /* drain writebuffer */
/*
* Return a non-zero value that can be used to find the channel
@@ -631,7 +631,7 @@ u32 au1xxx_dbdma_put_source(u32 chanid, dma_addr_t buf, int nbytes, u32 flags)
*/
dma_cache_wback_inv((unsigned long)buf, nbytes);
dp->dscr_cmd0 |= DSCR_CMD0_V; /* Let it rip */
au_sync();
wmb(); /* drain writebuffer */
dma_cache_wback_inv((unsigned long)dp, sizeof(*dp));
ctp->chan_ptr->ddma_dbell = 0;
@@ -693,7 +693,7 @@ u32 au1xxx_dbdma_put_dest(u32 chanid, dma_addr_t buf, int nbytes, u32 flags)
*/
dma_cache_inv((unsigned long)buf, nbytes);
dp->dscr_cmd0 |= DSCR_CMD0_V; /* Let it rip */
au_sync();
wmb(); /* drain writebuffer */
dma_cache_wback_inv((unsigned long)dp, sizeof(*dp));
ctp->chan_ptr->ddma_dbell = 0;
@@ -760,7 +760,7 @@ void au1xxx_dbdma_stop(u32 chanid)
cp = ctp->chan_ptr;
cp->ddma_cfg &= ~DDMA_CFG_EN; /* Disable channel */
au_sync();
wmb(); /* drain writebuffer */
while (!(cp->ddma_stat & DDMA_STAT_H)) {
udelay(1);
halt_timeout++;
@@ -771,7 +771,7 @@ void au1xxx_dbdma_stop(u32 chanid)
}
/* clear current desc valid and doorbell */
cp->ddma_stat |= (DDMA_STAT_DB | DDMA_STAT_V);
au_sync();
wmb(); /* drain writebuffer */
}
EXPORT_SYMBOL(au1xxx_dbdma_stop);
@@ -789,9 +789,9 @@ void au1xxx_dbdma_start(u32 chanid)
cp = ctp->chan_ptr;
cp->ddma_desptr = virt_to_phys(ctp->cur_ptr);
cp->ddma_cfg |= DDMA_CFG_EN; /* Enable channel */
au_sync();
wmb(); /* drain writebuffer */
cp->ddma_dbell = 0;
au_sync();
wmb(); /* drain writebuffer */
}
EXPORT_SYMBOL(au1xxx_dbdma_start);
@@ -832,7 +832,7 @@ u32 au1xxx_get_dma_residue(u32 chanid)
/* This is only valid if the channel is stopped. */
rv = cp->ddma_bytecnt;
au_sync();
wmb(); /* drain writebuffer */
return rv;
}
@@ -868,7 +868,7 @@ static irqreturn_t dbdma_interrupt(int irq, void *dev_id)
au1x_dma_chan_t *cp;
intstat = dbdma_gptr->ddma_intstat;
au_sync();
wmb(); /* drain writebuffer */
chan_index = __ffs(intstat);
ctp = chan_tab_ptr[chan_index];
@@ -877,7 +877,7 @@ static irqreturn_t dbdma_interrupt(int irq, void *dev_id)
/* Reset interrupt. */
cp->ddma_irq = 0;
au_sync();
wmb(); /* drain writebuffer */
if (ctp->chan_callback)
ctp->chan_callback(irq, ctp->chan_callparam);
@@ -1061,7 +1061,7 @@ static int __init dbdma_setup(unsigned int irq, dbdev_tab_t *idtable)
dbdma_gptr->ddma_config = 0;
dbdma_gptr->ddma_throttle = 0;
dbdma_gptr->ddma_inten = 0xffff;
au_sync();
wmb(); /* drain writebuffer */
ret = request_irq(irq, dbdma_interrupt, 0, "dbdma", (void *)dbdma_gptr);
if (ret)

View File

@@ -141,17 +141,17 @@ void dump_au1000_dma_channel(unsigned int dmanr)
printk(KERN_INFO "Au1000 DMA%d Register Dump:\n", dmanr);
printk(KERN_INFO " mode = 0x%08x\n",
au_readl(chan->io + DMA_MODE_SET));
__raw_readl(chan->io + DMA_MODE_SET));
printk(KERN_INFO " addr = 0x%08x\n",
au_readl(chan->io + DMA_PERIPHERAL_ADDR));
__raw_readl(chan->io + DMA_PERIPHERAL_ADDR));
printk(KERN_INFO " start0 = 0x%08x\n",
au_readl(chan->io + DMA_BUFFER0_START));
__raw_readl(chan->io + DMA_BUFFER0_START));
printk(KERN_INFO " start1 = 0x%08x\n",
au_readl(chan->io + DMA_BUFFER1_START));
__raw_readl(chan->io + DMA_BUFFER1_START));
printk(KERN_INFO " count0 = 0x%08x\n",
au_readl(chan->io + DMA_BUFFER0_COUNT));
__raw_readl(chan->io + DMA_BUFFER0_COUNT));
printk(KERN_INFO " count1 = 0x%08x\n",
au_readl(chan->io + DMA_BUFFER1_COUNT));
__raw_readl(chan->io + DMA_BUFFER1_COUNT));
}
/*
@@ -204,7 +204,8 @@ int request_au1000_dma(int dev_id, const char *dev_str,
}
/* fill it in */
chan->io = KSEG1ADDR(AU1000_DMA_PHYS_ADDR) + i * DMA_CHANNEL_LEN;
chan->io = (void __iomem *)(KSEG1ADDR(AU1000_DMA_PHYS_ADDR) +
i * DMA_CHANNEL_LEN);
chan->dev_id = dev_id;
chan->dev_str = dev_str;
chan->fifo_addr = dev->fifo_addr;

View File

@@ -389,13 +389,12 @@ static int au1x_ic1_setwake(struct irq_data *d, unsigned int on)
return -EINVAL;
local_irq_save(flags);
wakemsk = __raw_readl((void __iomem *)SYS_WAKEMSK);
wakemsk = alchemy_rdsys(AU1000_SYS_WAKEMSK);
if (on)
wakemsk |= 1 << bit;
else
wakemsk &= ~(1 << bit);
__raw_writel(wakemsk, (void __iomem *)SYS_WAKEMSK);
wmb();
alchemy_wrsys(wakemsk, AU1000_SYS_WAKEMSK);
local_irq_restore(flags);
return 0;

View File

@@ -11,6 +11,7 @@
* warranty of any kind, whether express or implied.
*/
#include <linux/clk.h>
#include <linux/dma-mapping.h>
#include <linux/etherdevice.h>
#include <linux/init.h>
@@ -99,10 +100,20 @@ static struct platform_device au1xx0_uart_device = {
static void __init alchemy_setup_uarts(int ctype)
{
unsigned int uartclk = get_au1x00_uart_baud_base() * 16;
long uartclk;
int s = sizeof(struct plat_serial8250_port);
int c = alchemy_get_uarts(ctype);
struct plat_serial8250_port *ports;
struct clk *clk = clk_get(NULL, ALCHEMY_PERIPH_CLK);
if (IS_ERR(clk))
return;
if (clk_prepare_enable(clk)) {
clk_put(clk);
return;
}
uartclk = clk_get_rate(clk);
clk_put(clk);
ports = kzalloc(s * (c + 1), GFP_KERNEL);
if (!ports) {
@@ -420,7 +431,7 @@ static void __init alchemy_setup_macs(int ctype)
memcpy(au1xxx_eth1_platform_data.mac, ethaddr, 6);
/* Register second MAC if enabled in pinfunc */
if (!(au_readl(SYS_PINFUNC) & (u32)SYS_PF_NI2)) {
if (!(alchemy_rdsys(AU1000_SYS_PINFUNC) & SYS_PF_NI2)) {
ret = platform_device_register(&au1xxx_eth1_device);
if (ret)
printk(KERN_INFO "Alchemy: failed to register MAC1\n");

View File

@@ -54,28 +54,28 @@ static unsigned int sleep_static_memctlr[4][3];
static void save_core_regs(void)
{
/* Clocks and PLLs. */
sleep_sys_clocks[0] = au_readl(SYS_FREQCTRL0);
sleep_sys_clocks[1] = au_readl(SYS_FREQCTRL1);
sleep_sys_clocks[2] = au_readl(SYS_CLKSRC);
sleep_sys_clocks[3] = au_readl(SYS_CPUPLL);
sleep_sys_clocks[4] = au_readl(SYS_AUXPLL);
sleep_sys_clocks[0] = alchemy_rdsys(AU1000_SYS_FREQCTRL0);
sleep_sys_clocks[1] = alchemy_rdsys(AU1000_SYS_FREQCTRL1);
sleep_sys_clocks[2] = alchemy_rdsys(AU1000_SYS_CLKSRC);
sleep_sys_clocks[3] = alchemy_rdsys(AU1000_SYS_CPUPLL);
sleep_sys_clocks[4] = alchemy_rdsys(AU1000_SYS_AUXPLL);
/* pin mux config */
sleep_sys_pinfunc = au_readl(SYS_PINFUNC);
sleep_sys_pinfunc = alchemy_rdsys(AU1000_SYS_PINFUNC);
/* Save the static memory controller configuration. */
sleep_static_memctlr[0][0] = au_readl(MEM_STCFG0);
sleep_static_memctlr[0][1] = au_readl(MEM_STTIME0);
sleep_static_memctlr[0][2] = au_readl(MEM_STADDR0);
sleep_static_memctlr[1][0] = au_readl(MEM_STCFG1);
sleep_static_memctlr[1][1] = au_readl(MEM_STTIME1);
sleep_static_memctlr[1][2] = au_readl(MEM_STADDR1);
sleep_static_memctlr[2][0] = au_readl(MEM_STCFG2);
sleep_static_memctlr[2][1] = au_readl(MEM_STTIME2);
sleep_static_memctlr[2][2] = au_readl(MEM_STADDR2);
sleep_static_memctlr[3][0] = au_readl(MEM_STCFG3);
sleep_static_memctlr[3][1] = au_readl(MEM_STTIME3);
sleep_static_memctlr[3][2] = au_readl(MEM_STADDR3);
sleep_static_memctlr[0][0] = alchemy_rdsmem(AU1000_MEM_STCFG0);
sleep_static_memctlr[0][1] = alchemy_rdsmem(AU1000_MEM_STTIME0);
sleep_static_memctlr[0][2] = alchemy_rdsmem(AU1000_MEM_STADDR0);
sleep_static_memctlr[1][0] = alchemy_rdsmem(AU1000_MEM_STCFG1);
sleep_static_memctlr[1][1] = alchemy_rdsmem(AU1000_MEM_STTIME1);
sleep_static_memctlr[1][2] = alchemy_rdsmem(AU1000_MEM_STADDR1);
sleep_static_memctlr[2][0] = alchemy_rdsmem(AU1000_MEM_STCFG2);
sleep_static_memctlr[2][1] = alchemy_rdsmem(AU1000_MEM_STTIME2);
sleep_static_memctlr[2][2] = alchemy_rdsmem(AU1000_MEM_STADDR2);
sleep_static_memctlr[3][0] = alchemy_rdsmem(AU1000_MEM_STCFG3);
sleep_static_memctlr[3][1] = alchemy_rdsmem(AU1000_MEM_STTIME3);
sleep_static_memctlr[3][2] = alchemy_rdsmem(AU1000_MEM_STADDR3);
}
static void restore_core_regs(void)
@@ -85,30 +85,28 @@ static void restore_core_regs(void)
* one of those Au1000 with a write-only PLL, where we dont
* have a valid value)
*/
au_writel(sleep_sys_clocks[0], SYS_FREQCTRL0);
au_writel(sleep_sys_clocks[1], SYS_FREQCTRL1);
au_writel(sleep_sys_clocks[2], SYS_CLKSRC);
au_writel(sleep_sys_clocks[4], SYS_AUXPLL);
alchemy_wrsys(sleep_sys_clocks[0], AU1000_SYS_FREQCTRL0);
alchemy_wrsys(sleep_sys_clocks[1], AU1000_SYS_FREQCTRL1);
alchemy_wrsys(sleep_sys_clocks[2], AU1000_SYS_CLKSRC);
alchemy_wrsys(sleep_sys_clocks[4], AU1000_SYS_AUXPLL);
if (!au1xxx_cpu_has_pll_wo())
au_writel(sleep_sys_clocks[3], SYS_CPUPLL);
au_sync();
alchemy_wrsys(sleep_sys_clocks[3], AU1000_SYS_CPUPLL);
au_writel(sleep_sys_pinfunc, SYS_PINFUNC);
au_sync();
alchemy_wrsys(sleep_sys_pinfunc, AU1000_SYS_PINFUNC);
/* Restore the static memory controller configuration. */
au_writel(sleep_static_memctlr[0][0], MEM_STCFG0);
au_writel(sleep_static_memctlr[0][1], MEM_STTIME0);
au_writel(sleep_static_memctlr[0][2], MEM_STADDR0);
au_writel(sleep_static_memctlr[1][0], MEM_STCFG1);
au_writel(sleep_static_memctlr[1][1], MEM_STTIME1);
au_writel(sleep_static_memctlr[1][2], MEM_STADDR1);
au_writel(sleep_static_memctlr[2][0], MEM_STCFG2);
au_writel(sleep_static_memctlr[2][1], MEM_STTIME2);
au_writel(sleep_static_memctlr[2][2], MEM_STADDR2);
au_writel(sleep_static_memctlr[3][0], MEM_STCFG3);
au_writel(sleep_static_memctlr[3][1], MEM_STTIME3);
au_writel(sleep_static_memctlr[3][2], MEM_STADDR3);
alchemy_wrsmem(sleep_static_memctlr[0][0], AU1000_MEM_STCFG0);
alchemy_wrsmem(sleep_static_memctlr[0][1], AU1000_MEM_STTIME0);
alchemy_wrsmem(sleep_static_memctlr[0][2], AU1000_MEM_STADDR0);
alchemy_wrsmem(sleep_static_memctlr[1][0], AU1000_MEM_STCFG1);
alchemy_wrsmem(sleep_static_memctlr[1][1], AU1000_MEM_STTIME1);
alchemy_wrsmem(sleep_static_memctlr[1][2], AU1000_MEM_STADDR1);
alchemy_wrsmem(sleep_static_memctlr[2][0], AU1000_MEM_STCFG2);
alchemy_wrsmem(sleep_static_memctlr[2][1], AU1000_MEM_STTIME2);
alchemy_wrsmem(sleep_static_memctlr[2][2], AU1000_MEM_STADDR2);
alchemy_wrsmem(sleep_static_memctlr[3][0], AU1000_MEM_STCFG3);
alchemy_wrsmem(sleep_static_memctlr[3][1], AU1000_MEM_STTIME3);
alchemy_wrsmem(sleep_static_memctlr[3][2], AU1000_MEM_STADDR3);
}
void au_sleep(void)

View File

@@ -27,12 +27,9 @@
#include <linux/init.h>
#include <linux/ioport.h>
#include <linux/jiffies.h>
#include <linux/module.h>
#include <asm/dma-coherence.h>
#include <asm/mipsregs.h>
#include <asm/time.h>
#include <au1000.h>
@@ -41,18 +38,6 @@ extern void set_cpuspec(void);
void __init plat_mem_setup(void)
{
unsigned long est_freq;
/* determine core clock */
est_freq = au1xxx_calc_clock();
est_freq += 5000; /* round */
est_freq -= est_freq % 10000;
printk(KERN_INFO "(PRId %08x) @ %lu.%02lu MHz\n", read_c0_prid(),
est_freq / 1000000, ((est_freq % 1000000) * 100) / 1000000);
/* this is faster than wasting cycles trying to approximate it */
preset_lpj = (est_freq >> 1) / HZ;
if (au1xxx_cpu_needs_config_od())
/* Various early Au1xx0 errata corrected by this */
set_c0_config(1 << 19); /* Set Config[OD] */

View File

@@ -46,7 +46,7 @@
static cycle_t au1x_counter1_read(struct clocksource *cs)
{
return au_readl(SYS_RTCREAD);
return alchemy_rdsys(AU1000_SYS_RTCREAD);
}
static struct clocksource au1x_counter1_clocksource = {
@@ -60,12 +60,11 @@ static struct clocksource au1x_counter1_clocksource = {
static int au1x_rtcmatch2_set_next_event(unsigned long delta,
struct clock_event_device *cd)
{
delta += au_readl(SYS_RTCREAD);
delta += alchemy_rdsys(AU1000_SYS_RTCREAD);
/* wait for register access */
while (au_readl(SYS_COUNTER_CNTRL) & SYS_CNTRL_M21)
while (alchemy_rdsys(AU1000_SYS_CNTRCTRL) & SYS_CNTRL_M21)
;
au_writel(delta, SYS_RTCMATCH2);
au_sync();
alchemy_wrsys(delta, AU1000_SYS_RTCMATCH2);
return 0;
}
@@ -112,31 +111,29 @@ static int __init alchemy_time_init(unsigned int m2int)
* (the 32S bit seems to be stuck set to 1 once a single clock-
* edge is detected, hence the timeouts).
*/
if (CNTR_OK != (au_readl(SYS_COUNTER_CNTRL) & CNTR_OK))
if (CNTR_OK != (alchemy_rdsys(AU1000_SYS_CNTRCTRL) & CNTR_OK))
goto cntr_err;
/*
* setup counter 1 (RTC) to tick at full speed
*/
t = 0xffffff;
while ((au_readl(SYS_COUNTER_CNTRL) & SYS_CNTRL_T1S) && --t)
while ((alchemy_rdsys(AU1000_SYS_CNTRCTRL) & SYS_CNTRL_T1S) && --t)
asm volatile ("nop");
if (!t)
goto cntr_err;
au_writel(0, SYS_RTCTRIM); /* 32.768 kHz */
au_sync();
alchemy_wrsys(0, AU1000_SYS_RTCTRIM); /* 32.768 kHz */
t = 0xffffff;
while ((au_readl(SYS_COUNTER_CNTRL) & SYS_CNTRL_C1S) && --t)
while ((alchemy_rdsys(AU1000_SYS_CNTRCTRL) & SYS_CNTRL_C1S) && --t)
asm volatile ("nop");
if (!t)
goto cntr_err;
au_writel(0, SYS_RTCWRITE);
au_sync();
alchemy_wrsys(0, AU1000_SYS_RTCWRITE);
t = 0xffffff;
while ((au_readl(SYS_COUNTER_CNTRL) & SYS_CNTRL_C1S) && --t)
while ((alchemy_rdsys(AU1000_SYS_CNTRCTRL) & SYS_CNTRL_C1S) && --t)
asm volatile ("nop");
if (!t)
goto cntr_err;

View File

@@ -9,6 +9,7 @@
*
*/
#include <linux/clk.h>
#include <linux/init.h>
#include <linux/io.h>
#include <linux/module.h>
@@ -387,10 +388,25 @@ static inline void au1200_usb_init(void)
udelay(1000);
}
static inline void au1000_usb_init(unsigned long rb, int reg)
static inline int au1000_usb_init(unsigned long rb, int reg)
{
void __iomem *base = (void __iomem *)KSEG1ADDR(rb + reg);
unsigned long r = __raw_readl(base);
struct clk *c;
/* 48MHz check. Don't init if no one can provide it */
c = clk_get(NULL, "usbh_clk");
if (IS_ERR(c))
return -ENODEV;
if (clk_round_rate(c, 48000000) != 48000000) {
clk_put(c);
return -ENODEV;
}
if (clk_set_rate(c, 48000000)) {
clk_put(c);
return -ENODEV;
}
clk_put(c);
#if defined(__BIG_ENDIAN)
r |= USBHEN_BE;
@@ -400,6 +416,8 @@ static inline void au1000_usb_init(unsigned long rb, int reg)
__raw_writel(r, base);
wmb();
udelay(1000);
return 0;
}
@@ -407,8 +425,15 @@ static inline void __au1xx0_ohci_control(int enable, unsigned long rb, int creg)
{
void __iomem *base = (void __iomem *)KSEG1ADDR(rb);
unsigned long r = __raw_readl(base + creg);
struct clk *c = clk_get(NULL, "usbh_clk");
if (IS_ERR(c))
return;
if (enable) {
if (clk_prepare_enable(c))
goto out;
__raw_writel(r | USBHEN_CE, base + creg);
wmb();
udelay(1000);
@@ -423,7 +448,10 @@ static inline void __au1xx0_ohci_control(int enable, unsigned long rb, int creg)
} else {
__raw_writel(r & ~(USBHEN_CE | USBHEN_E), base + creg);
wmb();
clk_disable_unprepare(c);
}
out:
clk_put(c);
}
static inline int au1000_usb_control(int block, int enable, unsigned long rb,
@@ -457,11 +485,11 @@ int alchemy_usb_control(int block, int enable)
case ALCHEMY_CPU_AU1500:
case ALCHEMY_CPU_AU1100:
ret = au1000_usb_control(block, enable,
AU1000_USB_OHCI_PHYS_ADDR, AU1000_OHCICFG);
AU1000_USB_OHCI_PHYS_ADDR, AU1000_OHCICFG);
break;
case ALCHEMY_CPU_AU1550:
ret = au1000_usb_control(block, enable,
AU1550_USB_OHCI_PHYS_ADDR, AU1550_OHCICFG);
AU1550_USB_OHCI_PHYS_ADDR, AU1550_OHCICFG);
break;
case ALCHEMY_CPU_AU1200:
ret = au1200_usb_control(block, enable);
@@ -569,14 +597,18 @@ static struct syscore_ops alchemy_usb_pm_ops = {
static int __init alchemy_usb_init(void)
{
int ret = 0;
switch (alchemy_get_cputype()) {
case ALCHEMY_CPU_AU1000:
case ALCHEMY_CPU_AU1500:
case ALCHEMY_CPU_AU1100:
au1000_usb_init(AU1000_USB_OHCI_PHYS_ADDR, AU1000_OHCICFG);
ret = au1000_usb_init(AU1000_USB_OHCI_PHYS_ADDR,
AU1000_OHCICFG);
break;
case ALCHEMY_CPU_AU1550:
au1000_usb_init(AU1550_USB_OHCI_PHYS_ADDR, AU1550_OHCICFG);
ret = au1000_usb_init(AU1550_USB_OHCI_PHYS_ADDR,
AU1550_OHCICFG);
break;
case ALCHEMY_CPU_AU1200:
au1200_usb_init();
@@ -586,8 +618,9 @@ static int __init alchemy_usb_init(void)
break;
}
register_syscore_ops(&alchemy_usb_pm_ops);
if (!ret)
register_syscore_ops(&alchemy_usb_pm_ops);
return 0;
return ret;
}
arch_initcall(alchemy_usb_init);

View File

@@ -19,6 +19,7 @@
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include <linux/clk.h>
#include <linux/dma-mapping.h>
#include <linux/gpio.h>
#include <linux/init.h>
@@ -496,6 +497,7 @@ int __init db1000_dev_setup(void)
int board = BCSR_WHOAMI_BOARD(bcsr_read(BCSR_WHOAMI));
int c0, c1, d0, d1, s0, s1, flashsize = 32, twosocks = 1;
unsigned long pfc;
struct clk *c, *p;
if (board == BCSR_WHOAMI_DB1500) {
c0 = AU1500_GPIO2_INT;
@@ -518,14 +520,25 @@ int __init db1000_dev_setup(void)
gpio_direction_input(20); /* sd1 cd# */
/* spi_gpio on SSI0 pins */
pfc = __raw_readl((void __iomem *)SYS_PINFUNC);
pfc = alchemy_rdsys(AU1000_SYS_PINFUNC);
pfc |= (1 << 0); /* SSI0 pins as GPIOs */
__raw_writel(pfc, (void __iomem *)SYS_PINFUNC);
wmb();
alchemy_wrsys(pfc, AU1000_SYS_PINFUNC);
spi_register_board_info(db1100_spi_info,
ARRAY_SIZE(db1100_spi_info));
/* link LCD clock to AUXPLL */
p = clk_get(NULL, "auxpll_clk");
c = clk_get(NULL, "lcd_intclk");
if (!IS_ERR(c) && !IS_ERR(p)) {
clk_set_parent(c, p);
clk_set_rate(c, clk_get_rate(p));
}
if (!IS_ERR(c))
clk_put(c);
if (!IS_ERR(p))
clk_put(p);
platform_add_devices(db1100_devs, ARRAY_SIZE(db1100_devs));
platform_device_register(&db1100_spi_dev);
} else if (board == BCSR_WHOAMI_DB1000) {

View File

@@ -18,6 +18,7 @@
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include <linux/clk.h>
#include <linux/dma-mapping.h>
#include <linux/gpio.h>
#include <linux/i2c.h>
@@ -129,7 +130,6 @@ static int __init db1200_detect_board(void)
int __init db1200_board_setup(void)
{
unsigned long freq0, clksrc, div, pfc;
unsigned short whoami;
if (db1200_detect_board())
@@ -149,34 +149,6 @@ int __init db1200_board_setup(void)
" Board-ID %d Daughtercard ID %d\n", get_system_type(),
(whoami >> 4) & 0xf, (whoami >> 8) & 0xf, whoami & 0xf);
/* SMBus/SPI on PSC0, Audio on PSC1 */
pfc = __raw_readl((void __iomem *)SYS_PINFUNC);
pfc &= ~(SYS_PINFUNC_P0A | SYS_PINFUNC_P0B);
pfc &= ~(SYS_PINFUNC_P1A | SYS_PINFUNC_P1B | SYS_PINFUNC_FS3);
pfc |= SYS_PINFUNC_P1C; /* SPI is configured later */
__raw_writel(pfc, (void __iomem *)SYS_PINFUNC);
wmb();
/* Clock configurations: PSC0: ~50MHz via Clkgen0, derived from
* CPU clock; all other clock generators off/unused.
*/
div = (get_au1x00_speed() + 25000000) / 50000000;
if (div & 1)
div++;
div = ((div >> 1) - 1) & 0xff;
freq0 = div << SYS_FC_FRDIV0_BIT;
__raw_writel(freq0, (void __iomem *)SYS_FREQCTRL0);
wmb();
freq0 |= SYS_FC_FE0; /* enable F0 */
__raw_writel(freq0, (void __iomem *)SYS_FREQCTRL0);
wmb();
/* psc0_intclk comes 1:1 from F0 */
clksrc = SYS_CS_MUX_FQ0 << SYS_CS_ME0_BIT;
__raw_writel(clksrc, (void __iomem *)SYS_CLKSRC);
wmb();
return 0;
}
@@ -250,7 +222,7 @@ static void au1200_nand_cmd_ctrl(struct mtd_info *mtd, int cmd,
static int au1200_nand_device_ready(struct mtd_info *mtd)
{
return __raw_readl((void __iomem *)MEM_STSTAT) & 1;
return alchemy_rdsmem(AU1000_MEM_STSTAT) & 1;
}
static struct mtd_partition db1200_nand_parts[] = {
@@ -847,6 +819,7 @@ int __init db1200_dev_setup(void)
unsigned long pfc;
unsigned short sw;
int swapped, bid;
struct clk *c;
bid = BCSR_WHOAMI_BOARD(bcsr_read(BCSR_WHOAMI));
if ((bid == BCSR_WHOAMI_PB1200_DDR1) ||
@@ -859,6 +832,24 @@ int __init db1200_dev_setup(void)
irq_set_irq_type(AU1200_GPIO7_INT, IRQ_TYPE_LEVEL_LOW);
bcsr_init_irq(DB1200_INT_BEGIN, DB1200_INT_END, AU1200_GPIO7_INT);
/* SMBus/SPI on PSC0, Audio on PSC1 */
pfc = alchemy_rdsys(AU1000_SYS_PINFUNC);
pfc &= ~(SYS_PINFUNC_P0A | SYS_PINFUNC_P0B);
pfc &= ~(SYS_PINFUNC_P1A | SYS_PINFUNC_P1B | SYS_PINFUNC_FS3);
pfc |= SYS_PINFUNC_P1C; /* SPI is configured later */
alchemy_wrsys(pfc, AU1000_SYS_PINFUNC);
/* get 50MHz for I2C driver on PSC0 */
c = clk_get(NULL, "psc0_intclk");
if (!IS_ERR(c)) {
pfc = clk_round_rate(c, 50000000);
if ((pfc < 1) || (abs(50000000 - pfc) > 2500000))
pr_warn("DB1200: cant get I2C close to 50MHz\n");
else
clk_set_rate(c, pfc);
clk_put(c);
}
/* insert/eject pairs: one of both is always screaming. To avoid
* issues they must not be automatically enabled when initially
* requested.
@@ -886,7 +877,7 @@ int __init db1200_dev_setup(void)
* As a result, in SPI mode, OTG simply won't work (PSC0 uses
* it as an input pin which is pulled high on the boards).
*/
pfc = __raw_readl((void __iomem *)SYS_PINFUNC) & ~SYS_PINFUNC_P0A;
pfc = alchemy_rdsys(AU1000_SYS_PINFUNC) & ~SYS_PINFUNC_P0A;
/* switch off OTG VBUS supply */
gpio_request(215, "otg-vbus");
@@ -912,8 +903,7 @@ int __init db1200_dev_setup(void)
printk(KERN_INFO " S6.8 ON : PSC0 mode SPI\n");
printk(KERN_INFO " OTG port VBUS supply disabled\n");
}
__raw_writel(pfc, (void __iomem *)SYS_PINFUNC);
wmb();
alchemy_wrsys(pfc, AU1000_SYS_PINFUNC);
/* Audio: DIP7 selects I2S(0)/AC97(1), but need I2C for I2S!
* so: DIP7=1 || DIP8=0 => AC97, DIP7=0 && DIP8=1 => I2S
@@ -932,6 +922,11 @@ int __init db1200_dev_setup(void)
}
/* Audio PSC clock is supplied externally. (FIXME: platdata!!) */
c = clk_get(NULL, "psc1_intclk");
if (!IS_ERR(c)) {
clk_prepare_enable(c);
clk_put(c);
}
__raw_writel(PSC_SEL_CLK_SERCLK,
(void __iomem *)KSEG1ADDR(AU1550_PSC1_PHYS_ADDR) + PSC_SEL_OFFSET);
wmb();

View File

@@ -4,6 +4,7 @@
* (c) 2009 Manuel Lauss <manuel.lauss@googlemail.com>
*/
#include <linux/clk.h>
#include <linux/dma-mapping.h>
#include <linux/gpio.h>
#include <linux/gpio_keys.h>
@@ -169,7 +170,7 @@ static void au1300_nand_cmd_ctrl(struct mtd_info *mtd, int cmd,
static int au1300_nand_device_ready(struct mtd_info *mtd)
{
return __raw_readl((void __iomem *)MEM_STSTAT) & 1;
return alchemy_rdsmem(AU1000_MEM_STSTAT) & 1;
}
static struct mtd_partition db1300_nand_parts[] = {
@@ -731,6 +732,7 @@ static struct platform_device *db1300_dev[] __initdata = {
int __init db1300_dev_setup(void)
{
int swapped, cpldirq;
struct clk *c;
/* setup CPLD IRQ muxer */
cpldirq = au1300_gpio_to_irq(AU1300_PIN_EXTCLK1);
@@ -761,6 +763,11 @@ int __init db1300_dev_setup(void)
(void __iomem *)KSEG1ADDR(AU1300_PSC2_PHYS_ADDR) + PSC_SEL_OFFSET);
wmb();
/* I2C uses internal 48MHz EXTCLK1 */
c = clk_get(NULL, "psc3_intclk");
if (!IS_ERR(c)) {
clk_prepare_enable(c);
clk_put(c);
}
__raw_writel(PSC_SEL_CLK_INTCLK,
(void __iomem *)KSEG1ADDR(AU1300_PSC3_PHYS_ADDR) + PSC_SEL_OFFSET);
wmb();

View File

@@ -4,6 +4,7 @@
* (c) 2011 Manuel Lauss <manuel.lauss@googlemail.com>
*/
#include <linux/clk.h>
#include <linux/dma-mapping.h>
#include <linux/gpio.h>
#include <linux/i2c.h>
@@ -31,16 +32,16 @@
static void __init db1550_hw_setup(void)
{
void __iomem *base;
unsigned long v;
/* complete SPI setup: link psc0_intclk to a 48MHz source,
* and assign GPIO16 to PSC0_SYNC1 (SPI cs# line) as well as PSC1_SYNC
* for AC97 on PB1550.
*/
base = (void __iomem *)SYS_CLKSRC;
__raw_writel(__raw_readl(base) | 0x000001e0, base);
base = (void __iomem *)SYS_PINFUNC;
__raw_writel(__raw_readl(base) | 1 | SYS_PF_PSC1_S1, base);
wmb();
v = alchemy_rdsys(AU1000_SYS_CLKSRC);
alchemy_wrsys(v | 0x000001e0, AU1000_SYS_CLKSRC);
v = alchemy_rdsys(AU1000_SYS_PINFUNC);
alchemy_wrsys(v | 1 | SYS_PF_PSC1_S1, AU1000_SYS_PINFUNC);
/* reset the AC97 codec now, the reset time in the psc-ac97 driver
* is apparently too short although it's ridiculous as it is.
@@ -151,7 +152,7 @@ static void au1550_nand_cmd_ctrl(struct mtd_info *mtd, int cmd,
static int au1550_nand_device_ready(struct mtd_info *mtd)
{
return __raw_readl((void __iomem *)MEM_STSTAT) & 1;
return alchemy_rdsmem(AU1000_MEM_STSTAT) & 1;
}
static struct mtd_partition db1550_nand_parts[] = {
@@ -217,7 +218,7 @@ static struct platform_device pb1550_nand_dev = {
static void __init pb1550_nand_setup(void)
{
int boot_swapboot = (au_readl(MEM_STSTAT) & (0x7 << 1)) |
int boot_swapboot = (alchemy_rdsmem(AU1000_MEM_STSTAT) & (0x7 << 1)) |
((bcsr_read(BCSR_STATUS) >> 6) & 0x1);
gpio_direction_input(206); /* de-assert NAND CS# */
@@ -574,6 +575,7 @@ static void __init pb1550_devices(void)
int __init db1550_dev_setup(void)
{
int swapped, id;
struct clk *c;
id = (BCSR_WHOAMI_BOARD(bcsr_read(BCSR_WHOAMI)) != BCSR_WHOAMI_DB1550);
@@ -582,6 +584,17 @@ int __init db1550_dev_setup(void)
spi_register_board_info(db1550_spi_devs,
ARRAY_SIZE(db1550_i2c_devs));
c = clk_get(NULL, "psc0_intclk");
if (!IS_ERR(c)) {
clk_prepare_enable(c);
clk_put(c);
}
c = clk_get(NULL, "psc2_intclk");
if (!IS_ERR(c)) {
clk_prepare_enable(c);
clk_put(c);
}
/* Audio PSC clock is supplied by codecs (PSC1, 3) FIXME: platdata!! */
__raw_writel(PSC_SEL_CLK_SERCLK,
(void __iomem *)KSEG1ADDR(AU1550_PSC1_PHYS_ADDR) + PSC_SEL_OFFSET);

Some files were not shown because too many files have changed in this diff Show More