Commit 6969a434 authored by Linus Torvalds's avatar Linus Torvalds

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

* 'upstream' of git://ftp.linux-mips.org/pub/scm/upstream-linus: (25 commits)
  MIPS: Use GCC __builtin_prefetch() to implement prefetch().
  MIPS: Octeon: Serial port fixes for OCTEON simulator.
  MIPS: Octeon: Get rid of early serial.
  MIPS: AR7: prevent race between clock initialization and devices registration
  MIPS: AR7: use ar7_has_high_vlynq() to determine watchdog base address
  MIPS: BCM63xx: Avoid namespace clash on GPIO_DIR_{IN,OUT}
  MIPS: MTX-1: Update defconfig
  MIPS: BCM47xx: Update defconfig
  MIPS: RB532: Update defconfig
  MIPS: AR7: Update defconfig
  RTC: rtc-cmos: Fix binary mode support
  MIPS: Oprofile: Loongson: Cleanup the comments
  MIPS: Oprofile: Loongson: Cleanup of the macros
  MIPS: Oprofile: Loongson: Remove unused variable from loongson2_cpu_setup()
  MIPS: Oprofile: Loongson: Remove useless parentheses
  MIPS: Oprofile: Loongson: Unify macro for setting events
  MIPS: nofpu and nodsp only affect CPU0
  MIPS: Clean up tables for bootmem allocation
  MIPS: Coding style cleanups of access of FCSR rounding mode bits
  MIPS: Loongson 2F: Add gpio/gpioilb support
  ...
parents 0fc377bd 0453fb3c
...@@ -1075,6 +1075,8 @@ config CPU_LOONGSON2F ...@@ -1075,6 +1075,8 @@ config CPU_LOONGSON2F
bool "Loongson 2F" bool "Loongson 2F"
depends on SYS_HAS_CPU_LOONGSON2F depends on SYS_HAS_CPU_LOONGSON2F
select CPU_LOONGSON2 select CPU_LOONGSON2
select GENERIC_GPIO
select ARCH_REQUIRE_GPIOLIB
help help
The Loongson 2F processor implements the MIPS III instruction set The Loongson 2F processor implements the MIPS III instruction set
with many extensions. with many extensions.
......
...@@ -36,6 +36,7 @@ ...@@ -36,6 +36,7 @@
#include <linux/spinlock.h> #include <linux/spinlock.h>
#include <linux/interrupt.h> #include <linux/interrupt.h>
#include <linux/module.h> #include <linux/module.h>
#include <linux/sysdev.h>
#include <asm/mach-au1x00/au1000.h> #include <asm/mach-au1x00/au1000.h>
#include <asm/mach-au1x00/au1xxx_dbdma.h> #include <asm/mach-au1x00/au1xxx_dbdma.h>
...@@ -174,10 +175,6 @@ static dbdev_tab_t dbdev_tab[] = { ...@@ -174,10 +175,6 @@ static dbdev_tab_t dbdev_tab[] = {
#define DBDEV_TAB_SIZE ARRAY_SIZE(dbdev_tab) #define DBDEV_TAB_SIZE ARRAY_SIZE(dbdev_tab)
#ifdef CONFIG_PM
static u32 au1xxx_dbdma_pm_regs[NUM_DBDMA_CHANS + 1][6];
#endif
static chan_tab_t *chan_tab_ptr[NUM_DBDMA_CHANS]; static chan_tab_t *chan_tab_ptr[NUM_DBDMA_CHANS];
...@@ -960,29 +957,37 @@ u32 au1xxx_dbdma_put_dscr(u32 chanid, au1x_ddma_desc_t *dscr) ...@@ -960,29 +957,37 @@ u32 au1xxx_dbdma_put_dscr(u32 chanid, au1x_ddma_desc_t *dscr)
return nbytes; return nbytes;
} }
#ifdef CONFIG_PM
void au1xxx_dbdma_suspend(void) struct alchemy_dbdma_sysdev {
struct sys_device sysdev;
u32 pm_regs[NUM_DBDMA_CHANS + 1][6];
};
static int alchemy_dbdma_suspend(struct sys_device *dev,
pm_message_t state)
{ {
struct alchemy_dbdma_sysdev *sdev =
container_of(dev, struct alchemy_dbdma_sysdev, sysdev);
int i; int i;
u32 addr; u32 addr;
addr = DDMA_GLOBAL_BASE; addr = DDMA_GLOBAL_BASE;
au1xxx_dbdma_pm_regs[0][0] = au_readl(addr + 0x00); sdev->pm_regs[0][0] = au_readl(addr + 0x00);
au1xxx_dbdma_pm_regs[0][1] = au_readl(addr + 0x04); sdev->pm_regs[0][1] = au_readl(addr + 0x04);
au1xxx_dbdma_pm_regs[0][2] = au_readl(addr + 0x08); sdev->pm_regs[0][2] = au_readl(addr + 0x08);
au1xxx_dbdma_pm_regs[0][3] = au_readl(addr + 0x0c); sdev->pm_regs[0][3] = au_readl(addr + 0x0c);
/* save channel configurations */ /* save channel configurations */
for (i = 1, addr = DDMA_CHANNEL_BASE; i <= NUM_DBDMA_CHANS; i++) { for (i = 1, addr = DDMA_CHANNEL_BASE; i <= NUM_DBDMA_CHANS; i++) {
au1xxx_dbdma_pm_regs[i][0] = au_readl(addr + 0x00); sdev->pm_regs[i][0] = au_readl(addr + 0x00);
au1xxx_dbdma_pm_regs[i][1] = au_readl(addr + 0x04); sdev->pm_regs[i][1] = au_readl(addr + 0x04);
au1xxx_dbdma_pm_regs[i][2] = au_readl(addr + 0x08); sdev->pm_regs[i][2] = au_readl(addr + 0x08);
au1xxx_dbdma_pm_regs[i][3] = au_readl(addr + 0x0c); sdev->pm_regs[i][3] = au_readl(addr + 0x0c);
au1xxx_dbdma_pm_regs[i][4] = au_readl(addr + 0x10); sdev->pm_regs[i][4] = au_readl(addr + 0x10);
au1xxx_dbdma_pm_regs[i][5] = au_readl(addr + 0x14); sdev->pm_regs[i][5] = au_readl(addr + 0x14);
/* halt channel */ /* halt channel */
au_writel(au1xxx_dbdma_pm_regs[i][0] & ~1, addr + 0x00); au_writel(sdev->pm_regs[i][0] & ~1, addr + 0x00);
au_sync(); au_sync();
while (!(au_readl(addr + 0x14) & 1)) while (!(au_readl(addr + 0x14) & 1))
au_sync(); au_sync();
...@@ -992,32 +997,65 @@ void au1xxx_dbdma_suspend(void) ...@@ -992,32 +997,65 @@ void au1xxx_dbdma_suspend(void)
/* disable channel interrupts */ /* disable channel interrupts */
au_writel(0, DDMA_GLOBAL_BASE + 0x0c); au_writel(0, DDMA_GLOBAL_BASE + 0x0c);
au_sync(); au_sync();
return 0;
} }
void au1xxx_dbdma_resume(void) static int alchemy_dbdma_resume(struct sys_device *dev)
{ {
struct alchemy_dbdma_sysdev *sdev =
container_of(dev, struct alchemy_dbdma_sysdev, sysdev);
int i; int i;
u32 addr; u32 addr;
addr = DDMA_GLOBAL_BASE; addr = DDMA_GLOBAL_BASE;
au_writel(au1xxx_dbdma_pm_regs[0][0], addr + 0x00); au_writel(sdev->pm_regs[0][0], addr + 0x00);
au_writel(au1xxx_dbdma_pm_regs[0][1], addr + 0x04); au_writel(sdev->pm_regs[0][1], addr + 0x04);
au_writel(au1xxx_dbdma_pm_regs[0][2], addr + 0x08); au_writel(sdev->pm_regs[0][2], addr + 0x08);
au_writel(au1xxx_dbdma_pm_regs[0][3], addr + 0x0c); au_writel(sdev->pm_regs[0][3], addr + 0x0c);
/* restore channel configurations */ /* restore channel configurations */
for (i = 1, addr = DDMA_CHANNEL_BASE; i <= NUM_DBDMA_CHANS; i++) { for (i = 1, addr = DDMA_CHANNEL_BASE; i <= NUM_DBDMA_CHANS; i++) {
au_writel(au1xxx_dbdma_pm_regs[i][0], addr + 0x00); au_writel(sdev->pm_regs[i][0], addr + 0x00);
au_writel(au1xxx_dbdma_pm_regs[i][1], addr + 0x04); au_writel(sdev->pm_regs[i][1], addr + 0x04);
au_writel(au1xxx_dbdma_pm_regs[i][2], addr + 0x08); au_writel(sdev->pm_regs[i][2], addr + 0x08);
au_writel(au1xxx_dbdma_pm_regs[i][3], addr + 0x0c); au_writel(sdev->pm_regs[i][3], addr + 0x0c);
au_writel(au1xxx_dbdma_pm_regs[i][4], addr + 0x10); au_writel(sdev->pm_regs[i][4], addr + 0x10);
au_writel(au1xxx_dbdma_pm_regs[i][5], addr + 0x14); au_writel(sdev->pm_regs[i][5], addr + 0x14);
au_sync(); au_sync();
addr += 0x100; /* next channel base */ addr += 0x100; /* next channel base */
} }
return 0;
}
static struct sysdev_class alchemy_dbdma_sysdev_class = {
.name = "dbdma",
.suspend = alchemy_dbdma_suspend,
.resume = alchemy_dbdma_resume,
};
static int __init alchemy_dbdma_sysdev_init(void)
{
struct alchemy_dbdma_sysdev *sdev;
int ret;
ret = sysdev_class_register(&alchemy_dbdma_sysdev_class);
if (ret)
return ret;
sdev = kzalloc(sizeof(struct alchemy_dbdma_sysdev), GFP_KERNEL);
if (!sdev)
return -ENOMEM;
sdev->sysdev.id = -1;
sdev->sysdev.cls = &alchemy_dbdma_sysdev_class;
ret = sysdev_register(&sdev->sysdev);
if (ret)
kfree(sdev);
return ret;
} }
#endif /* CONFIG_PM */
static int __init au1xxx_dbdma_init(void) static int __init au1xxx_dbdma_init(void)
{ {
...@@ -1046,6 +1084,11 @@ static int __init au1xxx_dbdma_init(void) ...@@ -1046,6 +1084,11 @@ static int __init au1xxx_dbdma_init(void)
else { else {
dbdma_initialized = 1; dbdma_initialized = 1;
printk(KERN_INFO "Alchemy DBDMA initialized\n"); printk(KERN_INFO "Alchemy DBDMA initialized\n");
ret = alchemy_dbdma_sysdev_init();
if (ret) {
printk(KERN_ERR "DBDMA PM init failed\n");
ret = 0;
}
} }
return ret; return ret;
......
...@@ -29,6 +29,8 @@ ...@@ -29,6 +29,8 @@
#include <linux/init.h> #include <linux/init.h>
#include <linux/interrupt.h> #include <linux/interrupt.h>
#include <linux/irq.h> #include <linux/irq.h>
#include <linux/slab.h>
#include <linux/sysdev.h>
#include <asm/irq_cpu.h> #include <asm/irq_cpu.h>
#include <asm/mipsregs.h> #include <asm/mipsregs.h>
...@@ -216,90 +218,6 @@ struct au1xxx_irqmap au1200_irqmap[] __initdata = { ...@@ -216,90 +218,6 @@ struct au1xxx_irqmap au1200_irqmap[] __initdata = {
}; };
#ifdef CONFIG_PM
/*
* Save/restore the interrupt controller state.
* Called from the save/restore core registers as part of the
* au_sleep function in power.c.....maybe I should just pm_register()
* them instead?
*/
static unsigned int sleep_intctl_config0[2];
static unsigned int sleep_intctl_config1[2];
static unsigned int sleep_intctl_config2[2];
static unsigned int sleep_intctl_src[2];
static unsigned int sleep_intctl_assign[2];
static unsigned int sleep_intctl_wake[2];
static unsigned int sleep_intctl_mask[2];
void save_au1xxx_intctl(void)
{
sleep_intctl_config0[0] = au_readl(IC0_CFG0RD);
sleep_intctl_config1[0] = au_readl(IC0_CFG1RD);
sleep_intctl_config2[0] = au_readl(IC0_CFG2RD);
sleep_intctl_src[0] = au_readl(IC0_SRCRD);
sleep_intctl_assign[0] = au_readl(IC0_ASSIGNRD);
sleep_intctl_wake[0] = au_readl(IC0_WAKERD);
sleep_intctl_mask[0] = au_readl(IC0_MASKRD);
sleep_intctl_config0[1] = au_readl(IC1_CFG0RD);
sleep_intctl_config1[1] = au_readl(IC1_CFG1RD);
sleep_intctl_config2[1] = au_readl(IC1_CFG2RD);
sleep_intctl_src[1] = au_readl(IC1_SRCRD);
sleep_intctl_assign[1] = au_readl(IC1_ASSIGNRD);
sleep_intctl_wake[1] = au_readl(IC1_WAKERD);
sleep_intctl_mask[1] = au_readl(IC1_MASKRD);
}
/*
* For most restore operations, we clear the entire register and
* then set the bits we found during the save.
*/
void restore_au1xxx_intctl(void)
{
au_writel(0xffffffff, IC0_MASKCLR); au_sync();
au_writel(0xffffffff, IC0_CFG0CLR); au_sync();
au_writel(sleep_intctl_config0[0], IC0_CFG0SET); au_sync();
au_writel(0xffffffff, IC0_CFG1CLR); au_sync();
au_writel(sleep_intctl_config1[0], IC0_CFG1SET); au_sync();
au_writel(0xffffffff, IC0_CFG2CLR); au_sync();
au_writel(sleep_intctl_config2[0], IC0_CFG2SET); au_sync();
au_writel(0xffffffff, IC0_SRCCLR); au_sync();
au_writel(sleep_intctl_src[0], IC0_SRCSET); au_sync();
au_writel(0xffffffff, IC0_ASSIGNCLR); au_sync();
au_writel(sleep_intctl_assign[0], IC0_ASSIGNSET); au_sync();
au_writel(0xffffffff, IC0_WAKECLR); au_sync();
au_writel(sleep_intctl_wake[0], IC0_WAKESET); au_sync();
au_writel(0xffffffff, IC0_RISINGCLR); au_sync();
au_writel(0xffffffff, IC0_FALLINGCLR); au_sync();
au_writel(0x00000000, IC0_TESTBIT); au_sync();
au_writel(0xffffffff, IC1_MASKCLR); au_sync();
au_writel(0xffffffff, IC1_CFG0CLR); au_sync();
au_writel(sleep_intctl_config0[1], IC1_CFG0SET); au_sync();
au_writel(0xffffffff, IC1_CFG1CLR); au_sync();
au_writel(sleep_intctl_config1[1], IC1_CFG1SET); au_sync();
au_writel(0xffffffff, IC1_CFG2CLR); au_sync();
au_writel(sleep_intctl_config2[1], IC1_CFG2SET); au_sync();
au_writel(0xffffffff, IC1_SRCCLR); au_sync();
au_writel(sleep_intctl_src[1], IC1_SRCSET); au_sync();
au_writel(0xffffffff, IC1_ASSIGNCLR); au_sync();
au_writel(sleep_intctl_assign[1], IC1_ASSIGNSET); au_sync();
au_writel(0xffffffff, IC1_WAKECLR); au_sync();
au_writel(sleep_intctl_wake[1], IC1_WAKESET); au_sync();
au_writel(0xffffffff, IC1_RISINGCLR); au_sync();
au_writel(0xffffffff, IC1_FALLINGCLR); au_sync();
au_writel(0x00000000, IC1_TESTBIT); au_sync();
au_writel(sleep_intctl_mask[1], IC1_MASKSET); au_sync();
au_writel(sleep_intctl_mask[0], IC0_MASKSET); au_sync();
}
#endif /* CONFIG_PM */
static void au1x_ic0_unmask(unsigned int irq_nr) static void au1x_ic0_unmask(unsigned int irq_nr)
{ {
unsigned int bit = irq_nr - AU1000_INTC0_INT_BASE; unsigned int bit = irq_nr - AU1000_INTC0_INT_BASE;
...@@ -635,3 +553,91 @@ void __init arch_init_irq(void) ...@@ -635,3 +553,91 @@ void __init arch_init_irq(void)
break; break;
} }
} }
struct alchemy_ic_sysdev {
struct sys_device sysdev;
void __iomem *base;
unsigned long pmdata[7];
};
static int alchemy_ic_suspend(struct sys_device *dev, pm_message_t state)
{
struct alchemy_ic_sysdev *icdev =
container_of(dev, struct alchemy_ic_sysdev, sysdev);
icdev->pmdata[0] = __raw_readl(icdev->base + IC_CFG0RD);
icdev->pmdata[1] = __raw_readl(icdev->base + IC_CFG1RD);
icdev->pmdata[2] = __raw_readl(icdev->base + IC_CFG2RD);
icdev->pmdata[3] = __raw_readl(icdev->base + IC_SRCRD);
icdev->pmdata[4] = __raw_readl(icdev->base + IC_ASSIGNRD);
icdev->pmdata[5] = __raw_readl(icdev->base + IC_WAKERD);
icdev->pmdata[6] = __raw_readl(icdev->base + IC_MASKRD);
return 0;
}
static int alchemy_ic_resume(struct sys_device *dev)
{
struct alchemy_ic_sysdev *icdev =
container_of(dev, struct alchemy_ic_sysdev, sysdev);
__raw_writel(0xffffffff, icdev->base + IC_MASKCLR);
__raw_writel(0xffffffff, icdev->base + IC_CFG0CLR);
__raw_writel(0xffffffff, icdev->base + IC_CFG1CLR);
__raw_writel(0xffffffff, icdev->base + IC_CFG2CLR);
__raw_writel(0xffffffff, icdev->base + IC_SRCCLR);
__raw_writel(0xffffffff, icdev->base + IC_ASSIGNCLR);
__raw_writel(0xffffffff, icdev->base + IC_WAKECLR);
__raw_writel(0xffffffff, icdev->base + IC_RISINGCLR);
__raw_writel(0xffffffff, icdev->base + IC_FALLINGCLR);
__raw_writel(0x00000000, icdev->base + IC_TESTBIT);
wmb();
__raw_writel(icdev->pmdata[0], icdev->base + IC_CFG0SET);
__raw_writel(icdev->pmdata[1], icdev->base + IC_CFG1SET);
__raw_writel(icdev->pmdata[2], icdev->base + IC_CFG2SET);
__raw_writel(icdev->pmdata[3], icdev->base + IC_SRCSET);
__raw_writel(icdev->pmdata[4], icdev->base + IC_ASSIGNSET);
__raw_writel(icdev->pmdata[5], icdev->base + IC_WAKESET);
wmb();
__raw_writel(icdev->pmdata[6], icdev->base + IC_MASKSET);
wmb();
return 0;
}
static struct sysdev_class alchemy_ic_sysdev_class = {
.name = "ic",
.suspend = alchemy_ic_suspend,
.resume = alchemy_ic_resume,
};
static int __init alchemy_ic_sysdev_init(void)
{
struct alchemy_ic_sysdev *icdev;
unsigned long icbase[2] = { IC0_PHYS_ADDR, IC1_PHYS_ADDR };
int err, i;
err = sysdev_class_register(&alchemy_ic_sysdev_class);
if (err)
return err;
for (i = 0; i < 2; i++) {
icdev = kzalloc(sizeof(struct alchemy_ic_sysdev), GFP_KERNEL);
if (!icdev)
return -ENOMEM;
icdev->base = ioremap(icbase[i], 0x1000);
icdev->sysdev.id = i;
icdev->sysdev.cls = &alchemy_ic_sysdev_class;
err = sysdev_register(&icdev->sysdev);
if (err) {
kfree(icdev);
return err;
}
}
return 0;
}
device_initcall(alchemy_ic_sysdev_init);
...@@ -36,9 +36,6 @@ ...@@ -36,9 +36,6 @@
#include <asm/uaccess.h> #include <asm/uaccess.h>
#include <asm/mach-au1x00/au1000.h> #include <asm/mach-au1x00/au1000.h>
#if defined(CONFIG_SOC_AU1550) || defined(CONFIG_SOC_AU1200)
#include <asm/mach-au1x00/au1xxx_dbdma.h>
#endif
#ifdef CONFIG_PM #ifdef CONFIG_PM
...@@ -106,9 +103,6 @@ static void save_core_regs(void) ...@@ -106,9 +103,6 @@ static void save_core_regs(void)
sleep_usb[1] = au_readl(0xb4020024); /* OTG_MUX */ sleep_usb[1] = au_readl(0xb4020024); /* OTG_MUX */
#endif #endif
/* Save interrupt controller state. */
save_au1xxx_intctl();
/* Clocks and PLLs. */ /* Clocks and PLLs. */
sleep_sys_clocks[0] = au_readl(SYS_FREQCTRL0); sleep_sys_clocks[0] = au_readl(SYS_FREQCTRL0);
sleep_sys_clocks[1] = au_readl(SYS_FREQCTRL1); sleep_sys_clocks[1] = au_readl(SYS_FREQCTRL1);
...@@ -132,10 +126,6 @@ static void save_core_regs(void) ...@@ -132,10 +126,6 @@ static void save_core_regs(void)
sleep_static_memctlr[3][0] = au_readl(MEM_STCFG3); sleep_static_memctlr[3][0] = au_readl(MEM_STCFG3);
sleep_static_memctlr[3][1] = au_readl(MEM_STTIME3); sleep_static_memctlr[3][1] = au_readl(MEM_STTIME3);
sleep_static_memctlr[3][2] = au_readl(MEM_STADDR3); sleep_static_memctlr[3][2] = au_readl(MEM_STADDR3);
#if defined(CONFIG_SOC_AU1550) || defined(CONFIG_SOC_AU1200)
au1xxx_dbdma_suspend();
#endif
} }
static void restore_core_regs(void) static void restore_core_regs(void)
...@@ -199,12 +189,6 @@ static void restore_core_regs(void) ...@@ -199,12 +189,6 @@ static void restore_core_regs(void)
au_writel(sleep_uart0_linectl, UART0_ADDR + UART_LCR); au_sync(); au_writel(sleep_uart0_linectl, UART0_ADDR + UART_LCR); au_sync();
au_writel(sleep_uart0_clkdiv, UART0_ADDR + UART_CLK); au_sync(); au_writel(sleep_uart0_clkdiv, UART0_ADDR + UART_CLK); au_sync();
} }
restore_au1xxx_intctl();
#if defined(CONFIG_SOC_AU1550) || defined(CONFIG_SOC_AU1200)
au1xxx_dbdma_resume();
#endif
} }
void au_sleep(void) void au_sleep(void)
......
...@@ -27,8 +27,10 @@ ...@@ -27,8 +27,10 @@
#include <linux/gpio.h> #include <linux/gpio.h>
#include <linux/init.h> #include <linux/init.h>
#include <linux/interrupt.h> #include <linux/interrupt.h>
#include <linux/pm.h>
#include <asm/mach-au1x00/au1000.h> #include <asm/mach-au1x00/au1000.h>
#include <asm/mach-pb1x00/pb1000.h> #include <asm/mach-pb1x00/pb1000.h>
#include <asm/reboot.h>
#include <prom.h> #include <prom.h>
#include "../platform.h" #include "../platform.h"
...@@ -38,8 +40,16 @@ const char *get_system_type(void) ...@@ -38,8 +40,16 @@ const char *get_system_type(void)
return "Alchemy Pb1000"; return "Alchemy Pb1000";
} }
void board_reset(void) static void board_reset(char *c)
{ {
asm volatile ("jr %0" : : "r" (0xbfc00000));
}
static void board_power_off(void)
{
printk(KERN_ALERT "It's now safe to remove power\n");
while (1)
asm volatile (".set mips3 ; wait ; .set mips1");
} }
void __init board_setup(void) void __init board_setup(void)
...@@ -177,6 +187,10 @@ void __init board_setup(void) ...@@ -177,6 +187,10 @@ void __init board_setup(void)
au_writel(au_readl(SYS_POWERCTRL) | (0x3 << 5), SYS_POWERCTRL); au_writel(au_readl(SYS_POWERCTRL) | (0x3 << 5), SYS_POWERCTRL);
break; break;
} }
pm_power_off = board_power_off;
_machine_halt = board_power_off;
_machine_restart = board_reset;
} }
static int __init pb1000_init_irq(void) static int __init pb1000_init_irq(void)
......
...@@ -39,11 +39,6 @@ const char *get_system_type(void) ...@@ -39,11 +39,6 @@ const char *get_system_type(void)
return "Alchemy Pb1100"; return "Alchemy Pb1100";
} }
void board_reset(void)
{
bcsr_write(BCSR_SYSTEM, 0);
}
void __init board_setup(void) void __init board_setup(void)
{ {
volatile void __iomem *base = (volatile void __iomem *)0xac000000UL; volatile void __iomem *base = (volatile void __iomem *)0xac000000UL;
......
...@@ -48,12 +48,6 @@ const char *get_system_type(void) ...@@ -48,12 +48,6 @@ const char *get_system_type(void)
return "Alchemy Pb1200"; return "Alchemy Pb1200";
} }
void board_reset(void)
{
bcsr_write(BCSR_RESETS, 0);
bcsr_write(BCSR_SYSTEM, 0);
}
void __init board_setup(void) void __init board_setup(void)
{ {
printk(KERN_INFO "AMD Alchemy Pb1200 Board\n"); printk(KERN_INFO "AMD Alchemy Pb1200 Board\n");
......
...@@ -45,11 +45,6 @@ const char *get_system_type(void) ...@@ -45,11 +45,6 @@ const char *get_system_type(void)
return "Alchemy Pb1500"; return "Alchemy Pb1500";
} }
void board_reset(void)
{
bcsr_write(BCSR_SYSTEM, 0);
}
void __init board_setup(void) void __init board_setup(void)
{ {
u32 pin_func; u32 pin_func;
......
...@@ -48,11 +48,6 @@ const char *get_system_type(void) ...@@ -48,11 +48,6 @@ const char *get_system_type(void)
return "Alchemy Pb1550"; return "Alchemy Pb1550";
} }
void board_reset(void)
{
bcsr_write(BCSR_SYSTEM, 0);
}
void __init board_setup(void) void __init board_setup(void)
{ {
u32 pin_func; u32 pin_func;
......
...@@ -576,7 +576,6 @@ static int __init ar7_register_devices(void) ...@@ -576,7 +576,6 @@ static int __init ar7_register_devices(void)
{ {
void __iomem *bootcr; void __iomem *bootcr;
u32 val; u32 val;
u16 chip_id;
int res; int res;
res = ar7_register_uarts(); res = ar7_register_uarts();
...@@ -635,18 +634,10 @@ static int __init ar7_register_devices(void) ...@@ -635,18 +634,10 @@ static int __init ar7_register_devices(void)
val = readl(bootcr); val = readl(bootcr);
iounmap(bootcr); iounmap(bootcr);
if (val & AR7_WDT_HW_ENA) { if (val & AR7_WDT_HW_ENA) {
chip_id = ar7_chip_id(); if (ar7_has_high_vlynq())
switch (chip_id) {
case AR7_CHIP_7100:
case AR7_CHIP_7200:
ar7_wdt_res.start = AR7_REGS_WDT;
break;
case AR7_CHIP_7300:
ar7_wdt_res.start = UR8_REGS_WDT; ar7_wdt_res.start = UR8_REGS_WDT;
break; else
default: ar7_wdt_res.start = AR7_REGS_WDT;
break;
}
ar7_wdt_res.end = ar7_wdt_res.start + 0x20; ar7_wdt_res.end = ar7_wdt_res.start + 0x20;
res = platform_device_register(&ar7_wdt); res = platform_device_register(&ar7_wdt);
...@@ -656,4 +647,4 @@ static int __init ar7_register_devices(void) ...@@ -656,4 +647,4 @@ static int __init ar7_register_devices(void)
return 0; return 0;
} }
arch_initcall(ar7_register_devices); device_initcall(ar7_register_devices);
...@@ -91,7 +91,7 @@ static int bcm63xx_gpio_set_direction(struct gpio_chip *chip, ...@@ -91,7 +91,7 @@ static int bcm63xx_gpio_set_direction(struct gpio_chip *chip,
spin_lock_irqsave(&bcm63xx_gpio_lock, flags); spin_lock_irqsave(&bcm63xx_gpio_lock, flags);
tmp = bcm_gpio_readl(reg); tmp = bcm_gpio_readl(reg);
if (dir == GPIO_DIR_IN) if (dir == BCM63XX_GPIO_DIR_IN)
tmp &= ~mask; tmp &= ~mask;
else else
tmp |= mask; tmp |= mask;
...@@ -103,14 +103,14 @@ static int bcm63xx_gpio_set_direction(struct gpio_chip *chip, ...@@ -103,14 +103,14 @@ static int bcm63xx_gpio_set_direction(struct gpio_chip *chip,
static int bcm63xx_gpio_direction_input(struct gpio_chip *chip, unsigned gpio) static int bcm63xx_gpio_direction_input(struct gpio_chip *chip, unsigned gpio)
{ {
return bcm63xx_gpio_set_direction(chip, gpio, GPIO_DIR_IN); return bcm63xx_gpio_set_direction(chip, gpio, BCM63XX_GPIO_DIR_IN);
} }
static int bcm63xx_gpio_direction_output(struct gpio_chip *chip, static int bcm63xx_gpio_direction_output(struct gpio_chip *chip,
unsigned gpio, int value) unsigned gpio, int value)
{ {
bcm63xx_gpio_set(chip, gpio, value); bcm63xx_gpio_set(chip, gpio, value);
return bcm63xx_gpio_set_direction(chip, gpio, GPIO_DIR_OUT); return bcm63xx_gpio_set_direction(chip, gpio, BCM63XX_GPIO_DIR_OUT);
} }
......
...@@ -65,7 +65,11 @@ static void __init octeon_uart_set_common(struct plat_serial8250_port *p) ...@@ -65,7 +65,11 @@ static void __init octeon_uart_set_common(struct plat_serial8250_port *p)
p->type = PORT_OCTEON; p->type = PORT_OCTEON;
p->iotype = UPIO_MEM; p->iotype = UPIO_MEM;
p->regshift = 3; /* I/O addresses are every 8 bytes */ p->regshift = 3; /* I/O addresses are every 8 bytes */
p->uartclk = mips_hpt_frequency; if (octeon_is_simulation())
/* Make simulator output fast*/
p->uartclk = 115200 * 16;
else
p->uartclk = mips_hpt_frequency;
p->serial_in = octeon_serial_in; p->serial_in = octeon_serial_in;
p->serial_out = octeon_serial_out; p->serial_out = octeon_serial_out;
} }
......
...@@ -403,7 +403,6 @@ void __init prom_init(void) ...@@ -403,7 +403,6 @@ void __init prom_init(void)
const int coreid = cvmx_get_core_num(); const int coreid = cvmx_get_core_num();
int i; int i;
int argc; int argc;
struct uart_port octeon_port;
#ifdef CONFIG_CAVIUM_RESERVE32 #ifdef CONFIG_CAVIUM_RESERVE32
int64_t addr = -1; int64_t addr = -1;
#endif #endif
...@@ -610,30 +609,6 @@ void __init prom_init(void) ...@@ -610,30 +609,6 @@ void __init prom_init(void)
_machine_restart = octeon_restart; _machine_restart = octeon_restart;
_machine_halt = octeon_halt; _machine_halt = octeon_halt;
memset(&octeon_port, 0, sizeof(octeon_port));
/*
* For early_serial_setup we don't set the port type or
* UPF_FIXED_TYPE.
*/
octeon_port.flags = ASYNC_SKIP_TEST | UPF_SHARE_IRQ;
octeon_port.iotype = UPIO_MEM;
/* I/O addresses are every 8 bytes */
octeon_port.regshift = 3;
/* Clock rate of the chip */
octeon_port.uartclk = mips_hpt_frequency;
octeon_port.fifosize = 64;
octeon_port.mapbase = 0x0001180000000800ull + (1024 * octeon_uart);
octeon_port.membase = cvmx_phys_to_ptr(octeon_port.mapbase);
octeon_port.serial_in = octeon_serial_in;
octeon_port.serial_out = octeon_serial_out;
#ifdef CONFIG_CAVIUM_OCTEON_2ND_KERNEL
octeon_port.line = 0;
#else
octeon_port.line = octeon_uart;
#endif
octeon_port.irq = 42 + octeon_uart;
early_serial_setup(&octeon_port);
octeon_user_io_init(); octeon_user_io_init();
register_smp_ops(&octeon_smp_ops); register_smp_ops(&octeon_smp_ops);
} }
...@@ -727,7 +702,7 @@ int prom_putchar(char c) ...@@ -727,7 +702,7 @@ int prom_putchar(char c)
} while ((lsrval & 0x20) == 0); } while ((lsrval & 0x20) == 0);
/* Write the byte */ /* Write the byte */
cvmx_write_csr(CVMX_MIO_UARTX_THR(octeon_uart), c); cvmx_write_csr(CVMX_MIO_UARTX_THR(octeon_uart), c & 0xffull);
return 1; return 1;
} }
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
...@@ -190,8 +190,6 @@ extern unsigned long au1xxx_calc_clock(void); ...@@ -190,8 +190,6 @@ extern unsigned long au1xxx_calc_clock(void);
/* PM: arch/mips/alchemy/common/sleeper.S, power.c, irq.c */ /* PM: arch/mips/alchemy/common/sleeper.S, power.c, irq.c */
void au1xxx_save_and_sleep(void); void au1xxx_save_and_sleep(void);
void au_sleep(void); void au_sleep(void);
void save_au1xxx_intctl(void);
void restore_au1xxx_intctl(void);
/* SOC Interrupt numbers */ /* SOC Interrupt numbers */
...@@ -835,6 +833,38 @@ enum soc_au1200_ints { ...@@ -835,6 +833,38 @@ enum soc_au1200_ints {
#define MEM_STNAND_DATA 0x20 #define MEM_STNAND_DATA 0x20
#endif #endif
/* Interrupt Controller register offsets */
#define IC_CFG0RD 0x40
#define IC_CFG0SET 0x40
#define IC_CFG0CLR 0x44
#define IC_CFG1RD 0x48
#define IC_CFG1SET 0x48
#define IC_CFG1CLR 0x4C
#define IC_CFG2RD 0x50
#define IC_CFG2SET 0x50
#define IC_CFG2CLR 0x54
#define IC_REQ0INT 0x54
#define IC_SRCRD 0x58
#define IC_SRCSET 0x58
#define IC_SRCCLR 0x5C
#define IC_REQ1INT 0x5C
#define IC_ASSIGNRD 0x60
#define IC_ASSIGNSET 0x60
#define IC_ASSIGNCLR 0x64
#define IC_WAKERD 0x68
#define IC_WAKESET 0x68
#define IC_WAKECLR 0x6C
#define IC_MASKRD 0x70
#define IC_MASKSET 0x70
#define IC_MASKCLR 0x74
#define IC_RISINGRD 0x78
#define IC_RISINGCLR 0x78
#define IC_FALLINGRD 0x7C
#define IC_FALLINGCLR 0x7C
#define IC_TESTBIT 0x80
/* Interrupt Controller 0 */ /* Interrupt Controller 0 */
#define IC0_CFG0RD 0xB0400040 #define IC0_CFG0RD 0xB0400040
#define IC0_CFG0SET 0xB0400040 #define IC0_CFG0SET 0xB0400040
......
...@@ -358,10 +358,6 @@ u32 au1xxx_dbdma_put_dscr(u32 chanid, au1x_ddma_desc_t *dscr); ...@@ -358,10 +358,6 @@ u32 au1xxx_dbdma_put_dscr(u32 chanid, au1x_ddma_desc_t *dscr);
u32 au1xxx_ddma_add_device(dbdev_tab_t *dev); u32 au1xxx_ddma_add_device(dbdev_tab_t *dev);
extern void au1xxx_ddma_del_device(u32 devid); extern void au1xxx_ddma_del_device(u32 devid);
void *au1xxx_ddma_get_nextptr_virt(au1x_ddma_desc_t *dp); void *au1xxx_ddma_get_nextptr_virt(au1x_ddma_desc_t *dp);
#ifdef CONFIG_PM
void au1xxx_dbdma_suspend(void);
void au1xxx_dbdma_resume(void);
#endif
/* /*
* Flags for the put_source/put_dest functions. * Flags for the put_source/put_dest functions.
......
...@@ -20,7 +20,7 @@ static inline unsigned long bcm63xx_gpio_count(void) ...@@ -20,7 +20,7 @@ static inline unsigned long bcm63xx_gpio_count(void)
} }
} }
#define GPIO_DIR_OUT 0x0 #define BCM63XX_GPIO_DIR_OUT 0x0
#define GPIO_DIR_IN 0x1 #define BCM63XX_GPIO_DIR_IN 0x1
#endif /* !BCM63XX_GPIO_H */ #endif /* !BCM63XX_GPIO_H */
...@@ -52,6 +52,8 @@ ...@@ -52,6 +52,8 @@
#define cpu_has_tx39_cache 0 #define cpu_has_tx39_cache 0
#define cpu_has_userlocal 0 #define cpu_has_userlocal 0
#define cpu_has_vce 0 #define cpu_has_vce 0
#define cpu_has_veic 0
#define cpu_has_vint 0
#define cpu_has_vtag_icache 0 #define cpu_has_vtag_icache 0
#define cpu_has_watch 1 #define cpu_has_watch 1
......
/*
* STLS2F GPIO Support
*
* Copyright (c) 2008 Richard Liu, STMicroelectronics <richard.liu@st.com>
* Copyright (c) 2008-2010 Arnaud Patard <apatard@mandriva.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.
*/
#ifndef __STLS2F_GPIO_H
#define __STLS2F_GPIO_H
#include <asm-generic/gpio.h>
extern void gpio_set_value(unsigned gpio, int value);
extern int gpio_get_value(unsigned gpio);
extern int gpio_cansleep(unsigned gpio);
/* The chip can do interrupt
* but it has not been tested and doc not clear
*/
static inline int gpio_to_irq(int gpio)
{
return -EINVAL;
}
static inline int irq_to_gpio(int gpio)
{
return -EINVAL;
}
#endif /* __STLS2F_GPIO_H */
...@@ -344,16 +344,10 @@ unsigned long get_wchan(struct task_struct *p); ...@@ -344,16 +344,10 @@ unsigned long get_wchan(struct task_struct *p);
#ifdef CONFIG_CPU_HAS_PREFETCH #ifdef CONFIG_CPU_HAS_PREFETCH
#define ARCH_HAS_PREFETCH #define ARCH_HAS_PREFETCH
#define prefetch(x) __builtin_prefetch((x), 0, 1)
static inline void prefetch(const void *addr) #define ARCH_HAS_PREFETCHW
{ #define prefetchw(x) __builtin_prefetch((x), 1, 1)
__asm__ __volatile__(
" .set mips4 \n"
" pref %0, (%1) \n"
" .set mips0 \n"
:
: "i" (Pref_Load), "r" (addr));
}
#endif #endif
......
...@@ -125,6 +125,30 @@ static int __init wait_disable(char *s) ...@@ -125,6 +125,30 @@ static int __init wait_disable(char *s)
__setup("nowait", wait_disable); __setup("nowait", wait_disable);
static int __cpuinitdata mips_fpu_disabled;
static int __init fpu_disable(char *s)
{
cpu_data[0].options &= ~MIPS_CPU_FPU;
mips_fpu_disabled = 1;
return 1;
}
__setup("nofpu", fpu_disable);
int __cpuinitdata mips_dsp_disabled;
static int __init dsp_disable(char *s)
{
cpu_data[0].ases &= ~MIPS_ASE_DSP;
mips_dsp_disabled = 1;
return 1;
}
__setup("nodsp", dsp_disable);
void __init check_wait(void) void __init check_wait(void)
{ {
struct cpuinfo_mips *c = &current_cpu_data; struct cpuinfo_mips *c = &current_cpu_data;
...@@ -982,6 +1006,12 @@ __cpuinit void cpu_probe(void) ...@@ -982,6 +1006,12 @@ __cpuinit void cpu_probe(void)
*/ */
BUG_ON(current_cpu_type() != c->cputype); BUG_ON(current_cpu_type() != c->cputype);
if (mips_fpu_disabled)
c->options &= ~MIPS_CPU_FPU;
if (mips_dsp_disabled)
c->ases &= ~MIPS_ASE_DSP;
if (c->options & MIPS_CPU_FPU) { if (c->options & MIPS_CPU_FPU) {
c->fpu_id = cpu_get_fpu_id(); c->fpu_id = cpu_get_fpu_id();
......
...@@ -65,7 +65,7 @@ static int loongson2_cpufreq_target(struct cpufreq_policy *policy, ...@@ -65,7 +65,7 @@ static int loongson2_cpufreq_target(struct cpufreq_policy *policy,
return -ENODEV; return -ENODEV;
cpus_allowed = current->cpus_allowed; cpus_allowed = current->cpus_allowed;
set_cpus_allowed(current, cpumask_of_cpu(cpu)); set_cpus_allowed_ptr(current, cpumask_of(cpu));
if (cpufreq_frequency_table_target if (cpufreq_frequency_table_target
(policy, &loongson2_clockmod_table[0], target_freq, relation, (policy, &loongson2_clockmod_table[0], target_freq, relation,
...@@ -91,7 +91,7 @@ static int loongson2_cpufreq_target(struct cpufreq_policy *policy, ...@@ -91,7 +91,7 @@ static int loongson2_cpufreq_target(struct cpufreq_policy *policy,
/* notifiers */ /* notifiers */
cpufreq_notify_transition(&freqs, CPUFREQ_PRECHANGE); cpufreq_notify_transition(&freqs, CPUFREQ_PRECHANGE);
set_cpus_allowed(current, cpus_allowed); set_cpus_allowed_ptr(current, &cpus_allowed);
/* setting the cpu frequency */ /* setting the cpu frequency */
clk_set_rate(cpuclk, freq); clk_set_rate(cpuclk, freq);
......
...@@ -100,10 +100,10 @@ asmlinkage long mipsmt_sys_sched_setaffinity(pid_t pid, unsigned int len, ...@@ -100,10 +100,10 @@ asmlinkage long mipsmt_sys_sched_setaffinity(pid_t pid, unsigned int len,
if (test_ti_thread_flag(ti, TIF_FPUBOUND) && if (test_ti_thread_flag(ti, TIF_FPUBOUND) &&
cpus_intersects(new_mask, mt_fpu_cpumask)) { cpus_intersects(new_mask, mt_fpu_cpumask)) {
cpus_and(effective_mask, new_mask, mt_fpu_cpumask); cpus_and(effective_mask, new_mask, mt_fpu_cpumask);
retval = set_cpus_allowed(p, effective_mask); retval = set_cpus_allowed_ptr(p, &effective_mask);
} else { } else {
clear_ti_thread_flag(ti, TIF_FPUBOUND); clear_ti_thread_flag(ti, TIF_FPUBOUND);
retval = set_cpus_allowed(p, new_mask); retval = set_cpus_allowed_ptr(p, &new_mask);
} }
out_unlock: out_unlock:
......
...@@ -569,27 +569,6 @@ void __init setup_arch(char **cmdline_p) ...@@ -569,27 +569,6 @@ void __init setup_arch(char **cmdline_p)
plat_smp_setup(); plat_smp_setup();
} }
static int __init fpu_disable(char *s)
{
int i;
for (i = 0; i < NR_CPUS; i++)
cpu_data[i].options &= ~MIPS_CPU_FPU;
return 1;
}
__setup("nofpu", fpu_disable);
static int __init dsp_disable(char *s)
{
cpu_data[0].ases &= ~MIPS_ASE_DSP;
return 1;
}
__setup("nodsp", dsp_disable);
unsigned long kernelsp[NR_CPUS]; unsigned long kernelsp[NR_CPUS];
unsigned long fw_arg0, fw_arg1, fw_arg2, fw_arg3; unsigned long fw_arg0, fw_arg1, fw_arg2, fw_arg3;
......
...@@ -867,7 +867,7 @@ static void mt_ase_fp_affinity(void) ...@@ -867,7 +867,7 @@ static void mt_ase_fp_affinity(void)
= current->cpus_allowed; = current->cpus_allowed;
cpus_and(tmask, current->cpus_allowed, cpus_and(tmask, current->cpus_allowed,
mt_fpu_cpumask); mt_fpu_cpumask);
set_cpus_allowed(current, tmask); set_cpus_allowed_ptr(current, &tmask);
set_thread_flag(TIF_FPUBOUND); set_thread_flag(TIF_FPUBOUND);
} }
} }
......
...@@ -4,6 +4,7 @@ ...@@ -4,6 +4,7 @@
obj-y += setup.o init.o cmdline.o env.o time.o reset.o irq.o \ obj-y += setup.o init.o cmdline.o env.o time.o reset.o irq.o \
pci.o bonito-irq.o mem.o machtype.o platform.o pci.o bonito-irq.o mem.o machtype.o platform.o
obj-$(CONFIG_GENERIC_GPIO) += gpio.o
# #
# Serial port support # Serial port support
......
/*
* STLS2F GPIO Support
*
* Copyright (c) 2008 Richard Liu, STMicroelectronics <richard.liu@st.com>
* Copyright (c) 2008-2010 Arnaud Patard <apatard@mandriva.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.
*/
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/module.h>
#include <linux/spinlock.h>
#include <linux/err.h>
#include <asm/types.h>
#include <loongson.h>
#include <linux/gpio.h>
#define STLS2F_N_GPIO 4
#define STLS2F_GPIO_IN_OFFSET 16
static DEFINE_SPINLOCK(gpio_lock);
int gpio_get_value(unsigned gpio)
{
u32 val;
u32 mask;
if (gpio >= STLS2F_N_GPIO)
return __gpio_get_value(gpio);
mask = 1 << (gpio + STLS2F_GPIO_IN_OFFSET);
spin_lock(&gpio_lock);
val = LOONGSON_GPIODATA;
spin_unlock(&gpio_lock);
return ((val & mask) != 0);
}
EXPORT_SYMBOL(gpio_get_value);
void gpio_set_value(unsigned gpio, int state)
{
u32 val;
u32 mask;
if (gpio >= STLS2F_N_GPIO) {
__gpio_set_value(gpio, state);
return ;
}
mask = 1 << gpio;
spin_lock(&gpio_lock);
val = LOONGSON_GPIODATA;
if (state)
val |= mask;
else
val &= (~mask);
LOONGSON_GPIODATA = val;
spin_unlock(&gpio_lock);
}
EXPORT_SYMBOL(gpio_set_value);
int gpio_cansleep(unsigned gpio)
{
if (gpio < STLS2F_N_GPIO)
return 0;
else
return __gpio_cansleep(gpio);
}
EXPORT_SYMBOL(gpio_cansleep);
static int ls2f_gpio_direction_input(struct gpio_chip *chip, unsigned gpio)
{
u32 temp;
u32 mask;
if (gpio >= STLS2F_N_GPIO)
return -EINVAL;
spin_lock(&gpio_lock);
mask = 1 << gpio;
temp = LOONGSON_GPIOIE;
temp |= mask;
LOONGSON_GPIOIE = temp;
spin_unlock(&gpio_lock);
return 0;
}
static int ls2f_gpio_direction_output(struct gpio_chip *chip,
unsigned gpio, int level)
{
u32 temp;
u32 mask;
if (gpio >= STLS2F_N_GPIO)
return -EINVAL;
gpio_set_value(gpio, level);
spin_lock(&gpio_lock);
mask = 1 << gpio;
temp = LOONGSON_GPIOIE;
temp &= (~mask);
LOONGSON_GPIOIE = temp;
spin_unlock(&gpio_lock);
return 0;
}
static int ls2f_gpio_get_value(struct gpio_chip *chip, unsigned gpio)
{
return gpio_get_value(gpio);
}
static void ls2f_gpio_set_value(struct gpio_chip *chip,
unsigned gpio, int value)
{
gpio_set_value(gpio, value);
}
static struct gpio_chip ls2f_chip = {
.label = "ls2f",
.direction_input = ls2f_gpio_direction_input,
.get = ls2f_gpio_get_value,
.direction_output = ls2f_gpio_direction_output,
.set = ls2f_gpio_set_value,
.base = 0,
.ngpio = STLS2F_N_GPIO,
};
static int __init ls2f_gpio_setup(void)
{
return gpiochip_add(&ls2f_chip);
}
arch_initcall(ls2f_gpio_setup);
...@@ -354,7 +354,8 @@ static int cop1Emulate(struct pt_regs *xcp, struct mips_fpu_struct *ctx) ...@@ -354,7 +354,8 @@ static int cop1Emulate(struct pt_regs *xcp, struct mips_fpu_struct *ctx)
if (MIPSInst_RD(ir) == FPCREG_CSR) { if (MIPSInst_RD(ir) == FPCREG_CSR) {
value = ctx->fcr31; value = ctx->fcr31;
value = (value & ~0x3) | mips_rm[value & 0x3]; value = (value & ~FPU_CSR_RM) |
mips_rm[modeindex(value)];
#ifdef CSRTRACE #ifdef CSRTRACE
printk("%p gpr[%d]<-csr=%08x\n", printk("%p gpr[%d]<-csr=%08x\n",
(void *) (xcp->cp0_epc), (void *) (xcp->cp0_epc),
...@@ -907,7 +908,7 @@ static int fpu_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx, ...@@ -907,7 +908,7 @@ static int fpu_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx,
ieee754sp fs; ieee754sp fs;
SPFROMREG(fs, MIPSInst_FS(ir)); SPFROMREG(fs, MIPSInst_FS(ir));
ieee754_csr.rm = ieee_rm[MIPSInst_FUNC(ir) & 0x3]; ieee754_csr.rm = ieee_rm[modeindex(MIPSInst_FUNC(ir))];
rv.w = ieee754sp_tint(fs); rv.w = ieee754sp_tint(fs);
ieee754_csr.rm = oldrm; ieee754_csr.rm = oldrm;
rfmt = w_fmt; rfmt = w_fmt;
...@@ -933,7 +934,7 @@ static int fpu_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx, ...@@ -933,7 +934,7 @@ static int fpu_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx,
ieee754sp fs; ieee754sp fs;
SPFROMREG(fs, MIPSInst_FS(ir)); SPFROMREG(fs, MIPSInst_FS(ir));
ieee754_csr.rm = ieee_rm[MIPSInst_FUNC(ir) & 0x3]; ieee754_csr.rm = ieee_rm[modeindex(MIPSInst_FUNC(ir))];
rv.l = ieee754sp_tlong(fs); rv.l = ieee754sp_tlong(fs);
ieee754_csr.rm = oldrm; ieee754_csr.rm = oldrm;
rfmt = l_fmt; rfmt = l_fmt;
...@@ -1081,7 +1082,7 @@ static int fpu_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx, ...@@ -1081,7 +1082,7 @@ static int fpu_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx,
ieee754dp fs; ieee754dp fs;
DPFROMREG(fs, MIPSInst_FS(ir)); DPFROMREG(fs, MIPSInst_FS(ir));
ieee754_csr.rm = ieee_rm[MIPSInst_FUNC(ir) & 0x3]; ieee754_csr.rm = ieee_rm[modeindex(MIPSInst_FUNC(ir))];
rv.w = ieee754dp_tint(fs); rv.w = ieee754dp_tint(fs);
ieee754_csr.rm = oldrm; ieee754_csr.rm = oldrm;
rfmt = w_fmt; rfmt = w_fmt;
...@@ -1107,7 +1108,7 @@ static int fpu_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx, ...@@ -1107,7 +1108,7 @@ static int fpu_emu(struct pt_regs *xcp, struct mips_fpu_struct *ctx,
ieee754dp fs; ieee754dp fs;
DPFROMREG(fs, MIPSInst_FS(ir)); DPFROMREG(fs, MIPSInst_FS(ir));
ieee754_csr.rm = ieee_rm[MIPSInst_FUNC(ir) & 0x3]; ieee754_csr.rm = ieee_rm[modeindex(MIPSInst_FUNC(ir))];
rv.l = ieee754dp_tlong(fs); rv.l = ieee754dp_tlong(fs);
ieee754_csr.rm = oldrm; ieee754_csr.rm = oldrm;
rfmt = l_fmt; rfmt = l_fmt;
......
...@@ -8,7 +8,6 @@ ...@@ -8,7 +8,6 @@
* This file is subject to the terms and conditions of the GNU General Public * This file is subject to the terms and conditions of the GNU General Public
* License. See the file "COPYING" in the main directory of this archive * License. See the file "COPYING" in the main directory of this archive
* for more details. * for more details.
*
*/ */
#include <linux/init.h> #include <linux/init.h>
#include <linux/oprofile.h> #include <linux/oprofile.h>
...@@ -17,24 +16,18 @@ ...@@ -17,24 +16,18 @@
#include <loongson.h> /* LOONGSON2_PERFCNT_IRQ */ #include <loongson.h> /* LOONGSON2_PERFCNT_IRQ */
#include "op_impl.h" #include "op_impl.h"
/*
* a patch should be sent to oprofile with the loongson-specific support.
* otherwise, the oprofile tool will not recognize this and complain about
* "cpu_type 'unset' is not valid".
*/
#define LOONGSON2_CPU_TYPE "mips/loongson2" #define LOONGSON2_CPU_TYPE "mips/loongson2"
#define LOONGSON2_COUNTER1_EVENT(event) ((event & 0x0f) << 5)
#define LOONGSON2_COUNTER2_EVENT(event) ((event & 0x0f) << 9)
#define LOONGSON2_PERFCNT_EXL (1UL << 0)
#define LOONGSON2_PERFCNT_KERNEL (1UL << 1)
#define LOONGSON2_PERFCNT_SUPERVISOR (1UL << 2)
#define LOONGSON2_PERFCNT_USER (1UL << 3)
#define LOONGSON2_PERFCNT_INT_EN (1UL << 4)
#define LOONGSON2_PERFCNT_OVERFLOW (1ULL << 31) #define LOONGSON2_PERFCNT_OVERFLOW (1ULL << 31)
/* Loongson2 performance counter register */ #define LOONGSON2_PERFCTRL_EXL (1UL << 0)
#define LOONGSON2_PERFCTRL_KERNEL (1UL << 1)
#define LOONGSON2_PERFCTRL_SUPERVISOR (1UL << 2)
#define LOONGSON2_PERFCTRL_USER (1UL << 3)
#define LOONGSON2_PERFCTRL_ENABLE (1UL << 4)
#define LOONGSON2_PERFCTRL_EVENT(idx, event) \
(((event) & 0x0f) << ((idx) ? 9 : 5))
#define read_c0_perfctrl() __read_64bit_c0_register($24, 0) #define read_c0_perfctrl() __read_64bit_c0_register($24, 0)
#define write_c0_perfctrl(val) __write_64bit_c0_register($24, 0, val) #define write_c0_perfctrl(val) __write_64bit_c0_register($24, 0, val)
#define read_c0_perfcnt() __read_64bit_c0_register($25, 0) #define read_c0_perfcnt() __read_64bit_c0_register($25, 0)
...@@ -49,7 +42,6 @@ static struct loongson2_register_config { ...@@ -49,7 +42,6 @@ static struct loongson2_register_config {
static char *oprofid = "LoongsonPerf"; static char *oprofid = "LoongsonPerf";
static irqreturn_t loongson2_perfcount_handler(int irq, void *dev_id); static irqreturn_t loongson2_perfcount_handler(int irq, void *dev_id);
/* Compute all of the registers in preparation for enabling profiling. */
static void loongson2_reg_setup(struct op_counter_config *cfg) static void loongson2_reg_setup(struct op_counter_config *cfg)
{ {
...@@ -57,41 +49,38 @@ static void loongson2_reg_setup(struct op_counter_config *cfg) ...@@ -57,41 +49,38 @@ static void loongson2_reg_setup(struct op_counter_config *cfg)
reg.reset_counter1 = 0; reg.reset_counter1 = 0;
reg.reset_counter2 = 0; reg.reset_counter2 = 0;
/* Compute the performance counter ctrl word. */
/* For now count kernel and user mode */ /*
* Compute the performance counter ctrl word.
* For now, count kernel and user mode.
*/
if (cfg[0].enabled) { if (cfg[0].enabled) {
ctrl |= LOONGSON2_COUNTER1_EVENT(cfg[0].event); ctrl |= LOONGSON2_PERFCTRL_EVENT(0, cfg[0].event);
reg.reset_counter1 = 0x80000000ULL - cfg[0].count; reg.reset_counter1 = 0x80000000ULL - cfg[0].count;
} }
if (cfg[1].enabled) { if (cfg[1].enabled) {
ctrl |= LOONGSON2_COUNTER2_EVENT(cfg[1].event); ctrl |= LOONGSON2_PERFCTRL_EVENT(1, cfg[1].event);
reg.reset_counter2 = (0x80000000ULL - cfg[1].count); reg.reset_counter2 = 0x80000000ULL - cfg[1].count;
} }
if (cfg[0].enabled || cfg[1].enabled) { if (cfg[0].enabled || cfg[1].enabled) {
ctrl |= LOONGSON2_PERFCNT_EXL | LOONGSON2_PERFCNT_INT_EN; ctrl |= LOONGSON2_PERFCTRL_EXL | LOONGSON2_PERFCTRL_ENABLE;
if (cfg[0].kernel || cfg[1].kernel) if (cfg[0].kernel || cfg[1].kernel)
ctrl |= LOONGSON2_PERFCNT_KERNEL; ctrl |= LOONGSON2_PERFCTRL_KERNEL;
if (cfg[0].user || cfg[1].user) if (cfg[0].user || cfg[1].user)
ctrl |= LOONGSON2_PERFCNT_USER; ctrl |= LOONGSON2_PERFCTRL_USER;
} }
reg.ctrl = ctrl; reg.ctrl = ctrl;
reg.cnt1_enabled = cfg[0].enabled; reg.cnt1_enabled = cfg[0].enabled;
reg.cnt2_enabled = cfg[1].enabled; reg.cnt2_enabled = cfg[1].enabled;
} }
/* Program all of the registers in preparation for enabling profiling. */
static void loongson2_cpu_setup(void *args) static void loongson2_cpu_setup(void *args)
{ {
uint64_t perfcount; write_c0_perfcnt((reg.reset_counter2 << 32) | reg.reset_counter1);
perfcount = (reg.reset_counter2 << 32) | reg.reset_counter1;
write_c0_perfcnt(perfcount);
} }
static void loongson2_cpu_start(void *args) static void loongson2_cpu_start(void *args)
...@@ -114,15 +103,8 @@ static irqreturn_t loongson2_perfcount_handler(int irq, void *dev_id) ...@@ -114,15 +103,8 @@ static irqreturn_t loongson2_perfcount_handler(int irq, void *dev_id)
struct pt_regs *regs = get_irq_regs(); struct pt_regs *regs = get_irq_regs();
int enabled; int enabled;
/*
* LOONGSON2 defines two 32-bit performance counters.
* To avoid a race updating the registers we need to stop the counters
* while we're messing with
* them ...
*/
/* Check whether the irq belongs to me */ /* Check whether the irq belongs to me */
enabled = read_c0_perfctrl() & LOONGSON2_PERFCNT_INT_EN; enabled = read_c0_perfctrl() & LOONGSON2_PERFCTRL_ENABLE;
if (!enabled) if (!enabled)
return IRQ_NONE; return IRQ_NONE;
enabled = reg.cnt1_enabled | reg.cnt2_enabled; enabled = reg.cnt1_enabled | reg.cnt2_enabled;
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
/*
* Definitions for memory preallocations
*
* Copyright (C) 2005-2009 Scientific-Atlanta, Inc.
*
* 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 program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* 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., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
#ifndef _ARCH_MIPS_POWERTV_ASIC_PREALLOC_H
#define _ARCH_MIPS_POWERTV_ASIC_PREALLOC_H
#define KIBIBYTE(n) ((n) * 1024) /* Number of kibibytes */
#define MEBIBYTE(n) ((n) * KIBIBYTE(1024)) /* Number of mebibytes */
/* "struct resource" array element definition */
#define PREALLOC(NAME, START, END, FLAGS) { \
.name = (NAME), \
.start = (START), \
.end = (END), \
.flags = (FLAGS) \
},
/* Individual resources in the preallocated resource arrays are defined using
* macros. These macros are conditionally defined based on their
* corresponding kernel configuration flag:
* - CONFIG_PREALLOC_NORMAL: preallocate resources for a normal settop box
* - CONFIG_PREALLOC_TFTP: preallocate the TFTP download resource
* - CONFIG_PREALLOC_DOCSIS: preallocate the DOCSIS resource
* - CONFIG_PREALLOC_PMEM: reserve space for persistent memory
*/
#ifdef CONFIG_PREALLOC_NORMAL
#define PREALLOC_NORMAL(name, start, end, flags) \
PREALLOC(name, start, end, flags)
#else
#define PREALLOC_NORMAL(name, start, end, flags)
#endif
#ifdef CONFIG_PREALLOC_TFTP
#define PREALLOC_TFTP(name, start, end, flags) \
PREALLOC(name, start, end, flags)
#else
#define PREALLOC_TFTP(name, start, end, flags)
#endif
#ifdef CONFIG_PREALLOC_DOCSIS
#define PREALLOC_DOCSIS(name, start, end, flags) \
PREALLOC(name, start, end, flags)
#else
#define PREALLOC_DOCSIS(name, start, end, flags)
#endif
#ifdef CONFIG_PREALLOC_PMEM
#define PREALLOC_PMEM(name, start, end, flags) \
PREALLOC(name, start, end, flags)
#else
#define PREALLOC_PMEM(name, start, end, flags)
#endif
#endif
...@@ -238,31 +238,32 @@ static int cmos_read_alarm(struct device *dev, struct rtc_wkalrm *t) ...@@ -238,31 +238,32 @@ static int cmos_read_alarm(struct device *dev, struct rtc_wkalrm *t)
rtc_control = CMOS_READ(RTC_CONTROL); rtc_control = CMOS_READ(RTC_CONTROL);
spin_unlock_irq(&rtc_lock); spin_unlock_irq(&rtc_lock);
/* REVISIT this assumes PC style usage: always BCD */ if (!(rtc_control & RTC_DM_BINARY) || RTC_ALWAYS_BCD) {
if (((unsigned)t->time.tm_sec) < 0x60)
if (((unsigned)t->time.tm_sec) < 0x60) t->time.tm_sec = bcd2bin(t->time.tm_sec);
t->time.tm_sec = bcd2bin(t->time.tm_sec);
else
t->time.tm_sec = -1;
if (((unsigned)t->time.tm_min) < 0x60)
t->time.tm_min = bcd2bin(t->time.tm_min);
else
t->time.tm_min = -1;
if (((unsigned)t->time.tm_hour) < 0x24)
t->time.tm_hour = bcd2bin(t->time.tm_hour);
else
t->time.tm_hour = -1;
if (cmos->day_alrm) {
if (((unsigned)t->time.tm_mday) <= 0x31)
t->time.tm_mday = bcd2bin(t->time.tm_mday);
else else
t->time.tm_mday = -1; t->time.tm_sec = -1;
if (cmos->mon_alrm) { if (((unsigned)t->time.tm_min) < 0x60)
if (((unsigned)t->time.tm_mon) <= 0x12) t->time.tm_min = bcd2bin(t->time.tm_min);
t->time.tm_mon = bcd2bin(t->time.tm_mon) - 1; else
t->time.tm_min = -1;
if (((unsigned)t->time.tm_hour) < 0x24)
t->time.tm_hour = bcd2bin(t->time.tm_hour);
else
t->time.tm_hour = -1;
if (cmos->day_alrm) {
if (((unsigned)t->time.tm_mday) <= 0x31)
t->time.tm_mday = bcd2bin(t->time.tm_mday);
else else
t->time.tm_mon = -1; t->time.tm_mday = -1;
if (cmos->mon_alrm) {
if (((unsigned)t->time.tm_mon) <= 0x12)
t->time.tm_mon = bcd2bin(t->time.tm_mon)-1;
else
t->time.tm_mon = -1;
}
} }
} }
t->time.tm_year = -1; t->time.tm_year = -1;
...@@ -322,29 +323,26 @@ static void cmos_irq_disable(struct cmos_rtc *cmos, unsigned char mask) ...@@ -322,29 +323,26 @@ static void cmos_irq_disable(struct cmos_rtc *cmos, unsigned char mask)
static int cmos_set_alarm(struct device *dev, struct rtc_wkalrm *t) static int cmos_set_alarm(struct device *dev, struct rtc_wkalrm *t)
{ {
struct cmos_rtc *cmos = dev_get_drvdata(dev); struct cmos_rtc *cmos = dev_get_drvdata(dev);
unsigned char mon, mday, hrs, min, sec; unsigned char mon, mday, hrs, min, sec, rtc_control;
if (!is_valid_irq(cmos->irq)) if (!is_valid_irq(cmos->irq))
return -EIO; return -EIO;
/* REVISIT this assumes PC style usage: always BCD */
/* Writing 0xff means "don't care" or "match all". */
mon = t->time.tm_mon + 1; mon = t->time.tm_mon + 1;
mon = (mon <= 12) ? bin2bcd(mon) : 0xff;
mday = t->time.tm_mday; mday = t->time.tm_mday;
mday = (mday >= 1 && mday <= 31) ? bin2bcd(mday) : 0xff;
hrs = t->time.tm_hour; hrs = t->time.tm_hour;
hrs = (hrs < 24) ? bin2bcd(hrs) : 0xff;
min = t->time.tm_min; min = t->time.tm_min;
min = (min < 60) ? bin2bcd(min) : 0xff;
sec = t->time.tm_sec; sec = t->time.tm_sec;
sec = (sec < 60) ? bin2bcd(sec) : 0xff;
rtc_control = CMOS_READ(RTC_CONTROL);
if (!(rtc_control & RTC_DM_BINARY) || RTC_ALWAYS_BCD) {
/* Writing 0xff means "don't care" or "match all". */
mon = (mon <= 12) ? bin2bcd(mon) : 0xff;
mday = (mday >= 1 && mday <= 31) ? bin2bcd(mday) : 0xff;
hrs = (hrs < 24) ? bin2bcd(hrs) : 0xff;
min = (min < 60) ? bin2bcd(min) : 0xff;
sec = (sec < 60) ? bin2bcd(sec) : 0xff;
}
spin_lock_irq(&rtc_lock); spin_lock_irq(&rtc_lock);
...@@ -478,7 +476,7 @@ static int cmos_procfs(struct device *dev, struct seq_file *seq) ...@@ -478,7 +476,7 @@ static int cmos_procfs(struct device *dev, struct seq_file *seq)
"update_IRQ\t: %s\n" "update_IRQ\t: %s\n"
"HPET_emulated\t: %s\n" "HPET_emulated\t: %s\n"
// "square_wave\t: %s\n" // "square_wave\t: %s\n"
// "BCD\t\t: %s\n" "BCD\t\t: %s\n"
"DST_enable\t: %s\n" "DST_enable\t: %s\n"
"periodic_freq\t: %d\n" "periodic_freq\t: %d\n"
"batt_status\t: %s\n", "batt_status\t: %s\n",
...@@ -486,7 +484,7 @@ static int cmos_procfs(struct device *dev, struct seq_file *seq) ...@@ -486,7 +484,7 @@ static int cmos_procfs(struct device *dev, struct seq_file *seq)
(rtc_control & RTC_UIE) ? "yes" : "no", (rtc_control & RTC_UIE) ? "yes" : "no",
is_hpet_enabled() ? "yes" : "no", is_hpet_enabled() ? "yes" : "no",
// (rtc_control & RTC_SQWE) ? "yes" : "no", // (rtc_control & RTC_SQWE) ? "yes" : "no",
// (rtc_control & RTC_DM_BINARY) ? "no" : "yes", (rtc_control & RTC_DM_BINARY) ? "no" : "yes",
(rtc_control & RTC_DST_EN) ? "yes" : "no", (rtc_control & RTC_DST_EN) ? "yes" : "no",
cmos->rtc->irq_freq, cmos->rtc->irq_freq,
(valid & RTC_VRT) ? "okay" : "dead"); (valid & RTC_VRT) ? "okay" : "dead");
...@@ -751,12 +749,11 @@ cmos_do_probe(struct device *dev, struct resource *ports, int rtc_irq) ...@@ -751,12 +749,11 @@ cmos_do_probe(struct device *dev, struct resource *ports, int rtc_irq)
spin_unlock_irq(&rtc_lock); spin_unlock_irq(&rtc_lock);
/* FIXME teach the alarm code how to handle binary mode; /* FIXME:
* <asm-generic/rtc.h> doesn't know 12-hour mode either. * <asm-generic/rtc.h> doesn't know 12-hour mode either.
*/ */
if (is_valid_irq(rtc_irq) && if (is_valid_irq(rtc_irq) && !(rtc_control & RTC_24H)) {
(!(rtc_control & RTC_24H) || (rtc_control & (RTC_DM_BINARY)))) { dev_warn(dev, "only 24-hr supported\n");
dev_dbg(dev, "only 24-hr BCD mode supported\n");
retval = -ENXIO; retval = -ENXIO;
goto cleanup1; goto cleanup1;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment