Fixed MTP to work with TWRP

This commit is contained in:
awab228 2018-06-19 23:16:04 +02:00
commit f6dfaef42e
50820 changed files with 20846062 additions and 0 deletions

View file

@ -0,0 +1,314 @@
# Copyright 2008 Openmoko, Inc.
# Simtec Electronics, Ben Dooks <ben@simtec.co.uk>
#
# Licensed under GPLv2
if ARCH_S3C64XX
# Configuration options for the S3C6410 CPU
config CPU_S3C6400
bool
help
Enable S3C6400 CPU support
config CPU_S3C6410
bool
help
Enable S3C6410 CPU support
config S3C64XX_PL080
def_bool DMADEVICES
select ARM_AMBA
select AMBA_PL08X
config S3C64XX_SETUP_SDHCI
bool
select S3C64XX_SETUP_SDHCI_GPIO
help
Internal configuration for default SDHCI setup for S3C6400 and
S3C6410 SoCs.
config S3C64XX_DEV_ONENAND1
bool
help
Compile in platform device definition for OneNAND1 controller
# platform specific device setup
config S3C64XX_SETUP_I2C0
bool
default y
help
Common setup code for i2c bus 0.
Note, currently since i2c0 is always compiled, this setup helper
is always compiled with it.
config S3C64XX_SETUP_I2C1
bool
help
Common setup code for i2c bus 1.
config S3C64XX_SETUP_IDE
bool
help
Common setup code for S3C64XX IDE.
config S3C64XX_SETUP_FB_24BPP
bool
help
Common setup code for S3C64XX with an 24bpp RGB display helper.
config S3C64XX_SETUP_KEYPAD
bool
help
Common setup code for S3C64XX KEYPAD GPIO configurations
config S3C64XX_SETUP_SDHCI_GPIO
bool
help
Common setup code for S3C64XX SDHCI GPIO configurations
config S3C64XX_SETUP_SPI
bool
help
Common setup code for SPI GPIO configurations
config S3C64XX_SETUP_USB_PHY
bool
help
Common setup code for USB PHY controller
# S36400 Macchine support
config MACH_SMDK6400
bool "SMDK6400"
select CPU_S3C6400
select S3C64XX_SETUP_SDHCI
select S3C_DEV_HSMMC1
help
Machine support for the Samsung SMDK6400
# S3C6410 machine support
config MACH_ANW6410
bool "A&W6410"
select CPU_S3C6410
select S3C64XX_SETUP_FB_24BPP
select S3C_DEV_FB
help
Machine support for the A&W6410
config MACH_MINI6410
bool "MINI6410"
select CPU_S3C6410
select S3C64XX_SETUP_FB_24BPP
select S3C64XX_SETUP_SDHCI
select S3C_DEV_FB
select S3C_DEV_HSMMC
select S3C_DEV_HSMMC1
select S3C_DEV_NAND
select S3C_DEV_USB_HOST
select SAMSUNG_DEV_ADC
select SAMSUNG_DEV_TS
help
Machine support for the FriendlyARM MINI6410
config MACH_REAL6410
bool "REAL6410"
select CPU_S3C6410
select S3C64XX_SETUP_FB_24BPP
select S3C64XX_SETUP_SDHCI
select S3C_DEV_FB
select S3C_DEV_HSMMC
select S3C_DEV_HSMMC1
select S3C_DEV_NAND
select S3C_DEV_USB_HOST
select SAMSUNG_DEV_ADC
select SAMSUNG_DEV_TS
help
Machine support for the CoreWind REAL6410
config MACH_SMDK6410
bool "SMDK6410"
select CPU_S3C6410
select HAVE_S3C2410_WATCHDOG if WATCHDOG
select S3C64XX_SETUP_FB_24BPP
select S3C64XX_SETUP_I2C1
select S3C64XX_SETUP_IDE
select S3C64XX_SETUP_KEYPAD
select S3C64XX_SETUP_SDHCI
select S3C64XX_SETUP_USB_PHY
select S3C_DEV_FB
select S3C_DEV_HSMMC
select S3C_DEV_HSMMC1
select S3C_DEV_I2C1
select S3C_DEV_RTC
select S3C_DEV_USB_HOST
select S3C_DEV_USB_HSOTG
select S3C_DEV_WDT
select SAMSUNG_DEV_ADC
select SAMSUNG_DEV_BACKLIGHT
select SAMSUNG_DEV_IDE
select SAMSUNG_DEV_KEYPAD
select SAMSUNG_DEV_PWM
select SAMSUNG_DEV_TS
help
Machine support for the Samsung SMDK6410
# At least some of the SMDK6410s were shipped with the card detect
# for the MMC/SD slots connected to the same input. This means that
# either the boards need to be altered to have channel0 to an alternate
# configuration or that only one slot can be used.
choice
prompt "SMDK6410 MMC/SD slot setup"
depends on MACH_SMDK6410
config SMDK6410_SD_CH0
bool "Use channel 0 only"
depends on MACH_SMDK6410
help
Select CON7 (channel 0) as the MMC/SD slot, as
at least some SMDK6410 boards come with the
resistors fitted so that the card detects for
channels 0 and 1 are the same.
config SMDK6410_SD_CH1
bool "Use channel 1 only"
depends on MACH_SMDK6410
help
Select CON6 (channel 1) as the MMC/SD slot, as
at least some SMDK6410 boards come with the
resistors fitted so that the card detects for
channels 0 and 1 are the same.
endchoice
config SMDK6410_WM1190_EV1
bool "Support Wolfson Microelectronics 1190-EV1 PMIC card"
depends on MACH_SMDK6410
select MFD_WM8350_I2C
select REGULATOR
select REGULATOR_WM8350
help
The Wolfson Microelectronics 1190-EV1 is a WM835x based PMIC
and audio daughtercard for the Samsung SMDK6410 reference
platform. Enabling this option will build support for this
module into the kernel. The presence of the module will be
detected at runtime so the resulting kernel can be used
with or without the 1190-EV1 fitted.
config SMDK6410_WM1192_EV1
bool "Support Wolfson Microelectronics 1192-EV1 PMIC card"
depends on MACH_SMDK6410
select MFD_WM831X
select MFD_WM831X_I2C
select REGULATOR
select REGULATOR_WM831X
help
The Wolfson Microelectronics 1192-EV1 is a WM831x based PMIC
daughtercard for the Samsung SMDK6410 reference platform.
Enabling this option will build support for this module into
the kernel. The presence of the daughtercard will be
detected at runtime so the resulting kernel can be used
with or without the 1192-EV1 fitted.
config MACH_NCP
bool "NCP"
select CPU_S3C6410
select S3C64XX_SETUP_I2C1
select S3C_DEV_HSMMC1
select S3C_DEV_I2C1
help
Machine support for the Samsung NCP
config MACH_HMT
bool "Airgoo HMT"
select CPU_S3C6410
select S3C64XX_SETUP_FB_24BPP
select S3C_DEV_FB
select S3C_DEV_NAND
select S3C_DEV_USB_HOST
select SAMSUNG_DEV_PWM
help
Machine support for the Airgoo HMT
config MACH_SMARTQ
bool
select CPU_S3C6410
select S3C64XX_SETUP_FB_24BPP
select S3C64XX_SETUP_SDHCI
select S3C64XX_SETUP_USB_PHY
select S3C_DEV_FB
select S3C_DEV_HSMMC
select S3C_DEV_HSMMC1
select S3C_DEV_HSMMC2
select S3C_DEV_HWMON
select S3C_DEV_RTC
select S3C_DEV_USB_HOST
select S3C_DEV_USB_HSOTG
select SAMSUNG_DEV_ADC
select SAMSUNG_DEV_PWM
select SAMSUNG_DEV_TS
help
Shared machine support for SmartQ 5/7
config MACH_SMARTQ5
bool "SmartQ 5"
select MACH_SMARTQ
help
Machine support for the SmartQ 5
config MACH_SMARTQ7
bool "SmartQ 7"
select MACH_SMARTQ
help
Machine support for the SmartQ 7
config MACH_WLF_CRAGG_6410
bool "Wolfson Cragganmore 6410"
select CPU_S3C6410
select I2C
select LEDS_GPIO_REGISTER
select S3C64XX_DEV_SPI0
select S3C64XX_SETUP_FB_24BPP
select S3C64XX_SETUP_I2C1
select S3C64XX_SETUP_IDE
select S3C64XX_SETUP_KEYPAD
select S3C64XX_SETUP_SDHCI
select S3C64XX_SETUP_SPI
select S3C64XX_SETUP_USB_PHY
select S3C_DEV_FB
select S3C_DEV_HSMMC
select S3C_DEV_HSMMC1
select S3C_DEV_HSMMC2
select S3C_DEV_I2C1
select S3C_DEV_RTC
select S3C_DEV_USB_HOST
select S3C_DEV_USB_HSOTG
select S3C_DEV_WDT
select SAMSUNG_DEV_ADC
select SAMSUNG_DEV_KEYPAD
select SAMSUNG_DEV_PWM
help
Machine support for the Wolfson Cragganmore S3C6410 variant.
config MACH_S3C64XX_DT
bool "Samsung S3C6400/S3C6410 machine using Device Tree"
select CLKSRC_OF
select CPU_S3C6400
select CPU_S3C6410
select PINCTRL
select PINCTRL_S3C64XX
select USE_OF
help
Machine support for Samsung S3C6400/S3C6410 machines with Device Tree
enabled.
Select this if a fdt blob is available for your S3C64XX SoC based
board.
Note: This is under development and not all peripherals can be
supported with this machine file.
endif

View file

@ -0,0 +1,55 @@
# arch/arm/mach-s3c64xx/Makefile
#
# Copyright 2008 Openmoko, Inc.
# Copyright 2008 Simtec Electronics
#
# Licensed under GPLv2
# Core
obj-y += common.o
# Core support
obj-$(CONFIG_CPU_S3C6400) += s3c6400.o
obj-$(CONFIG_CPU_S3C6410) += s3c6410.o
# PM
obj-$(CONFIG_PM) += pm.o irq-pm.o sleep.o
obj-$(CONFIG_CPU_IDLE) += cpuidle.o
# DMA support
obj-$(CONFIG_S3C64XX_PL080) += pl080.o
# Device support
obj-y += dev-uart.o
obj-y += dev-audio.o
# Device setup
obj-$(CONFIG_S3C64XX_SETUP_FB_24BPP) += setup-fb-24bpp.o
obj-$(CONFIG_S3C64XX_SETUP_I2C0) += setup-i2c0.o
obj-$(CONFIG_S3C64XX_SETUP_I2C1) += setup-i2c1.o
obj-$(CONFIG_S3C64XX_SETUP_IDE) += setup-ide.o
obj-$(CONFIG_S3C64XX_SETUP_KEYPAD) += setup-keypad.o
obj-$(CONFIG_S3C64XX_SETUP_SDHCI_GPIO) += setup-sdhci-gpio.o
obj-$(CONFIG_S3C64XX_SETUP_SPI) += setup-spi.o
obj-$(CONFIG_S3C64XX_SETUP_USB_PHY) += setup-usb-phy.o
# Machine support
obj-$(CONFIG_MACH_ANW6410) += mach-anw6410.o
obj-$(CONFIG_MACH_HMT) += mach-hmt.o
obj-$(CONFIG_MACH_MINI6410) += mach-mini6410.o
obj-$(CONFIG_MACH_NCP) += mach-ncp.o
obj-$(CONFIG_MACH_REAL6410) += mach-real6410.o
obj-$(CONFIG_MACH_SMARTQ) += mach-smartq.o
obj-$(CONFIG_MACH_SMARTQ5) += mach-smartq5.o
obj-$(CONFIG_MACH_SMARTQ7) += mach-smartq7.o
obj-$(CONFIG_MACH_SMDK6400) += mach-smdk6400.o
obj-$(CONFIG_MACH_SMDK6410) += mach-smdk6410.o
obj-$(CONFIG_MACH_WLF_CRAGG_6410) += mach-crag6410.o mach-crag6410-module.o
obj-$(CONFIG_MACH_S3C64XX_DT) += mach-s3c64xx-dt.o

View file

@ -0,0 +1,2 @@
zreladdr-y += 0x50008000
params_phys-y := 0x50000100

View file

@ -0,0 +1,442 @@
/*
* Copyright (c) 2011 Samsung Electronics Co., Ltd.
* http://www.samsung.com
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* Common Codes for S3C64XX machines
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
/*
* NOTE: Code in this file is not used when booting with Device Tree support.
*/
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/module.h>
#include <linux/clk-provider.h>
#include <linux/interrupt.h>
#include <linux/ioport.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/platform_device.h>
#include <linux/reboot.h>
#include <linux/io.h>
#include <linux/dma-mapping.h>
#include <linux/irq.h>
#include <linux/gpio.h>
#include <linux/irqchip/arm-vic.h>
#include <clocksource/samsung_pwm.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <asm/system_misc.h>
#include <mach/map.h>
#include <mach/hardware.h>
#include <mach/regs-gpio.h>
#include <mach/gpio-samsung.h>
#include <plat/cpu.h>
#include <plat/devs.h>
#include <plat/pm.h>
#include <plat/gpio-cfg.h>
#include <plat/irq-uart.h>
#include <plat/pwm-core.h>
#include <plat/regs-irqtype.h>
#include <plat/watchdog-reset.h>
#include "common.h"
/* External clock frequency */
static unsigned long xtal_f = 12000000, xusbxti_f = 48000000;
void __init s3c64xx_set_xtal_freq(unsigned long freq)
{
xtal_f = freq;
}
void __init s3c64xx_set_xusbxti_freq(unsigned long freq)
{
xusbxti_f = freq;
}
/* uart registration process */
static void __init s3c64xx_init_uarts(struct s3c2410_uartcfg *cfg, int no)
{
s3c24xx_init_uartdevs("s3c6400-uart", s3c64xx_uart_resources, cfg, no);
}
/* table of supported CPUs */
static const char name_s3c6400[] = "S3C6400";
static const char name_s3c6410[] = "S3C6410";
static struct cpu_table cpu_ids[] __initdata = {
{
.idcode = S3C6400_CPU_ID,
.idmask = S3C64XX_CPU_MASK,
.map_io = s3c6400_map_io,
.init_uarts = s3c64xx_init_uarts,
.init = s3c6400_init,
.name = name_s3c6400,
}, {
.idcode = S3C6410_CPU_ID,
.idmask = S3C64XX_CPU_MASK,
.map_io = s3c6410_map_io,
.init_uarts = s3c64xx_init_uarts,
.init = s3c6410_init,
.name = name_s3c6410,
},
};
/* minimal IO mapping */
/* see notes on uart map in arch/arm/mach-s3c64xx/include/mach/debug-macro.S */
#define UART_OFFS (S3C_PA_UART & 0xfffff)
static struct map_desc s3c_iodesc[] __initdata = {
{
.virtual = (unsigned long)S3C_VA_SYS,
.pfn = __phys_to_pfn(S3C64XX_PA_SYSCON),
.length = SZ_4K,
.type = MT_DEVICE,
}, {
.virtual = (unsigned long)S3C_VA_MEM,
.pfn = __phys_to_pfn(S3C64XX_PA_SROM),
.length = SZ_4K,
.type = MT_DEVICE,
}, {
.virtual = (unsigned long)(S3C_VA_UART + UART_OFFS),
.pfn = __phys_to_pfn(S3C_PA_UART),
.length = SZ_4K,
.type = MT_DEVICE,
}, {
.virtual = (unsigned long)VA_VIC0,
.pfn = __phys_to_pfn(S3C64XX_PA_VIC0),
.length = SZ_16K,
.type = MT_DEVICE,
}, {
.virtual = (unsigned long)VA_VIC1,
.pfn = __phys_to_pfn(S3C64XX_PA_VIC1),
.length = SZ_16K,
.type = MT_DEVICE,
}, {
.virtual = (unsigned long)S3C_VA_TIMER,
.pfn = __phys_to_pfn(S3C_PA_TIMER),
.length = SZ_16K,
.type = MT_DEVICE,
}, {
.virtual = (unsigned long)S3C64XX_VA_GPIO,
.pfn = __phys_to_pfn(S3C64XX_PA_GPIO),
.length = SZ_4K,
.type = MT_DEVICE,
}, {
.virtual = (unsigned long)S3C64XX_VA_MODEM,
.pfn = __phys_to_pfn(S3C64XX_PA_MODEM),
.length = SZ_4K,
.type = MT_DEVICE,
}, {
.virtual = (unsigned long)S3C_VA_WATCHDOG,
.pfn = __phys_to_pfn(S3C64XX_PA_WATCHDOG),
.length = SZ_4K,
.type = MT_DEVICE,
}, {
.virtual = (unsigned long)S3C_VA_USB_HSPHY,
.pfn = __phys_to_pfn(S3C64XX_PA_USB_HSPHY),
.length = SZ_1K,
.type = MT_DEVICE,
},
};
static struct bus_type s3c64xx_subsys = {
.name = "s3c64xx-core",
.dev_name = "s3c64xx-core",
};
static struct device s3c64xx_dev = {
.bus = &s3c64xx_subsys,
};
static struct samsung_pwm_variant s3c64xx_pwm_variant = {
.bits = 32,
.div_base = 0,
.has_tint_cstat = true,
.tclk_mask = (1 << 7) | (1 << 6) | (1 << 5),
};
void __init samsung_set_timer_source(unsigned int event, unsigned int source)
{
s3c64xx_pwm_variant.output_mask = BIT(SAMSUNG_PWM_NUM) - 1;
s3c64xx_pwm_variant.output_mask &= ~(BIT(event) | BIT(source));
}
void __init samsung_timer_init(void)
{
unsigned int timer_irqs[SAMSUNG_PWM_NUM] = {
IRQ_TIMER0_VIC, IRQ_TIMER1_VIC, IRQ_TIMER2_VIC,
IRQ_TIMER3_VIC, IRQ_TIMER4_VIC,
};
samsung_pwm_clocksource_init(S3C_VA_TIMER,
timer_irqs, &s3c64xx_pwm_variant);
}
/* read cpu identification code */
void __init s3c64xx_init_io(struct map_desc *mach_desc, int size)
{
/* initialise the io descriptors we need for initialisation */
iotable_init(s3c_iodesc, ARRAY_SIZE(s3c_iodesc));
iotable_init(mach_desc, size);
/* detect cpu id */
s3c64xx_init_cpu();
s3c_init_cpu(samsung_cpu_id, cpu_ids, ARRAY_SIZE(cpu_ids));
samsung_pwm_set_platdata(&s3c64xx_pwm_variant);
}
static __init int s3c64xx_dev_init(void)
{
/* Not applicable when using DT. */
if (of_have_populated_dt())
return 0;
subsys_system_register(&s3c64xx_subsys, NULL);
return device_register(&s3c64xx_dev);
}
core_initcall(s3c64xx_dev_init);
/*
* setup the sources the vic should advertise resume
* for, even though it is not doing the wake
* (set_irq_wake needs to be valid)
*/
#define IRQ_VIC0_RESUME (1 << (IRQ_RTC_TIC - IRQ_VIC0_BASE))
#define IRQ_VIC1_RESUME (1 << (IRQ_RTC_ALARM - IRQ_VIC1_BASE) | \
1 << (IRQ_PENDN - IRQ_VIC1_BASE) | \
1 << (IRQ_HSMMC0 - IRQ_VIC1_BASE) | \
1 << (IRQ_HSMMC1 - IRQ_VIC1_BASE) | \
1 << (IRQ_HSMMC2 - IRQ_VIC1_BASE))
void __init s3c64xx_init_irq(u32 vic0_valid, u32 vic1_valid)
{
/*
* FIXME: there is no better place to put this at the moment
* (s3c64xx_clk_init needs ioremap and must happen before init_time
* samsung_wdt_reset_init needs clocks)
*/
s3c64xx_clk_init(NULL, xtal_f, xusbxti_f, soc_is_s3c6400(), S3C_VA_SYS);
samsung_wdt_reset_init(S3C_VA_WATCHDOG);
printk(KERN_DEBUG "%s: initialising interrupts\n", __func__);
/* initialise the pair of VICs */
vic_init(VA_VIC0, IRQ_VIC0_BASE, vic0_valid, IRQ_VIC0_RESUME);
vic_init(VA_VIC1, IRQ_VIC1_BASE, vic1_valid, IRQ_VIC1_RESUME);
}
#define eint_offset(irq) ((irq) - IRQ_EINT(0))
#define eint_irq_to_bit(irq) ((u32)(1 << eint_offset(irq)))
static inline void s3c_irq_eint_mask(struct irq_data *data)
{
u32 mask;
mask = __raw_readl(S3C64XX_EINT0MASK);
mask |= (u32)data->chip_data;
__raw_writel(mask, S3C64XX_EINT0MASK);
}
static void s3c_irq_eint_unmask(struct irq_data *data)
{
u32 mask;
mask = __raw_readl(S3C64XX_EINT0MASK);
mask &= ~((u32)data->chip_data);
__raw_writel(mask, S3C64XX_EINT0MASK);
}
static inline void s3c_irq_eint_ack(struct irq_data *data)
{
__raw_writel((u32)data->chip_data, S3C64XX_EINT0PEND);
}
static void s3c_irq_eint_maskack(struct irq_data *data)
{
/* compiler should in-line these */
s3c_irq_eint_mask(data);
s3c_irq_eint_ack(data);
}
static int s3c_irq_eint_set_type(struct irq_data *data, unsigned int type)
{
int offs = eint_offset(data->irq);
int pin, pin_val;
int shift;
u32 ctrl, mask;
u32 newvalue = 0;
void __iomem *reg;
if (offs > 27)
return -EINVAL;
if (offs <= 15)
reg = S3C64XX_EINT0CON0;
else
reg = S3C64XX_EINT0CON1;
switch (type) {
case IRQ_TYPE_NONE:
printk(KERN_WARNING "No edge setting!\n");
break;
case IRQ_TYPE_EDGE_RISING:
newvalue = S3C2410_EXTINT_RISEEDGE;
break;
case IRQ_TYPE_EDGE_FALLING:
newvalue = S3C2410_EXTINT_FALLEDGE;
break;
case IRQ_TYPE_EDGE_BOTH:
newvalue = S3C2410_EXTINT_BOTHEDGE;
break;
case IRQ_TYPE_LEVEL_LOW:
newvalue = S3C2410_EXTINT_LOWLEV;
break;
case IRQ_TYPE_LEVEL_HIGH:
newvalue = S3C2410_EXTINT_HILEV;
break;
default:
printk(KERN_ERR "No such irq type %d", type);
return -1;
}
if (offs <= 15)
shift = (offs / 2) * 4;
else
shift = ((offs - 16) / 2) * 4;
mask = 0x7 << shift;
ctrl = __raw_readl(reg);
ctrl &= ~mask;
ctrl |= newvalue << shift;
__raw_writel(ctrl, reg);
/* set the GPIO pin appropriately */
if (offs < 16) {
pin = S3C64XX_GPN(offs);
pin_val = S3C_GPIO_SFN(2);
} else if (offs < 23) {
pin = S3C64XX_GPL(offs + 8 - 16);
pin_val = S3C_GPIO_SFN(3);
} else {
pin = S3C64XX_GPM(offs - 23);
pin_val = S3C_GPIO_SFN(3);
}
s3c_gpio_cfgpin(pin, pin_val);
return 0;
}
static struct irq_chip s3c_irq_eint = {
.name = "s3c-eint",
.irq_mask = s3c_irq_eint_mask,
.irq_unmask = s3c_irq_eint_unmask,
.irq_mask_ack = s3c_irq_eint_maskack,
.irq_ack = s3c_irq_eint_ack,
.irq_set_type = s3c_irq_eint_set_type,
.irq_set_wake = s3c_irqext_wake,
};
/* s3c_irq_demux_eint
*
* This function demuxes the IRQ from the group0 external interrupts,
* from IRQ_EINT(0) to IRQ_EINT(27). It is designed to be inlined into
* the specific handlers s3c_irq_demux_eintX_Y.
*/
static inline void s3c_irq_demux_eint(unsigned int start, unsigned int end)
{
u32 status = __raw_readl(S3C64XX_EINT0PEND);
u32 mask = __raw_readl(S3C64XX_EINT0MASK);
unsigned int irq;
status &= ~mask;
status >>= start;
status &= (1 << (end - start + 1)) - 1;
for (irq = IRQ_EINT(start); irq <= IRQ_EINT(end); irq++) {
if (status & 1)
generic_handle_irq(irq);
status >>= 1;
}
}
static void s3c_irq_demux_eint0_3(unsigned int irq, struct irq_desc *desc)
{
s3c_irq_demux_eint(0, 3);
}
static void s3c_irq_demux_eint4_11(unsigned int irq, struct irq_desc *desc)
{
s3c_irq_demux_eint(4, 11);
}
static void s3c_irq_demux_eint12_19(unsigned int irq, struct irq_desc *desc)
{
s3c_irq_demux_eint(12, 19);
}
static void s3c_irq_demux_eint20_27(unsigned int irq, struct irq_desc *desc)
{
s3c_irq_demux_eint(20, 27);
}
static int __init s3c64xx_init_irq_eint(void)
{
int irq;
/* On DT-enabled systems EINTs are handled by pinctrl-s3c64xx driver. */
if (of_have_populated_dt())
return -ENODEV;
for (irq = IRQ_EINT(0); irq <= IRQ_EINT(27); irq++) {
irq_set_chip_and_handler(irq, &s3c_irq_eint, handle_level_irq);
irq_set_chip_data(irq, (void *)eint_irq_to_bit(irq));
set_irq_flags(irq, IRQF_VALID);
}
irq_set_chained_handler(IRQ_EINT0_3, s3c_irq_demux_eint0_3);
irq_set_chained_handler(IRQ_EINT4_11, s3c_irq_demux_eint4_11);
irq_set_chained_handler(IRQ_EINT12_19, s3c_irq_demux_eint12_19);
irq_set_chained_handler(IRQ_EINT20_27, s3c_irq_demux_eint20_27);
return 0;
}
arch_initcall(s3c64xx_init_irq_eint);
void s3c64xx_restart(enum reboot_mode mode, const char *cmd)
{
if (mode != REBOOT_SOFT)
samsung_wdt_reset();
/* if all else fails, or mode was for soft, jump to 0 */
soft_restart(0);
}

View file

@ -0,0 +1,59 @@
/*
* Copyright (c) 2011 Samsung Electronics Co., Ltd.
* http://www.samsung.com
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* Common Header for S3C64XX machines
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef __ARCH_ARM_MACH_S3C64XX_COMMON_H
#define __ARCH_ARM_MACH_S3C64XX_COMMON_H
#include <linux/reboot.h>
void s3c64xx_init_irq(u32 vic0, u32 vic1);
void s3c64xx_init_io(struct map_desc *mach_desc, int size);
void s3c64xx_restart(enum reboot_mode mode, const char *cmd);
void s3c64xx_clk_init(struct device_node *np, unsigned long xtal_f,
unsigned long xusbxti_f, bool is_s3c6400, void __iomem *reg_base);
void s3c64xx_set_xtal_freq(unsigned long freq);
void s3c64xx_set_xusbxti_freq(unsigned long freq);
#ifdef CONFIG_CPU_S3C6400
extern int s3c6400_init(void);
extern void s3c6400_init_irq(void);
extern void s3c6400_map_io(void);
#else
#define s3c6400_map_io NULL
#define s3c6400_init NULL
#endif
#ifdef CONFIG_CPU_S3C6410
extern int s3c6410_init(void);
extern void s3c6410_init_irq(void);
extern void s3c6410_map_io(void);
#else
#define s3c6410_map_io NULL
#define s3c6410_init NULL
#endif
#ifdef CONFIG_S3C64XX_PL080
extern struct pl08x_platform_data s3c64xx_dma0_plat_data;
extern struct pl08x_platform_data s3c64xx_dma1_plat_data;
#endif
#endif /* __ARCH_ARM_MACH_S3C64XX_COMMON_H */

View file

@ -0,0 +1,63 @@
/* linux/arch/arm/mach-s3c64xx/cpuidle.c
*
* Copyright (c) 2011 Wolfson Microelectronics, plc
* Copyright (c) 2011 Samsung Electronics Co., Ltd.
* http://www.samsung.com
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/cpuidle.h>
#include <linux/io.h>
#include <linux/export.h>
#include <linux/time.h>
#include <asm/proc-fns.h>
#include <mach/map.h>
#include "regs-sys.h"
#include "regs-syscon-power.h"
static int s3c64xx_enter_idle(struct cpuidle_device *dev,
struct cpuidle_driver *drv,
int index)
{
unsigned long tmp;
/* Setup PWRCFG to enter idle mode */
tmp = __raw_readl(S3C64XX_PWR_CFG);
tmp &= ~S3C64XX_PWRCFG_CFG_WFI_MASK;
tmp |= S3C64XX_PWRCFG_CFG_WFI_IDLE;
__raw_writel(tmp, S3C64XX_PWR_CFG);
cpu_do_idle();
return index;
}
static struct cpuidle_driver s3c64xx_cpuidle_driver = {
.name = "s3c64xx_cpuidle",
.owner = THIS_MODULE,
.states = {
{
.enter = s3c64xx_enter_idle,
.exit_latency = 1,
.target_residency = 1,
.flags = CPUIDLE_FLAG_TIME_VALID,
.name = "IDLE",
.desc = "System active, ARM gated",
},
},
.state_count = 1,
};
static int __init s3c64xx_init_cpuidle(void)
{
return cpuidle_register(&s3c64xx_cpuidle_driver, NULL);
}
device_initcall(s3c64xx_init_cpuidle);

View file

@ -0,0 +1,25 @@
/* Cragganmore 6410 shared definitions
*
* Copyright 2011 Wolfson Microelectronics plc
* Mark Brown <broonie@opensource.wolfsonmicro.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef MACH_CRAG6410_H
#define MACH_CRAG6410_H
#include <mach/gpio-samsung.h>
#define GLENFARCLAS_PMIC_IRQ_BASE IRQ_BOARD_START
#define BANFF_PMIC_IRQ_BASE (IRQ_BOARD_START + 64)
#define PCA935X_GPIO_BASE GPIO_BOARD_START
#define CODEC_GPIO_BASE (GPIO_BOARD_START + 8)
#define GLENFARCLAS_PMIC_GPIO_BASE (GPIO_BOARD_START + 32)
#define BANFF_PMIC_GPIO_BASE (GPIO_BOARD_START + 64)
#define MMGPIO_GPIO_BASE (GPIO_BOARD_START + 96)
#endif

View file

@ -0,0 +1,228 @@
/* linux/arch/arm/plat-s3c/dev-audio.c
*
* Copyright 2009 Wolfson Microelectronics
* Mark Brown <broonie@opensource.wolfsonmicro.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/kernel.h>
#include <linux/string.h>
#include <linux/platform_device.h>
#include <linux/dma-mapping.h>
#include <linux/gpio.h>
#include <linux/export.h>
#include <mach/irqs.h>
#include <mach/map.h>
#include <mach/dma.h>
#include <plat/devs.h>
#include <linux/platform_data/asoc-s3c.h>
#include <plat/gpio-cfg.h>
#include <mach/gpio-samsung.h>
static int s3c64xx_i2s_cfg_gpio(struct platform_device *pdev)
{
unsigned int base;
switch (pdev->id) {
case 0:
base = S3C64XX_GPD(0);
break;
case 1:
base = S3C64XX_GPE(0);
break;
case 2:
s3c_gpio_cfgpin(S3C64XX_GPC(4), S3C_GPIO_SFN(5));
s3c_gpio_cfgpin(S3C64XX_GPC(5), S3C_GPIO_SFN(5));
s3c_gpio_cfgpin(S3C64XX_GPC(7), S3C_GPIO_SFN(5));
s3c_gpio_cfgpin_range(S3C64XX_GPH(6), 4, S3C_GPIO_SFN(5));
return 0;
default:
printk(KERN_DEBUG "Invalid I2S Controller number: %d\n",
pdev->id);
return -EINVAL;
}
s3c_gpio_cfgpin_range(base, 5, S3C_GPIO_SFN(3));
return 0;
}
static struct resource s3c64xx_iis0_resource[] = {
[0] = DEFINE_RES_MEM(S3C64XX_PA_IIS0, SZ_256),
[1] = DEFINE_RES_DMA(DMACH_I2S0_OUT),
[2] = DEFINE_RES_DMA(DMACH_I2S0_IN),
};
static struct s3c_audio_pdata i2sv3_pdata = {
.cfg_gpio = s3c64xx_i2s_cfg_gpio,
};
struct platform_device s3c64xx_device_iis0 = {
.name = "samsung-i2s",
.id = 0,
.num_resources = ARRAY_SIZE(s3c64xx_iis0_resource),
.resource = s3c64xx_iis0_resource,
.dev = {
.platform_data = &i2sv3_pdata,
},
};
EXPORT_SYMBOL(s3c64xx_device_iis0);
static struct resource s3c64xx_iis1_resource[] = {
[0] = DEFINE_RES_MEM(S3C64XX_PA_IIS1, SZ_256),
[1] = DEFINE_RES_DMA(DMACH_I2S1_OUT),
[2] = DEFINE_RES_DMA(DMACH_I2S1_IN),
};
struct platform_device s3c64xx_device_iis1 = {
.name = "samsung-i2s",
.id = 1,
.num_resources = ARRAY_SIZE(s3c64xx_iis1_resource),
.resource = s3c64xx_iis1_resource,
.dev = {
.platform_data = &i2sv3_pdata,
},
};
EXPORT_SYMBOL(s3c64xx_device_iis1);
static struct resource s3c64xx_iisv4_resource[] = {
[0] = DEFINE_RES_MEM(S3C64XX_PA_IISV4, SZ_256),
[1] = DEFINE_RES_DMA(DMACH_HSI_I2SV40_TX),
[2] = DEFINE_RES_DMA(DMACH_HSI_I2SV40_RX),
};
static struct s3c_audio_pdata i2sv4_pdata = {
.cfg_gpio = s3c64xx_i2s_cfg_gpio,
.type = {
.i2s = {
.quirks = QUIRK_PRI_6CHAN,
},
},
};
struct platform_device s3c64xx_device_iisv4 = {
.name = "samsung-i2s",
.id = 2,
.num_resources = ARRAY_SIZE(s3c64xx_iisv4_resource),
.resource = s3c64xx_iisv4_resource,
.dev = {
.platform_data = &i2sv4_pdata,
},
};
EXPORT_SYMBOL(s3c64xx_device_iisv4);
/* PCM Controller platform_devices */
static int s3c64xx_pcm_cfg_gpio(struct platform_device *pdev)
{
unsigned int base;
switch (pdev->id) {
case 0:
base = S3C64XX_GPD(0);
break;
case 1:
base = S3C64XX_GPE(0);
break;
default:
printk(KERN_DEBUG "Invalid PCM Controller number: %d\n",
pdev->id);
return -EINVAL;
}
s3c_gpio_cfgpin_range(base, 5, S3C_GPIO_SFN(2));
return 0;
}
static struct resource s3c64xx_pcm0_resource[] = {
[0] = DEFINE_RES_MEM(S3C64XX_PA_PCM0, SZ_256),
[1] = DEFINE_RES_DMA(DMACH_PCM0_TX),
[2] = DEFINE_RES_DMA(DMACH_PCM0_RX),
};
static struct s3c_audio_pdata s3c_pcm0_pdata = {
.cfg_gpio = s3c64xx_pcm_cfg_gpio,
};
struct platform_device s3c64xx_device_pcm0 = {
.name = "samsung-pcm",
.id = 0,
.num_resources = ARRAY_SIZE(s3c64xx_pcm0_resource),
.resource = s3c64xx_pcm0_resource,
.dev = {
.platform_data = &s3c_pcm0_pdata,
},
};
EXPORT_SYMBOL(s3c64xx_device_pcm0);
static struct resource s3c64xx_pcm1_resource[] = {
[0] = DEFINE_RES_MEM(S3C64XX_PA_PCM1, SZ_256),
[1] = DEFINE_RES_DMA(DMACH_PCM1_TX),
[2] = DEFINE_RES_DMA(DMACH_PCM1_RX),
};
static struct s3c_audio_pdata s3c_pcm1_pdata = {
.cfg_gpio = s3c64xx_pcm_cfg_gpio,
};
struct platform_device s3c64xx_device_pcm1 = {
.name = "samsung-pcm",
.id = 1,
.num_resources = ARRAY_SIZE(s3c64xx_pcm1_resource),
.resource = s3c64xx_pcm1_resource,
.dev = {
.platform_data = &s3c_pcm1_pdata,
},
};
EXPORT_SYMBOL(s3c64xx_device_pcm1);
/* AC97 Controller platform devices */
static int s3c64xx_ac97_cfg_gpd(struct platform_device *pdev)
{
return s3c_gpio_cfgpin_range(S3C64XX_GPD(0), 5, S3C_GPIO_SFN(4));
}
static int s3c64xx_ac97_cfg_gpe(struct platform_device *pdev)
{
return s3c_gpio_cfgpin_range(S3C64XX_GPE(0), 5, S3C_GPIO_SFN(4));
}
static struct resource s3c64xx_ac97_resource[] = {
[0] = DEFINE_RES_MEM(S3C64XX_PA_AC97, SZ_256),
[1] = DEFINE_RES_DMA(DMACH_AC97_PCMOUT),
[2] = DEFINE_RES_DMA(DMACH_AC97_PCMIN),
[3] = DEFINE_RES_DMA(DMACH_AC97_MICIN),
[4] = DEFINE_RES_IRQ(IRQ_AC97),
};
static struct s3c_audio_pdata s3c_ac97_pdata;
static u64 s3c64xx_ac97_dmamask = DMA_BIT_MASK(32);
struct platform_device s3c64xx_device_ac97 = {
.name = "samsung-ac97",
.id = -1,
.num_resources = ARRAY_SIZE(s3c64xx_ac97_resource),
.resource = s3c64xx_ac97_resource,
.dev = {
.platform_data = &s3c_ac97_pdata,
.dma_mask = &s3c64xx_ac97_dmamask,
.coherent_dma_mask = DMA_BIT_MASK(32),
},
};
EXPORT_SYMBOL(s3c64xx_device_ac97);
void __init s3c64xx_ac97_setup_gpio(int num)
{
if (num == S3C64XX_AC97_GPD)
s3c_ac97_pdata.cfg_gpio = s3c64xx_ac97_cfg_gpd;
else
s3c_ac97_pdata.cfg_gpio = s3c64xx_ac97_cfg_gpe;
}

View file

@ -0,0 +1,71 @@
/* linux/arch/arm/plat-s3c64xx/dev-uart.c
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* Base S3C64XX UART resource and device definitions
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/interrupt.h>
#include <linux/list.h>
#include <linux/platform_device.h>
#include <asm/mach/arch.h>
#include <asm/mach/irq.h>
#include <mach/hardware.h>
#include <mach/map.h>
#include <plat/devs.h>
/* Serial port registrations */
/* 64xx uarts are closer together */
static struct resource s3c64xx_uart0_resource[] = {
[0] = DEFINE_RES_MEM(S3C_PA_UART0, SZ_256),
[1] = DEFINE_RES_IRQ(IRQ_UART0),
};
static struct resource s3c64xx_uart1_resource[] = {
[0] = DEFINE_RES_MEM(S3C_PA_UART1, SZ_256),
[1] = DEFINE_RES_IRQ(IRQ_UART1),
};
static struct resource s3c6xx_uart2_resource[] = {
[0] = DEFINE_RES_MEM(S3C_PA_UART2, SZ_256),
[1] = DEFINE_RES_IRQ(IRQ_UART2),
};
static struct resource s3c64xx_uart3_resource[] = {
[0] = DEFINE_RES_MEM(S3C_PA_UART3, SZ_256),
[1] = DEFINE_RES_IRQ(IRQ_UART3),
};
struct s3c24xx_uart_resources s3c64xx_uart_resources[] __initdata = {
[0] = {
.resources = s3c64xx_uart0_resource,
.nr_resources = ARRAY_SIZE(s3c64xx_uart0_resource),
},
[1] = {
.resources = s3c64xx_uart1_resource,
.nr_resources = ARRAY_SIZE(s3c64xx_uart1_resource),
},
[2] = {
.resources = s3c6xx_uart2_resource,
.nr_resources = ARRAY_SIZE(s3c6xx_uart2_resource),
},
[3] = {
.resources = s3c64xx_uart3_resource,
.nr_resources = ARRAY_SIZE(s3c64xx_uart3_resource),
},
};

View file

@ -0,0 +1,38 @@
/* arch/arm/mach-s3c6400/include/mach/debug-macro.S
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* http://armlinux.simtec.co.uk/
* Ben Dooks <ben@simtec.co.uk>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
/* pull in the relevant register and map files. */
#include <linux/serial_s3c.h>
#include <mach/map.h>
/* note, for the boot process to work we have to keep the UART
* virtual address aligned to an 1MiB boundary for the L1
* mapping the head code makes. We keep the UART virtual address
* aligned and add in the offset when we load the value here.
*/
.macro addruart, rp, rv, tmp
ldr \rp, = S3C_PA_UART
ldr \rv, = (S3C_VA_UART + S3C_PA_UART & 0xfffff)
#if CONFIG_DEBUG_S3C_UART != 0
add \rp, \rp, #(0x400 * CONFIG_DEBUG_S3C_UART)
add \rv, \rv, #(0x400 * CONFIG_DEBUG_S3C_UART)
#endif
.endm
/* include the reset of the code which will do the work, we're only
* compiling for a single cpu processor type so the default of s3c2440
* will be fine with us.
*/
#include <debug/samsung.S>

View file

@ -0,0 +1,71 @@
/* linux/arch/arm/mach-s3c6400/include/mach/dma.h
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C6400 - DMA support
*/
#ifndef __ASM_ARCH_DMA_H
#define __ASM_ARCH_DMA_H __FILE__
#define S3C64XX_DMA_CHAN(name) ((unsigned long)(name))
/* DMA0/SDMA0 */
#define DMACH_UART0 S3C64XX_DMA_CHAN("uart0_tx")
#define DMACH_UART0_SRC2 S3C64XX_DMA_CHAN("uart0_rx")
#define DMACH_UART1 S3C64XX_DMA_CHAN("uart1_tx")
#define DMACH_UART1_SRC2 S3C64XX_DMA_CHAN("uart1_rx")
#define DMACH_UART2 S3C64XX_DMA_CHAN("uart2_tx")
#define DMACH_UART2_SRC2 S3C64XX_DMA_CHAN("uart2_rx")
#define DMACH_UART3 S3C64XX_DMA_CHAN("uart3_tx")
#define DMACH_UART3_SRC2 S3C64XX_DMA_CHAN("uart3_rx")
#define DMACH_PCM0_TX S3C64XX_DMA_CHAN("pcm0_tx")
#define DMACH_PCM0_RX S3C64XX_DMA_CHAN("pcm0_rx")
#define DMACH_I2S0_OUT S3C64XX_DMA_CHAN("i2s0_tx")
#define DMACH_I2S0_IN S3C64XX_DMA_CHAN("i2s0_rx")
#define DMACH_SPI0_TX S3C64XX_DMA_CHAN("spi0_tx")
#define DMACH_SPI0_RX S3C64XX_DMA_CHAN("spi0_rx")
#define DMACH_HSI_I2SV40_TX S3C64XX_DMA_CHAN("i2s2_tx")
#define DMACH_HSI_I2SV40_RX S3C64XX_DMA_CHAN("i2s2_rx")
/* DMA1/SDMA1 */
#define DMACH_PCM1_TX S3C64XX_DMA_CHAN("pcm1_tx")
#define DMACH_PCM1_RX S3C64XX_DMA_CHAN("pcm1_rx")
#define DMACH_I2S1_OUT S3C64XX_DMA_CHAN("i2s1_tx")
#define DMACH_I2S1_IN S3C64XX_DMA_CHAN("i2s1_rx")
#define DMACH_SPI1_TX S3C64XX_DMA_CHAN("spi1_tx")
#define DMACH_SPI1_RX S3C64XX_DMA_CHAN("spi1_rx")
#define DMACH_AC97_PCMOUT S3C64XX_DMA_CHAN("ac97_out")
#define DMACH_AC97_PCMIN S3C64XX_DMA_CHAN("ac97_in")
#define DMACH_AC97_MICIN S3C64XX_DMA_CHAN("ac97_mic")
#define DMACH_PWM S3C64XX_DMA_CHAN("pwm")
#define DMACH_IRDA S3C64XX_DMA_CHAN("irda")
#define DMACH_EXTERNAL S3C64XX_DMA_CHAN("external")
#define DMACH_SECURITY_RX S3C64XX_DMA_CHAN("sec_rx")
#define DMACH_SECURITY_TX S3C64XX_DMA_CHAN("sec_tx")
enum dma_ch {
DMACH_MAX = 32
};
struct s3c2410_dma_client {
char *name;
};
static inline bool samsung_dma_has_circular(void)
{
return true;
}
static inline bool samsung_dma_is_dmadev(void)
{
return true;
}
#include <linux/amba/pl08x.h>
#include <plat/dma-ops.h>
#endif /* __ASM_ARCH_IRQ_H */

View file

@ -0,0 +1,94 @@
/*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* http://armlinux.simtec.co.uk/
* Ben Dooks <ben@simtec.co.uk>
*
* S3C6400 - GPIO lib support
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef GPIO_SAMSUNG_S3C64XX_H
#define GPIO_SAMSUNG_S3C64XX_H
/* GPIO bank sizes */
#define S3C64XX_GPIO_A_NR (8)
#define S3C64XX_GPIO_B_NR (7)
#define S3C64XX_GPIO_C_NR (8)
#define S3C64XX_GPIO_D_NR (5)
#define S3C64XX_GPIO_E_NR (5)
#define S3C64XX_GPIO_F_NR (16)
#define S3C64XX_GPIO_G_NR (7)
#define S3C64XX_GPIO_H_NR (10)
#define S3C64XX_GPIO_I_NR (16)
#define S3C64XX_GPIO_J_NR (12)
#define S3C64XX_GPIO_K_NR (16)
#define S3C64XX_GPIO_L_NR (15)
#define S3C64XX_GPIO_M_NR (6)
#define S3C64XX_GPIO_N_NR (16)
#define S3C64XX_GPIO_O_NR (16)
#define S3C64XX_GPIO_P_NR (15)
#define S3C64XX_GPIO_Q_NR (9)
/* GPIO bank numbes */
/* CONFIG_S3C_GPIO_SPACE allows the user to select extra
* space for debugging purposes so that any accidental
* change from one gpio bank to another can be caught.
*/
#define S3C64XX_GPIO_NEXT(__gpio) \
((__gpio##_START) + (__gpio##_NR) + CONFIG_S3C_GPIO_SPACE + 1)
enum s3c_gpio_number {
S3C64XX_GPIO_A_START = 0,
S3C64XX_GPIO_B_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_A),
S3C64XX_GPIO_C_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_B),
S3C64XX_GPIO_D_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_C),
S3C64XX_GPIO_E_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_D),
S3C64XX_GPIO_F_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_E),
S3C64XX_GPIO_G_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_F),
S3C64XX_GPIO_H_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_G),
S3C64XX_GPIO_I_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_H),
S3C64XX_GPIO_J_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_I),
S3C64XX_GPIO_K_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_J),
S3C64XX_GPIO_L_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_K),
S3C64XX_GPIO_M_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_L),
S3C64XX_GPIO_N_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_M),
S3C64XX_GPIO_O_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_N),
S3C64XX_GPIO_P_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_O),
S3C64XX_GPIO_Q_START = S3C64XX_GPIO_NEXT(S3C64XX_GPIO_P),
};
/* S3C64XX GPIO number definitions. */
#define S3C64XX_GPA(_nr) (S3C64XX_GPIO_A_START + (_nr))
#define S3C64XX_GPB(_nr) (S3C64XX_GPIO_B_START + (_nr))
#define S3C64XX_GPC(_nr) (S3C64XX_GPIO_C_START + (_nr))
#define S3C64XX_GPD(_nr) (S3C64XX_GPIO_D_START + (_nr))
#define S3C64XX_GPE(_nr) (S3C64XX_GPIO_E_START + (_nr))
#define S3C64XX_GPF(_nr) (S3C64XX_GPIO_F_START + (_nr))
#define S3C64XX_GPG(_nr) (S3C64XX_GPIO_G_START + (_nr))
#define S3C64XX_GPH(_nr) (S3C64XX_GPIO_H_START + (_nr))
#define S3C64XX_GPI(_nr) (S3C64XX_GPIO_I_START + (_nr))
#define S3C64XX_GPJ(_nr) (S3C64XX_GPIO_J_START + (_nr))
#define S3C64XX_GPK(_nr) (S3C64XX_GPIO_K_START + (_nr))
#define S3C64XX_GPL(_nr) (S3C64XX_GPIO_L_START + (_nr))
#define S3C64XX_GPM(_nr) (S3C64XX_GPIO_M_START + (_nr))
#define S3C64XX_GPN(_nr) (S3C64XX_GPIO_N_START + (_nr))
#define S3C64XX_GPO(_nr) (S3C64XX_GPIO_O_START + (_nr))
#define S3C64XX_GPP(_nr) (S3C64XX_GPIO_P_START + (_nr))
#define S3C64XX_GPQ(_nr) (S3C64XX_GPIO_Q_START + (_nr))
/* the end of the S3C64XX specific gpios */
#define S3C64XX_GPIO_END (S3C64XX_GPQ(S3C64XX_GPIO_Q_NR) + 1)
#define S3C_GPIO_END S3C64XX_GPIO_END
/* define the number of gpios we need to the one after the GPQ() range */
#define GPIO_BOARD_START (S3C64XX_GPQ(S3C64XX_GPIO_Q_NR) + 1)
#endif /* GPIO_SAMSUNG_S3C64XX_H */

View file

@ -0,0 +1,16 @@
/* linux/arch/arm/mach-s3c6400/include/mach/hardware.h
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C6400 - Hardware support
*/
#ifndef __ASM_ARCH_HARDWARE_H
#define __ASM_ARCH_HARDWARE_H __FILE__
/* currently nothing here, placeholder */
#endif /* __ASM_ARCH_IRQ_H */

View file

@ -0,0 +1,185 @@
/* linux/arch/arm/mach-s3c64xx/include/mach/irqs.h
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C64XX - IRQ support
*/
#ifndef __ASM_MACH_S3C64XX_IRQS_H
#define __ASM_MACH_S3C64XX_IRQS_H __FILE__
/* we keep the first set of CPU IRQs out of the range of
* the ISA space, so that the PC104 has them to itself
* and we don't end up having to do horrible things to the
* standard ISA drivers....
*
* note, since we're using the VICs, our start must be a
* mulitple of 32 to allow the common code to work
*/
#define S3C_IRQ_OFFSET (32)
#define S3C_IRQ(x) ((x) + S3C_IRQ_OFFSET)
#define IRQ_VIC0_BASE S3C_IRQ(0)
#define IRQ_VIC1_BASE S3C_IRQ(32)
/* VIC based IRQs */
#define S3C64XX_IRQ_VIC0(x) (IRQ_VIC0_BASE + (x))
#define S3C64XX_IRQ_VIC1(x) (IRQ_VIC1_BASE + (x))
/* VIC0 */
#define IRQ_EINT0_3 S3C64XX_IRQ_VIC0(0)
#define IRQ_EINT4_11 S3C64XX_IRQ_VIC0(1)
#define IRQ_RTC_TIC S3C64XX_IRQ_VIC0(2)
#define IRQ_CAMIF_C S3C64XX_IRQ_VIC0(3)
#define IRQ_CAMIF_P S3C64XX_IRQ_VIC0(4)
#define IRQ_CAMIF_MC S3C64XX_IRQ_VIC0(5)
#define IRQ_S3C6410_IIC1 S3C64XX_IRQ_VIC0(5)
#define IRQ_S3C6410_IIS S3C64XX_IRQ_VIC0(6)
#define IRQ_S3C6400_CAMIF_MP S3C64XX_IRQ_VIC0(6)
#define IRQ_CAMIF_WE_C S3C64XX_IRQ_VIC0(7)
#define IRQ_S3C6410_G3D S3C64XX_IRQ_VIC0(8)
#define IRQ_S3C6400_CAMIF_WE_P S3C64XX_IRQ_VIC0(8)
#define IRQ_POST0 S3C64XX_IRQ_VIC0(9)
#define IRQ_ROTATOR S3C64XX_IRQ_VIC0(10)
#define IRQ_2D S3C64XX_IRQ_VIC0(11)
#define IRQ_TVENC S3C64XX_IRQ_VIC0(12)
#define IRQ_SCALER S3C64XX_IRQ_VIC0(13)
#define IRQ_BATF S3C64XX_IRQ_VIC0(14)
#define IRQ_JPEG S3C64XX_IRQ_VIC0(15)
#define IRQ_MFC S3C64XX_IRQ_VIC0(16)
#define IRQ_SDMA0 S3C64XX_IRQ_VIC0(17)
#define IRQ_SDMA1 S3C64XX_IRQ_VIC0(18)
#define IRQ_ARM_DMAERR S3C64XX_IRQ_VIC0(19)
#define IRQ_ARM_DMA S3C64XX_IRQ_VIC0(20)
#define IRQ_ARM_DMAS S3C64XX_IRQ_VIC0(21)
#define IRQ_KEYPAD S3C64XX_IRQ_VIC0(22)
#define IRQ_TIMER0_VIC S3C64XX_IRQ_VIC0(23)
#define IRQ_TIMER1_VIC S3C64XX_IRQ_VIC0(24)
#define IRQ_TIMER2_VIC S3C64XX_IRQ_VIC0(25)
#define IRQ_WDT S3C64XX_IRQ_VIC0(26)
#define IRQ_TIMER3_VIC S3C64XX_IRQ_VIC0(27)
#define IRQ_TIMER4_VIC S3C64XX_IRQ_VIC0(28)
#define IRQ_LCD_FIFO S3C64XX_IRQ_VIC0(29)
#define IRQ_LCD_VSYNC S3C64XX_IRQ_VIC0(30)
#define IRQ_LCD_SYSTEM S3C64XX_IRQ_VIC0(31)
/* VIC1 */
#define IRQ_EINT12_19 S3C64XX_IRQ_VIC1(0)
#define IRQ_EINT20_27 S3C64XX_IRQ_VIC1(1)
#define IRQ_PCM0 S3C64XX_IRQ_VIC1(2)
#define IRQ_PCM1 S3C64XX_IRQ_VIC1(3)
#define IRQ_AC97 S3C64XX_IRQ_VIC1(4)
#define IRQ_UART0 S3C64XX_IRQ_VIC1(5)
#define IRQ_UART1 S3C64XX_IRQ_VIC1(6)
#define IRQ_UART2 S3C64XX_IRQ_VIC1(7)
#define IRQ_UART3 S3C64XX_IRQ_VIC1(8)
#define IRQ_DMA0 S3C64XX_IRQ_VIC1(9)
#define IRQ_DMA1 S3C64XX_IRQ_VIC1(10)
#define IRQ_ONENAND0 S3C64XX_IRQ_VIC1(11)
#define IRQ_ONENAND1 S3C64XX_IRQ_VIC1(12)
#define IRQ_NFC S3C64XX_IRQ_VIC1(13)
#define IRQ_CFCON S3C64XX_IRQ_VIC1(14)
#define IRQ_USBH S3C64XX_IRQ_VIC1(15)
#define IRQ_SPI0 S3C64XX_IRQ_VIC1(16)
#define IRQ_SPI1 S3C64XX_IRQ_VIC1(17)
#define IRQ_IIC S3C64XX_IRQ_VIC1(18)
#define IRQ_HSItx S3C64XX_IRQ_VIC1(19)
#define IRQ_HSIrx S3C64XX_IRQ_VIC1(20)
#define IRQ_RESERVED S3C64XX_IRQ_VIC1(21)
#define IRQ_MSM S3C64XX_IRQ_VIC1(22)
#define IRQ_HOSTIF S3C64XX_IRQ_VIC1(23)
#define IRQ_HSMMC0 S3C64XX_IRQ_VIC1(24)
#define IRQ_HSMMC1 S3C64XX_IRQ_VIC1(25)
#define IRQ_HSMMC2 IRQ_SPI1 /* shared with SPI1 */
#define IRQ_OTG S3C64XX_IRQ_VIC1(26)
#define IRQ_IRDA S3C64XX_IRQ_VIC1(27)
#define IRQ_RTC_ALARM S3C64XX_IRQ_VIC1(28)
#define IRQ_SEC S3C64XX_IRQ_VIC1(29)
#define IRQ_PENDN S3C64XX_IRQ_VIC1(30)
#define IRQ_TC IRQ_PENDN
#define IRQ_ADC S3C64XX_IRQ_VIC1(31)
/* compatibility for device defines */
#define IRQ_IIC1 IRQ_S3C6410_IIC1
/* Since the IRQ_EINT(x) are a linear mapping on current s3c64xx series
* we just defined them as an IRQ_EINT(x) macro from S3C_IRQ_EINT_BASE
* which we place after the pair of VICs. */
#define S3C_IRQ_EINT_BASE S3C_IRQ(64+5)
#define S3C_EINT(x) ((x) + S3C_IRQ_EINT_BASE)
#define IRQ_EINT(x) S3C_EINT(x)
#define IRQ_EINT_BIT(x) ((x) - S3C_EINT(0))
/* Next the external interrupt groups. These are similar to the IRQ_EINT(x)
* that they are sourced from the GPIO pins but with a different scheme for
* priority and source indication.
*
* The IRQ_EINT(x) can be thought of as 'group 0' of the available GPIO
* interrupts, but for historical reasons they are kept apart from these
* next interrupts.
*
* Use IRQ_EINT_GROUP(group, offset) to get the number for use in the
* machine specific support files.
*/
#define IRQ_EINT_GROUP1_NR (15)
#define IRQ_EINT_GROUP2_NR (8)
#define IRQ_EINT_GROUP3_NR (5)
#define IRQ_EINT_GROUP4_NR (14)
#define IRQ_EINT_GROUP5_NR (7)
#define IRQ_EINT_GROUP6_NR (10)
#define IRQ_EINT_GROUP7_NR (16)
#define IRQ_EINT_GROUP8_NR (15)
#define IRQ_EINT_GROUP9_NR (9)
#define IRQ_EINT_GROUP_BASE S3C_EINT(28)
#define IRQ_EINT_GROUP1_BASE (IRQ_EINT_GROUP_BASE + 0x00)
#define IRQ_EINT_GROUP2_BASE (IRQ_EINT_GROUP1_BASE + IRQ_EINT_GROUP1_NR)
#define IRQ_EINT_GROUP3_BASE (IRQ_EINT_GROUP2_BASE + IRQ_EINT_GROUP2_NR)
#define IRQ_EINT_GROUP4_BASE (IRQ_EINT_GROUP3_BASE + IRQ_EINT_GROUP3_NR)
#define IRQ_EINT_GROUP5_BASE (IRQ_EINT_GROUP4_BASE + IRQ_EINT_GROUP4_NR)
#define IRQ_EINT_GROUP6_BASE (IRQ_EINT_GROUP5_BASE + IRQ_EINT_GROUP5_NR)
#define IRQ_EINT_GROUP7_BASE (IRQ_EINT_GROUP6_BASE + IRQ_EINT_GROUP6_NR)
#define IRQ_EINT_GROUP8_BASE (IRQ_EINT_GROUP7_BASE + IRQ_EINT_GROUP7_NR)
#define IRQ_EINT_GROUP9_BASE (IRQ_EINT_GROUP8_BASE + IRQ_EINT_GROUP8_NR)
#define IRQ_EINT_GROUP(group, no) (IRQ_EINT_GROUP##group##_BASE + (no))
/* Define a group of interrupts for board-specific use (eg, for MFD
* interrupt controllers). */
#define IRQ_BOARD_START (IRQ_EINT_GROUP9_BASE + IRQ_EINT_GROUP9_NR + 1)
#ifdef CONFIG_MACH_WLF_CRAGG_6410
#define IRQ_BOARD_NR 160
#elif defined(CONFIG_SMDK6410_WM1190_EV1)
#define IRQ_BOARD_NR 64
#elif defined(CONFIG_SMDK6410_WM1192_EV1)
#define IRQ_BOARD_NR 64
#else
#define IRQ_BOARD_NR 16
#endif
#define IRQ_BOARD_END (IRQ_BOARD_START + IRQ_BOARD_NR)
/* Set the default NR_IRQS */
#define NR_IRQS (IRQ_BOARD_END + 1)
/* Compatibility */
#define IRQ_ONENAND IRQ_ONENAND0
#define IRQ_I2S0 IRQ_S3C6410_IIS
#endif /* __ASM_MACH_S3C64XX_IRQS_H */

View file

@ -0,0 +1,126 @@
/* linux/arch/arm/mach-s3c6400/include/mach/map.h
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* http://armlinux.simtec.co.uk/
* Ben Dooks <ben@simtec.co.uk>
*
* S3C64XX - Memory map definitions
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef __ASM_ARCH_MAP_H
#define __ASM_ARCH_MAP_H __FILE__
#include <plat/map-base.h>
#include <plat/map-s3c.h>
/*
* Post-mux Chip Select Regions Xm0CSn_
* These may be used by SROM, NAND or CF depending on settings
*/
#define S3C64XX_PA_XM0CSN0 (0x10000000)
#define S3C64XX_PA_XM0CSN1 (0x18000000)
#define S3C64XX_PA_XM0CSN2 (0x20000000)
#define S3C64XX_PA_XM0CSN3 (0x28000000)
#define S3C64XX_PA_XM0CSN4 (0x30000000)
#define S3C64XX_PA_XM0CSN5 (0x38000000)
/* HSMMC units */
#define S3C64XX_PA_HSMMC(x) (0x7C200000 + ((x) * 0x100000))
#define S3C64XX_PA_HSMMC0 S3C64XX_PA_HSMMC(0)
#define S3C64XX_PA_HSMMC1 S3C64XX_PA_HSMMC(1)
#define S3C64XX_PA_HSMMC2 S3C64XX_PA_HSMMC(2)
#define S3C_PA_UART (0x7F005000)
#define S3C_PA_UART0 (S3C_PA_UART + 0x00)
#define S3C_PA_UART1 (S3C_PA_UART + 0x400)
#define S3C_PA_UART2 (S3C_PA_UART + 0x800)
#define S3C_PA_UART3 (S3C_PA_UART + 0xC00)
#define S3C_UART_OFFSET (0x400)
/* See notes on UART VA mapping in debug-macro.S */
#define S3C_VA_UARTx(x) (S3C_VA_UART + (S3C_PA_UART & 0xfffff) + ((x) * S3C_UART_OFFSET))
#define S3C_VA_UART0 S3C_VA_UARTx(0)
#define S3C_VA_UART1 S3C_VA_UARTx(1)
#define S3C_VA_UART2 S3C_VA_UARTx(2)
#define S3C_VA_UART3 S3C_VA_UARTx(3)
#define S3C64XX_PA_SROM (0x70000000)
#define S3C64XX_PA_ONENAND0 (0x70100000)
#define S3C64XX_PA_ONENAND0_BUF (0x20000000)
#define S3C64XX_SZ_ONENAND0_BUF (SZ_64M)
/* NAND and OneNAND1 controllers occupy the same register region
(depending on SoC POP version) */
#define S3C64XX_PA_ONENAND1 (0x70200000)
#define S3C64XX_PA_ONENAND1_BUF (0x28000000)
#define S3C64XX_SZ_ONENAND1_BUF (SZ_64M)
#define S3C64XX_PA_NAND (0x70200000)
#define S3C64XX_PA_FB (0x77100000)
#define S3C64XX_PA_USB_HSOTG (0x7C000000)
#define S3C64XX_PA_WATCHDOG (0x7E004000)
#define S3C64XX_PA_RTC (0x7E005000)
#define S3C64XX_PA_KEYPAD (0x7E00A000)
#define S3C64XX_PA_ADC (0x7E00B000)
#define S3C64XX_PA_SYSCON (0x7E00F000)
#define S3C64XX_PA_AC97 (0x7F001000)
#define S3C64XX_PA_IIS0 (0x7F002000)
#define S3C64XX_PA_IIS1 (0x7F003000)
#define S3C64XX_PA_TIMER (0x7F006000)
#define S3C64XX_PA_IIC0 (0x7F004000)
#define S3C64XX_PA_SPI0 (0x7F00B000)
#define S3C64XX_PA_SPI1 (0x7F00C000)
#define S3C64XX_PA_PCM0 (0x7F009000)
#define S3C64XX_PA_PCM1 (0x7F00A000)
#define S3C64XX_PA_IISV4 (0x7F00D000)
#define S3C64XX_PA_IIC1 (0x7F00F000)
#define S3C64XX_PA_GPIO (0x7F008000)
#define S3C64XX_SZ_GPIO SZ_4K
#define S3C64XX_PA_SDRAM (0x50000000)
#define S3C64XX_PA_CFCON (0x70300000)
#define S3C64XX_PA_VIC0 (0x71200000)
#define S3C64XX_PA_VIC1 (0x71300000)
#define S3C64XX_PA_MODEM (0x74108000)
#define S3C64XX_PA_USBHOST (0x74300000)
#define S3C64XX_PA_USB_HSPHY (0x7C100000)
/* compatibiltiy defines. */
#define S3C_PA_TIMER S3C64XX_PA_TIMER
#define S3C_PA_HSMMC0 S3C64XX_PA_HSMMC0
#define S3C_PA_HSMMC1 S3C64XX_PA_HSMMC1
#define S3C_PA_HSMMC2 S3C64XX_PA_HSMMC2
#define S3C_PA_IIC S3C64XX_PA_IIC0
#define S3C_PA_IIC1 S3C64XX_PA_IIC1
#define S3C_PA_NAND S3C64XX_PA_NAND
#define S3C_PA_ONENAND S3C64XX_PA_ONENAND0
#define S3C_PA_ONENAND_BUF S3C64XX_PA_ONENAND0_BUF
#define S3C_SZ_ONENAND_BUF S3C64XX_SZ_ONENAND0_BUF
#define S3C_PA_FB S3C64XX_PA_FB
#define S3C_PA_USBHOST S3C64XX_PA_USBHOST
#define S3C_PA_USB_HSOTG S3C64XX_PA_USB_HSOTG
#define S3C_PA_RTC S3C64XX_PA_RTC
#define S3C_PA_WDT S3C64XX_PA_WATCHDOG
#define S3C_PA_SPI0 S3C64XX_PA_SPI0
#define S3C_PA_SPI1 S3C64XX_PA_SPI1
#define SAMSUNG_PA_ADC S3C64XX_PA_ADC
#define SAMSUNG_PA_CFCON S3C64XX_PA_CFCON
#define SAMSUNG_PA_KEYPAD S3C64XX_PA_KEYPAD
#define SAMSUNG_PA_TIMER S3C64XX_PA_TIMER
#endif /* __ASM_ARCH_6400_MAP_H */

View file

@ -0,0 +1,121 @@
/* linux/arch/arm/mach-s3c64xx/include/mach/pm-core.h
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C64XX - PM core support for arch/arm/plat-s3c/pm.c
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef __MACH_S3C64XX_PM_CORE_H
#define __MACH_S3C64XX_PM_CORE_H __FILE__
#include <linux/serial_s3c.h>
#include <mach/regs-gpio.h>
static inline void s3c_pm_debug_init_uart(void)
{
u32 tmp = __raw_readl(S3C_PCLK_GATE);
/* As a note, since the S3C64XX UARTs generally have multiple
* clock sources, we simply enable PCLK at the moment and hope
* that the resume settings for the UART are suitable for the
* use with PCLK.
*/
tmp |= S3C_CLKCON_PCLK_UART0;
tmp |= S3C_CLKCON_PCLK_UART1;
tmp |= S3C_CLKCON_PCLK_UART2;
tmp |= S3C_CLKCON_PCLK_UART3;
__raw_writel(tmp, S3C_PCLK_GATE);
udelay(10);
}
static inline void s3c_pm_arch_prepare_irqs(void)
{
/* VIC should have already been taken care of */
/* clear any pending EINT0 interrupts */
__raw_writel(__raw_readl(S3C64XX_EINT0PEND), S3C64XX_EINT0PEND);
}
static inline void s3c_pm_arch_stop_clocks(void)
{
}
static inline void s3c_pm_arch_show_resume_irqs(void)
{
}
/* make these defines, we currently do not have any need to change
* the IRQ wake controls depending on the CPU we are running on */
#define s3c_irqwake_eintallow ((1 << 28) - 1)
#define s3c_irqwake_intallow (~0)
static inline void s3c_pm_arch_update_uart(void __iomem *regs,
struct pm_uart_save *save)
{
u32 ucon = __raw_readl(regs + S3C2410_UCON);
u32 ucon_clk = ucon & S3C6400_UCON_CLKMASK;
u32 save_clk = save->ucon & S3C6400_UCON_CLKMASK;
u32 new_ucon;
u32 delta;
/* S3C64XX UART blocks only support level interrupts, so ensure that
* when we restore unused UART blocks we force the level interrupt
* settigs. */
save->ucon |= S3C2410_UCON_TXILEVEL | S3C2410_UCON_RXILEVEL;
/* We have a constraint on changing the clock type of the UART
* between UCLKx and PCLK, so ensure that when we restore UCON
* that the CLK field is correctly modified if the bootloader
* has changed anything.
*/
if (ucon_clk != save_clk) {
new_ucon = save->ucon;
delta = ucon_clk ^ save_clk;
/* change from UCLKx => wrong PCLK,
* either UCLK can be tested for by a bit-test
* with UCLK0 */
if (ucon_clk & S3C6400_UCON_UCLK0 &&
!(save_clk & S3C6400_UCON_UCLK0) &&
delta & S3C6400_UCON_PCLK2) {
new_ucon &= ~S3C6400_UCON_UCLK0;
} else if (delta == S3C6400_UCON_PCLK2) {
/* as an precaution, don't change from
* PCLK2 => PCLK or vice-versa */
new_ucon ^= S3C6400_UCON_PCLK2;
}
S3C_PMDBG("ucon change %04x => %04x (save=%04x)\n",
ucon, new_ucon, save->ucon);
save->ucon = new_ucon;
}
}
static inline void s3c_pm_restored_gpios(void)
{
/* ensure sleep mode has been cleared from the system */
__raw_writel(0, S3C64XX_SLPEN);
}
static inline void samsung_pm_saved_gpios(void)
{
/* turn on the sleep mode and keep it there, as it seems that during
* suspend the xCON registers get re-set and thus you can end up with
* problems between going to sleep and resuming.
*/
__raw_writel(S3C64XX_SLPEN_USE_xSLP, S3C64XX_SLPEN);
}
#endif /* __MACH_S3C64XX_PM_CORE_H */

View file

@ -0,0 +1,38 @@
/* arch/arm/plat-s3c64xx/include/plat/regs-clock.h
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C64XX clock register definitions
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef __PLAT_REGS_CLOCK_H
#define __PLAT_REGS_CLOCK_H __FILE__
/*
* FIXME: Remove remaining definitions
*/
#define S3C_CLKREG(x) (S3C_VA_SYS + (x))
#define S3C_PCLK_GATE S3C_CLKREG(0x34)
#define S3C6410_CLK_SRC2 S3C_CLKREG(0x10C)
#define S3C_MEM_SYS_CFG S3C_CLKREG(0x120)
/* PCLK GATE Registers */
#define S3C_CLKCON_PCLK_UART3 (1<<4)
#define S3C_CLKCON_PCLK_UART2 (1<<3)
#define S3C_CLKCON_PCLK_UART1 (1<<2)
#define S3C_CLKCON_PCLK_UART0 (1<<1)
/* MEM_SYS_CFG */
#define MEM_SYS_CFG_INDEP_CF 0x4000
#define MEM_SYS_CFG_EBI_FIX_PRI_CFCON 0x30
#endif /* _PLAT_REGS_CLOCK_H */

View file

@ -0,0 +1,187 @@
/* linux/arch/arm/plat-s3c64xx/include/mach/regs-gpio.h
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C64XX - GPIO register definitions
*/
#ifndef __ASM_PLAT_S3C64XX_REGS_GPIO_H
#define __ASM_PLAT_S3C64XX_REGS_GPIO_H __FILE__
/* Base addresses for each of the banks */
#define S3C64XX_GPIOREG(reg) (S3C64XX_VA_GPIO + (reg))
#define S3C64XX_GPA_BASE S3C64XX_GPIOREG(0x0000)
#define S3C64XX_GPB_BASE S3C64XX_GPIOREG(0x0020)
#define S3C64XX_GPC_BASE S3C64XX_GPIOREG(0x0040)
#define S3C64XX_GPD_BASE S3C64XX_GPIOREG(0x0060)
#define S3C64XX_GPE_BASE S3C64XX_GPIOREG(0x0080)
#define S3C64XX_GPF_BASE S3C64XX_GPIOREG(0x00A0)
#define S3C64XX_GPG_BASE S3C64XX_GPIOREG(0x00C0)
#define S3C64XX_GPH_BASE S3C64XX_GPIOREG(0x00E0)
#define S3C64XX_GPI_BASE S3C64XX_GPIOREG(0x0100)
#define S3C64XX_GPJ_BASE S3C64XX_GPIOREG(0x0120)
#define S3C64XX_GPK_BASE S3C64XX_GPIOREG(0x0800)
#define S3C64XX_GPL_BASE S3C64XX_GPIOREG(0x0810)
#define S3C64XX_GPM_BASE S3C64XX_GPIOREG(0x0820)
#define S3C64XX_GPN_BASE S3C64XX_GPIOREG(0x0830)
#define S3C64XX_GPO_BASE S3C64XX_GPIOREG(0x0140)
#define S3C64XX_GPP_BASE S3C64XX_GPIOREG(0x0160)
#define S3C64XX_GPQ_BASE S3C64XX_GPIOREG(0x0180)
/* SPCON */
#define S3C64XX_SPCON S3C64XX_GPIOREG(0x1A0)
#define S3C64XX_SPCON_DRVCON_CAM_MASK (0x3 << 30)
#define S3C64XX_SPCON_DRVCON_CAM_SHIFT (30)
#define S3C64XX_SPCON_DRVCON_CAM_2mA (0x0 << 30)
#define S3C64XX_SPCON_DRVCON_CAM_4mA (0x1 << 30)
#define S3C64XX_SPCON_DRVCON_CAM_7mA (0x2 << 30)
#define S3C64XX_SPCON_DRVCON_CAM_9mA (0x3 << 30)
#define S3C64XX_SPCON_DRVCON_HSSPI_MASK (0x3 << 28)
#define S3C64XX_SPCON_DRVCON_HSSPI_SHIFT (28)
#define S3C64XX_SPCON_DRVCON_HSSPI_2mA (0x0 << 28)
#define S3C64XX_SPCON_DRVCON_HSSPI_4mA (0x1 << 28)
#define S3C64XX_SPCON_DRVCON_HSSPI_7mA (0x2 << 28)
#define S3C64XX_SPCON_DRVCON_HSSPI_9mA (0x3 << 28)
#define S3C64XX_SPCON_DRVCON_HSMMC_MASK (0x3 << 26)
#define S3C64XX_SPCON_DRVCON_HSMMC_SHIFT (26)
#define S3C64XX_SPCON_DRVCON_HSMMC_2mA (0x0 << 26)
#define S3C64XX_SPCON_DRVCON_HSMMC_4mA (0x1 << 26)
#define S3C64XX_SPCON_DRVCON_HSMMC_7mA (0x2 << 26)
#define S3C64XX_SPCON_DRVCON_HSMMC_9mA (0x3 << 26)
#define S3C64XX_SPCON_DRVCON_LCD_MASK (0x3 << 24)
#define S3C64XX_SPCON_DRVCON_LCD_SHIFT (24)
#define S3C64XX_SPCON_DRVCON_LCD_2mA (0x0 << 24)
#define S3C64XX_SPCON_DRVCON_LCD_4mA (0x1 << 24)
#define S3C64XX_SPCON_DRVCON_LCD_7mA (0x2 << 24)
#define S3C64XX_SPCON_DRVCON_LCD_9mA (0x3 << 24)
#define S3C64XX_SPCON_DRVCON_MODEM_MASK (0x3 << 22)
#define S3C64XX_SPCON_DRVCON_MODEM_SHIFT (22)
#define S3C64XX_SPCON_DRVCON_MODEM_2mA (0x0 << 22)
#define S3C64XX_SPCON_DRVCON_MODEM_4mA (0x1 << 22)
#define S3C64XX_SPCON_DRVCON_MODEM_7mA (0x2 << 22)
#define S3C64XX_SPCON_DRVCON_MODEM_9mA (0x3 << 22)
#define S3C64XX_SPCON_nRSTOUT_OEN (1 << 21)
#define S3C64XX_SPCON_DRVCON_SPICLK1_MASK (0x3 << 18)
#define S3C64XX_SPCON_DRVCON_SPICLK1_SHIFT (18)
#define S3C64XX_SPCON_DRVCON_SPICLK1_2mA (0x0 << 18)
#define S3C64XX_SPCON_DRVCON_SPICLK1_4mA (0x1 << 18)
#define S3C64XX_SPCON_DRVCON_SPICLK1_7mA (0x2 << 18)
#define S3C64XX_SPCON_DRVCON_SPICLK1_9mA (0x3 << 18)
#define S3C64XX_SPCON_MEM1_DQS_PUD_MASK (0x3 << 16)
#define S3C64XX_SPCON_MEM1_DQS_PUD_SHIFT (16)
#define S3C64XX_SPCON_MEM1_DQS_PUD_DISABLED (0x0 << 16)
#define S3C64XX_SPCON_MEM1_DQS_PUD_DOWN (0x1 << 16)
#define S3C64XX_SPCON_MEM1_DQS_PUD_UP (0x2 << 16)
#define S3C64XX_SPCON_MEM1_D_PUD1_MASK (0x3 << 14)
#define S3C64XX_SPCON_MEM1_D_PUD1_SHIFT (14)
#define S3C64XX_SPCON_MEM1_D_PUD1_DISABLED (0x0 << 14)
#define S3C64XX_SPCON_MEM1_D_PUD1_DOWN (0x1 << 14)
#define S3C64XX_SPCON_MEM1_D_PUD1_UP (0x2 << 14)
#define S3C64XX_SPCON_MEM1_D_PUD0_MASK (0x3 << 12)
#define S3C64XX_SPCON_MEM1_D_PUD0_SHIFT (12)
#define S3C64XX_SPCON_MEM1_D_PUD0_DISABLED (0x0 << 12)
#define S3C64XX_SPCON_MEM1_D_PUD0_DOWN (0x1 << 12)
#define S3C64XX_SPCON_MEM1_D_PUD0_UP (0x2 << 12)
#define S3C64XX_SPCON_MEM0_D_PUD_MASK (0x3 << 8)
#define S3C64XX_SPCON_MEM0_D_PUD_SHIFT (8)
#define S3C64XX_SPCON_MEM0_D_PUD_DISABLED (0x0 << 8)
#define S3C64XX_SPCON_MEM0_D_PUD_DOWN (0x1 << 8)
#define S3C64XX_SPCON_MEM0_D_PUD_UP (0x2 << 8)
#define S3C64XX_SPCON_USBH_DMPD (1 << 7)
#define S3C64XX_SPCON_USBH_DPPD (1 << 6)
#define S3C64XX_SPCON_USBH_PUSW2 (1 << 5)
#define S3C64XX_SPCON_USBH_PUSW1 (1 << 4)
#define S3C64XX_SPCON_USBH_SUSPND (1 << 3)
#define S3C64XX_SPCON_LCD_SEL_MASK (0x3 << 0)
#define S3C64XX_SPCON_LCD_SEL_SHIFT (0)
#define S3C64XX_SPCON_LCD_SEL_HOST (0x0 << 0)
#define S3C64XX_SPCON_LCD_SEL_RGB (0x1 << 0)
#define S3C64XX_SPCON_LCD_SEL_606_656 (0x2 << 0)
/* External interrupt registers */
#define S3C64XX_EINT12CON S3C64XX_GPIOREG(0x200)
#define S3C64XX_EINT34CON S3C64XX_GPIOREG(0x204)
#define S3C64XX_EINT56CON S3C64XX_GPIOREG(0x208)
#define S3C64XX_EINT78CON S3C64XX_GPIOREG(0x20C)
#define S3C64XX_EINT9CON S3C64XX_GPIOREG(0x210)
#define S3C64XX_EINT12FLTCON S3C64XX_GPIOREG(0x220)
#define S3C64XX_EINT34FLTCON S3C64XX_GPIOREG(0x224)
#define S3C64XX_EINT56FLTCON S3C64XX_GPIOREG(0x228)
#define S3C64XX_EINT78FLTCON S3C64XX_GPIOREG(0x22C)
#define S3C64XX_EINT9FLTCON S3C64XX_GPIOREG(0x230)
#define S3C64XX_EINT12MASK S3C64XX_GPIOREG(0x240)
#define S3C64XX_EINT34MASK S3C64XX_GPIOREG(0x244)
#define S3C64XX_EINT56MASK S3C64XX_GPIOREG(0x248)
#define S3C64XX_EINT78MASK S3C64XX_GPIOREG(0x24C)
#define S3C64XX_EINT9MASK S3C64XX_GPIOREG(0x250)
#define S3C64XX_EINT12PEND S3C64XX_GPIOREG(0x260)
#define S3C64XX_EINT34PEND S3C64XX_GPIOREG(0x264)
#define S3C64XX_EINT56PEND S3C64XX_GPIOREG(0x268)
#define S3C64XX_EINT78PEND S3C64XX_GPIOREG(0x26C)
#define S3C64XX_EINT9PEND S3C64XX_GPIOREG(0x270)
#define S3C64XX_PRIORITY S3C64XX_GPIOREG(0x280)
#define S3C64XX_PRIORITY_ARB(x) (1 << (x))
#define S3C64XX_SERVICE S3C64XX_GPIOREG(0x284)
#define S3C64XX_SERVICEPEND S3C64XX_GPIOREG(0x288)
#define S3C64XX_EINT0CON0 S3C64XX_GPIOREG(0x900)
#define S3C64XX_EINT0CON1 S3C64XX_GPIOREG(0x904)
#define S3C64XX_EINT0FLTCON0 S3C64XX_GPIOREG(0x910)
#define S3C64XX_EINT0FLTCON1 S3C64XX_GPIOREG(0x914)
#define S3C64XX_EINT0FLTCON2 S3C64XX_GPIOREG(0x918)
#define S3C64XX_EINT0FLTCON3 S3C64XX_GPIOREG(0x91C)
#define S3C64XX_EINT0MASK S3C64XX_GPIOREG(0x920)
#define S3C64XX_EINT0PEND S3C64XX_GPIOREG(0x924)
/* GPIO sleep configuration */
#define S3C64XX_SPCONSLP S3C64XX_GPIOREG(0x880)
#define S3C64XX_SPCONSLP_TDO_PULLDOWN (1 << 14)
#define S3C64XX_SPCONSLP_CKE1INIT (1 << 5)
#define S3C64XX_SPCONSLP_RSTOUT_MASK (0x3 << 12)
#define S3C64XX_SPCONSLP_RSTOUT_OUT0 (0x0 << 12)
#define S3C64XX_SPCONSLP_RSTOUT_OUT1 (0x1 << 12)
#define S3C64XX_SPCONSLP_RSTOUT_HIZ (0x2 << 12)
#define S3C64XX_SPCONSLP_KPCOL_MASK (0x3 << 0)
#define S3C64XX_SPCONSLP_KPCOL_OUT0 (0x0 << 0)
#define S3C64XX_SPCONSLP_KPCOL_OUT1 (0x1 << 0)
#define S3C64XX_SPCONSLP_KPCOL_INP (0x2 << 0)
#define S3C64XX_SLPEN S3C64XX_GPIOREG(0x930)
#define S3C64XX_SLPEN_USE_xSLP (1 << 0)
#define S3C64XX_SLPEN_CFG_BYSLPEN (1 << 1)
#endif /* __ASM_PLAT_S3C64XX_REGS_GPIO_H */

View file

@ -0,0 +1,19 @@
/* linux/arch/arm/mach-s3c6400/include/mach/regs-irq.h
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* http://armlinux.simtec.co.uk/
* Ben Dooks <ben@simtec.co.uk>
*
* S3C64XX - IRQ register definitions
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef __ASM_ARCH_REGS_IRQ_H
#define __ASM_ARCH_REGS_IRQ_H __FILE__
#endif /* __ASM_ARCH_6400_REGS_IRQ_H */

View file

@ -0,0 +1,124 @@
/* arch/arm/plat-s3c64xx/irq-pm.c
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C64XX - Interrupt handling Power Management
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
/*
* NOTE: Code in this file is not used when booting with Device Tree support.
*/
#include <linux/kernel.h>
#include <linux/syscore_ops.h>
#include <linux/interrupt.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/irq.h>
#include <linux/io.h>
#include <linux/of.h>
#include <mach/map.h>
#include <mach/regs-gpio.h>
#include <plat/cpu.h>
#include <plat/pm.h>
/* We handled all the IRQ types in this code, to save having to make several
* small files to handle each different type separately. Having the EINT_GRP
* code here shouldn't be as much bloat as the IRQ table space needed when
* they are enabled. The added benefit is we ensure that these registers are
* in the same state as we suspended.
*/
static struct sleep_save irq_save[] = {
SAVE_ITEM(S3C64XX_PRIORITY),
SAVE_ITEM(S3C64XX_EINT0CON0),
SAVE_ITEM(S3C64XX_EINT0CON1),
SAVE_ITEM(S3C64XX_EINT0FLTCON0),
SAVE_ITEM(S3C64XX_EINT0FLTCON1),
SAVE_ITEM(S3C64XX_EINT0FLTCON2),
SAVE_ITEM(S3C64XX_EINT0FLTCON3),
SAVE_ITEM(S3C64XX_EINT0MASK),
};
static struct irq_grp_save {
u32 fltcon;
u32 con;
u32 mask;
} eint_grp_save[5];
#ifndef CONFIG_SERIAL_SAMSUNG_UARTS
#define SERIAL_SAMSUNG_UARTS 0
#else
#define SERIAL_SAMSUNG_UARTS CONFIG_SERIAL_SAMSUNG_UARTS
#endif
static u32 irq_uart_mask[SERIAL_SAMSUNG_UARTS];
static int s3c64xx_irq_pm_suspend(void)
{
struct irq_grp_save *grp = eint_grp_save;
int i;
S3C_PMDBG("%s: suspending IRQs\n", __func__);
s3c_pm_do_save(irq_save, ARRAY_SIZE(irq_save));
for (i = 0; i < SERIAL_SAMSUNG_UARTS; i++)
irq_uart_mask[i] = __raw_readl(S3C_VA_UARTx(i) + S3C64XX_UINTM);
for (i = 0; i < ARRAY_SIZE(eint_grp_save); i++, grp++) {
grp->con = __raw_readl(S3C64XX_EINT12CON + (i * 4));
grp->mask = __raw_readl(S3C64XX_EINT12MASK + (i * 4));
grp->fltcon = __raw_readl(S3C64XX_EINT12FLTCON + (i * 4));
}
return 0;
}
static void s3c64xx_irq_pm_resume(void)
{
struct irq_grp_save *grp = eint_grp_save;
int i;
S3C_PMDBG("%s: resuming IRQs\n", __func__);
s3c_pm_do_restore(irq_save, ARRAY_SIZE(irq_save));
for (i = 0; i < SERIAL_SAMSUNG_UARTS; i++)
__raw_writel(irq_uart_mask[i], S3C_VA_UARTx(i) + S3C64XX_UINTM);
for (i = 0; i < ARRAY_SIZE(eint_grp_save); i++, grp++) {
__raw_writel(grp->con, S3C64XX_EINT12CON + (i * 4));
__raw_writel(grp->mask, S3C64XX_EINT12MASK + (i * 4));
__raw_writel(grp->fltcon, S3C64XX_EINT12FLTCON + (i * 4));
}
S3C_PMDBG("%s: IRQ configuration restored\n", __func__);
}
static struct syscore_ops s3c64xx_irq_syscore_ops = {
.suspend = s3c64xx_irq_pm_suspend,
.resume = s3c64xx_irq_pm_resume,
};
static __init int s3c64xx_syscore_init(void)
{
/* Appropriate drivers (pinctrl, uart) handle this when using DT. */
if (of_have_populated_dt())
return 0;
register_syscore_ops(&s3c64xx_irq_syscore_ops);
return 0;
}
core_initcall(s3c64xx_syscore_init);

View file

@ -0,0 +1,238 @@
/* linux/arch/arm/mach-s3c64xx/mach-anw6410.c
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
* Copyright 2009 Kwangwoo Lee
* Kwangwoo Lee <kwangwoo.lee@gmail.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/interrupt.h>
#include <linux/list.h>
#include <linux/timer.h>
#include <linux/init.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/platform_device.h>
#include <linux/io.h>
#include <linux/i2c.h>
#include <linux/fb.h>
#include <linux/gpio.h>
#include <linux/delay.h>
#include <linux/dm9000.h>
#include <video/platform_lcd.h>
#include <video/samsung_fimd.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <asm/mach/irq.h>
#include <mach/hardware.h>
#include <mach/map.h>
#include <asm/irq.h>
#include <asm/mach-types.h>
#include <linux/platform_data/i2c-s3c2410.h>
#include <plat/fb.h>
#include <plat/devs.h>
#include <plat/cpu.h>
#include <mach/regs-gpio.h>
#include <mach/gpio-samsung.h>
#include <plat/samsung-time.h>
#include "common.h"
#include "regs-modem.h"
/* DM9000 */
#define ANW6410_PA_DM9000 (0x18000000)
/* A hardware buffer to control external devices is mapped at 0x30000000.
* It can not be read. So current status must be kept in anw6410_extdev_status.
*/
#define ANW6410_VA_EXTDEV S3C_ADDR(0x02000000)
#define ANW6410_PA_EXTDEV (0x30000000)
#define ANW6410_EN_DM9000 (1<<11)
#define ANW6410_EN_LCD (1<<14)
static __u32 anw6410_extdev_status;
static struct s3c2410_uartcfg anw6410_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,
.ucon = 0x3c5,
.ulcon = 0x03,
.ufcon = 0x51,
},
[1] = {
.hwport = 1,
.flags = 0,
.ucon = 0x3c5,
.ulcon = 0x03,
.ufcon = 0x51,
},
};
/* framebuffer and LCD setup. */
static void __init anw6410_lcd_mode_set(void)
{
u32 tmp;
/* set the LCD type */
tmp = __raw_readl(S3C64XX_SPCON);
tmp &= ~S3C64XX_SPCON_LCD_SEL_MASK;
tmp |= S3C64XX_SPCON_LCD_SEL_RGB;
__raw_writel(tmp, S3C64XX_SPCON);
/* remove the LCD bypass */
tmp = __raw_readl(S3C64XX_MODEM_MIFPCON);
tmp &= ~MIFPCON_LCD_BYPASS;
__raw_writel(tmp, S3C64XX_MODEM_MIFPCON);
}
/* GPF1 = LCD panel power
* GPF4 = LCD backlight control
*/
static void anw6410_lcd_power_set(struct plat_lcd_data *pd,
unsigned int power)
{
if (power) {
anw6410_extdev_status |= (ANW6410_EN_LCD << 16);
__raw_writel(anw6410_extdev_status, ANW6410_VA_EXTDEV);
gpio_direction_output(S3C64XX_GPF(1), 1);
gpio_direction_output(S3C64XX_GPF(4), 1);
} else {
anw6410_extdev_status &= ~(ANW6410_EN_LCD << 16);
__raw_writel(anw6410_extdev_status, ANW6410_VA_EXTDEV);
gpio_direction_output(S3C64XX_GPF(1), 0);
gpio_direction_output(S3C64XX_GPF(4), 0);
}
}
static struct plat_lcd_data anw6410_lcd_power_data = {
.set_power = anw6410_lcd_power_set,
};
static struct platform_device anw6410_lcd_powerdev = {
.name = "platform-lcd",
.dev.parent = &s3c_device_fb.dev,
.dev.platform_data = &anw6410_lcd_power_data,
};
static struct s3c_fb_pd_win anw6410_fb_win0 = {
.max_bpp = 32,
.default_bpp = 16,
.xres = 800,
.yres = 480,
};
static struct fb_videomode anw6410_lcd_timing = {
.left_margin = 8,
.right_margin = 13,
.upper_margin = 7,
.lower_margin = 5,
.hsync_len = 3,
.vsync_len = 1,
.xres = 800,
.yres = 480,
};
/* 405566 clocks per frame => 60Hz refresh requires 24333960Hz clock */
static struct s3c_fb_platdata anw6410_lcd_pdata __initdata = {
.setup_gpio = s3c64xx_fb_gpio_setup_24bpp,
.vtiming = &anw6410_lcd_timing,
.win[0] = &anw6410_fb_win0,
.vidcon0 = VIDCON0_VIDOUT_RGB | VIDCON0_PNRMODE_RGB,
.vidcon1 = VIDCON1_INV_HSYNC | VIDCON1_INV_VSYNC,
};
/* DM9000AEP 10/100 ethernet controller */
static void __init anw6410_dm9000_enable(void)
{
anw6410_extdev_status |= (ANW6410_EN_DM9000 << 16);
__raw_writel(anw6410_extdev_status, ANW6410_VA_EXTDEV);
}
static struct resource anw6410_dm9000_resource[] = {
[0] = DEFINE_RES_MEM(ANW6410_PA_DM9000, 4),
[1] = DEFINE_RES_MEM(ANW6410_PA_DM9000 + 4, 501),
[2] = DEFINE_RES_NAMED(IRQ_EINT(15), 1, NULL, IORESOURCE_IRQ \
| IRQF_TRIGGER_HIGH),
};
static struct dm9000_plat_data anw6410_dm9000_pdata = {
.flags = (DM9000_PLATF_16BITONLY | DM9000_PLATF_NO_EEPROM),
/* dev_addr can be set to provide hwaddr. */
};
static struct platform_device anw6410_device_eth = {
.name = "dm9000",
.id = -1,
.num_resources = ARRAY_SIZE(anw6410_dm9000_resource),
.resource = anw6410_dm9000_resource,
.dev = {
.platform_data = &anw6410_dm9000_pdata,
},
};
static struct map_desc anw6410_iodesc[] __initdata = {
{
.virtual = (unsigned long)ANW6410_VA_EXTDEV,
.pfn = __phys_to_pfn(ANW6410_PA_EXTDEV),
.length = SZ_64K,
.type = MT_DEVICE,
},
};
static struct platform_device *anw6410_devices[] __initdata = {
&s3c_device_fb,
&anw6410_lcd_powerdev,
&anw6410_device_eth,
};
static void __init anw6410_map_io(void)
{
s3c64xx_init_io(anw6410_iodesc, ARRAY_SIZE(anw6410_iodesc));
s3c64xx_set_xtal_freq(12000000);
s3c24xx_init_uarts(anw6410_uartcfgs, ARRAY_SIZE(anw6410_uartcfgs));
samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
anw6410_lcd_mode_set();
}
static void __init anw6410_machine_init(void)
{
s3c_fb_set_platdata(&anw6410_lcd_pdata);
gpio_request(S3C64XX_GPF(1), "panel power");
gpio_request(S3C64XX_GPF(4), "LCD backlight");
anw6410_dm9000_enable();
platform_add_devices(anw6410_devices, ARRAY_SIZE(anw6410_devices));
}
MACHINE_START(ANW6410, "A&W6410")
/* Maintainer: Kwangwoo Lee <kwangwoo.lee@gmail.com> */
.atag_offset = 0x100,
.init_irq = s3c6410_init_irq,
.map_io = anw6410_map_io,
.init_machine = anw6410_machine_init,
.init_time = samsung_timer_init,
.restart = s3c64xx_restart,
MACHINE_END

View file

@ -0,0 +1,404 @@
/* Speyside modules for Cragganmore - board data probing
*
* Copyright 2011 Wolfson Microelectronics plc
* Mark Brown <broonie@opensource.wolfsonmicro.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/export.h>
#include <linux/interrupt.h>
#include <linux/i2c.h>
#include <linux/spi/spi.h>
#include <linux/mfd/wm831x/irq.h>
#include <linux/mfd/wm831x/gpio.h>
#include <linux/mfd/wm8994/pdata.h>
#include <linux/mfd/arizona/pdata.h>
#include <linux/regulator/machine.h>
#include <sound/wm0010.h>
#include <sound/wm2200.h>
#include <sound/wm5100.h>
#include <sound/wm8996.h>
#include <sound/wm8962.h>
#include <sound/wm9081.h>
#include <linux/platform_data/spi-s3c64xx.h>
#include "crag6410.h"
static struct s3c64xx_spi_csinfo wm0010_spi_csinfo = {
.line = S3C64XX_GPC(3),
};
static struct wm0010_pdata wm0010_pdata = {
.gpio_reset = S3C64XX_GPN(6),
.reset_active_high = 1, /* Active high for Glenfarclas Rev 2 */
};
static struct spi_board_info wm1253_devs[] = {
[0] = {
.modalias = "wm0010",
.max_speed_hz = 26 * 1000 * 1000,
.bus_num = 0,
.chip_select = 0,
.mode = SPI_MODE_0,
.irq = S3C_EINT(4),
.controller_data = &wm0010_spi_csinfo,
.platform_data = &wm0010_pdata,
},
};
static struct spi_board_info balblair_devs[] = {
[0] = {
.modalias = "wm0010",
.max_speed_hz = 26 * 1000 * 1000,
.bus_num = 0,
.chip_select = 0,
.mode = SPI_MODE_0,
.irq = S3C_EINT(4),
.controller_data = &wm0010_spi_csinfo,
.platform_data = &wm0010_pdata,
},
};
static struct wm5100_pdata wm5100_pdata = {
.ldo_ena = S3C64XX_GPN(7),
.irq_flags = IRQF_TRIGGER_HIGH,
.gpio_base = CODEC_GPIO_BASE,
.in_mode = {
WM5100_IN_DIFF,
WM5100_IN_DIFF,
WM5100_IN_DIFF,
WM5100_IN_SE,
},
.hp_pol = CODEC_GPIO_BASE + 3,
.jack_modes = {
{ WM5100_MICDET_MICBIAS3, 0, 0 },
{ WM5100_MICDET_MICBIAS2, 1, 1 },
},
.gpio_defaults = {
0,
0,
0,
0,
0x2, /* IRQ: CMOS output */
0x3, /* CLKOUT: CMOS output */
},
};
static struct wm8996_retune_mobile_config wm8996_retune[] = {
{
.name = "Sub LPF",
.rate = 48000,
.regs = {
0x6318, 0x6300, 0x1000, 0x0000, 0x0004, 0x2000, 0xF000,
0x0000, 0x0004, 0x2000, 0xF000, 0x0000, 0x0004, 0x2000,
0xF000, 0x0000, 0x0004, 0x1000, 0x0800, 0x4000
},
},
{
.name = "Sub HPF",
.rate = 48000,
.regs = {
0x000A, 0x6300, 0x1000, 0x0000, 0x0004, 0x2000, 0xF000,
0x0000, 0x0004, 0x2000, 0xF000, 0x0000, 0x0004, 0x2000,
0xF000, 0x0000, 0x0004, 0x1000, 0x0800, 0x4000
},
},
};
static struct wm8996_pdata wm8996_pdata __initdata = {
.ldo_ena = S3C64XX_GPN(7),
.gpio_base = CODEC_GPIO_BASE,
.micdet_def = 1,
.inl_mode = WM8996_DIFFERRENTIAL_1,
.inr_mode = WM8996_DIFFERRENTIAL_1,
.irq_flags = IRQF_TRIGGER_RISING,
.gpio_default = {
0x8001, /* GPIO1 == ADCLRCLK1 */
0x8001, /* GPIO2 == ADCLRCLK2, input due to CPU */
0x0141, /* GPIO3 == HP_SEL */
0x0002, /* GPIO4 == IRQ */
0x020e, /* GPIO5 == CLKOUT */
},
.retune_mobile_cfgs = wm8996_retune,
.num_retune_mobile_cfgs = ARRAY_SIZE(wm8996_retune),
};
static struct wm8962_pdata wm8962_pdata __initdata = {
.gpio_init = {
0,
WM8962_GPIO_FN_OPCLK,
WM8962_GPIO_FN_DMICCLK,
0,
0x8000 | WM8962_GPIO_FN_DMICDAT,
WM8962_GPIO_FN_IRQ, /* Open drain mode */
},
.in4_dc_measure = true,
};
static struct wm9081_pdata wm9081_pdata __initdata = {
.irq_high = false,
.irq_cmos = false,
};
static const struct i2c_board_info wm1254_devs[] = {
{ I2C_BOARD_INFO("wm8996", 0x1a),
.platform_data = &wm8996_pdata,
.irq = GLENFARCLAS_PMIC_IRQ_BASE + WM831X_IRQ_GPIO_2,
},
{ I2C_BOARD_INFO("wm9081", 0x6c),
.platform_data = &wm9081_pdata, },
};
static const struct i2c_board_info wm1255_devs[] = {
{ I2C_BOARD_INFO("wm5100", 0x1a),
.platform_data = &wm5100_pdata,
.irq = GLENFARCLAS_PMIC_IRQ_BASE + WM831X_IRQ_GPIO_2,
},
{ I2C_BOARD_INFO("wm9081", 0x6c),
.platform_data = &wm9081_pdata, },
};
static const struct i2c_board_info wm1259_devs[] = {
{ I2C_BOARD_INFO("wm8962", 0x1a),
.platform_data = &wm8962_pdata,
.irq = GLENFARCLAS_PMIC_IRQ_BASE + WM831X_IRQ_GPIO_2,
},
};
static struct regulator_init_data wm8994_ldo1 = {
.supply_regulator = "WALLVDD",
};
static struct regulator_init_data wm8994_ldo2 = {
.supply_regulator = "WALLVDD",
};
static struct wm8994_pdata wm8994_pdata = {
.gpio_base = CODEC_GPIO_BASE,
.micb2_delay = 150,
.gpio_defaults = {
0x3, /* IRQ out, active high, CMOS */
},
.ldo = {
{ .enable = S3C64XX_GPN(6), .init_data = &wm8994_ldo1, },
{ .enable = S3C64XX_GPN(4), .init_data = &wm8994_ldo2, },
},
};
static const struct i2c_board_info wm1277_devs[] = {
{ I2C_BOARD_INFO("wm8958", 0x1a), /* WM8958 is the superset */
.platform_data = &wm8994_pdata,
.irq = GLENFARCLAS_PMIC_IRQ_BASE + WM831X_IRQ_GPIO_2,
},
};
static struct arizona_pdata wm5102_reva_pdata = {
.ldoena = S3C64XX_GPN(7),
.gpio_base = CODEC_GPIO_BASE,
.irq_flags = IRQF_TRIGGER_HIGH,
.micd_pol_gpio = CODEC_GPIO_BASE + 4,
.micd_rate = 6,
.gpio_defaults = {
[2] = 0x10000, /* AIF3TXLRCLK */
[3] = 0x4, /* OPCLK */
},
};
static struct s3c64xx_spi_csinfo codec_spi_csinfo = {
.line = S3C64XX_GPN(5),
};
static struct spi_board_info wm5102_reva_spi_devs[] = {
[0] = {
.modalias = "wm5102",
.max_speed_hz = 10 * 1000 * 1000,
.bus_num = 0,
.chip_select = 1,
.mode = SPI_MODE_0,
.irq = GLENFARCLAS_PMIC_IRQ_BASE +
WM831X_IRQ_GPIO_2,
.controller_data = &codec_spi_csinfo,
.platform_data = &wm5102_reva_pdata,
},
};
static struct arizona_pdata wm5102_pdata = {
.ldoena = S3C64XX_GPN(7),
.gpio_base = CODEC_GPIO_BASE,
.irq_flags = IRQF_TRIGGER_HIGH,
.micd_pol_gpio = CODEC_GPIO_BASE + 2,
.gpio_defaults = {
[2] = 0x10000, /* AIF3TXLRCLK */
[3] = 0x4, /* OPCLK */
},
};
static struct spi_board_info wm5102_spi_devs[] = {
[0] = {
.modalias = "wm5102",
.max_speed_hz = 10 * 1000 * 1000,
.bus_num = 0,
.chip_select = 1,
.mode = SPI_MODE_0,
.irq = GLENFARCLAS_PMIC_IRQ_BASE +
WM831X_IRQ_GPIO_2,
.controller_data = &codec_spi_csinfo,
.platform_data = &wm5102_pdata,
},
};
static struct spi_board_info wm5110_spi_devs[] = {
[0] = {
.modalias = "wm5110",
.max_speed_hz = 10 * 1000 * 1000,
.bus_num = 0,
.chip_select = 1,
.mode = SPI_MODE_0,
.irq = GLENFARCLAS_PMIC_IRQ_BASE +
WM831X_IRQ_GPIO_2,
.controller_data = &codec_spi_csinfo,
.platform_data = &wm5102_reva_pdata,
},
};
static const struct i2c_board_info wm6230_i2c_devs[] = {
{ I2C_BOARD_INFO("wm9081", 0x6c),
.platform_data = &wm9081_pdata, },
};
static struct wm2200_pdata wm2200_pdata = {
.ldo_ena = S3C64XX_GPN(7),
.gpio_defaults = {
[2] = 0x0005, /* GPIO3 24.576MHz output clock */
},
};
static const struct i2c_board_info wm2200_i2c[] = {
{ I2C_BOARD_INFO("wm2200", 0x3a),
.platform_data = &wm2200_pdata, },
};
static const struct {
u8 id;
u8 rev;
const char *name;
const struct i2c_board_info *i2c_devs;
int num_i2c_devs;
const struct spi_board_info *spi_devs;
int num_spi_devs;
} gf_mods[] = {
{ .id = 0x01, .rev = 0xff, .name = "1250-EV1 Springbank" },
{ .id = 0x02, .rev = 0xff, .name = "1251-EV1 Jura" },
{ .id = 0x03, .rev = 0xff, .name = "1252-EV1 Glenlivet" },
{ .id = 0x06, .rev = 0xff, .name = "WM8997-6721-CS96-EV1 Lapraoig" },
{ .id = 0x07, .rev = 0xff, .name = "WM5110-6271 Deanston",
.spi_devs = wm5110_spi_devs,
.num_spi_devs = ARRAY_SIZE(wm5110_spi_devs) },
{ .id = 0x08, .rev = 0xff, .name = "WM8903-6102 Tamdhu" },
{ .id = 0x09, .rev = 0xff, .name = "WM1811A-6305 Adelphi" },
{ .id = 0x0a, .rev = 0xff, .name = "WM8996-6272 Blackadder" },
{ .id = 0x0b, .rev = 0xff, .name = "WM8994-6235 Benromach" },
{ .id = 0x11, .rev = 0xff, .name = "6249-EV2 Glenfarclas", },
{ .id = 0x14, .rev = 0xff, .name = "6271-EV1 Lochnagar" },
{ .id = 0x15, .rev = 0xff, .name = "6320-EV1 Bells",
.i2c_devs = wm6230_i2c_devs,
.num_i2c_devs = ARRAY_SIZE(wm6230_i2c_devs) },
{ .id = 0x21, .rev = 0xff, .name = "1275-EV1 Mortlach" },
{ .id = 0x25, .rev = 0xff, .name = "1274-EV1 Glencadam" },
{ .id = 0x31, .rev = 0xff, .name = "1253-EV1 Tomatin",
.spi_devs = wm1253_devs, .num_spi_devs = ARRAY_SIZE(wm1253_devs) },
{ .id = 0x32, .rev = 0xff, .name = "XXXX-EV1 Caol Illa" },
{ .id = 0x33, .rev = 0xff, .name = "XXXX-EV1 Oban" },
{ .id = 0x34, .rev = 0xff, .name = "WM0010-6320-CS42 Balblair",
.spi_devs = balblair_devs,
.num_spi_devs = ARRAY_SIZE(balblair_devs) },
{ .id = 0x39, .rev = 0xff, .name = "1254-EV1 Dallas Dhu",
.i2c_devs = wm1254_devs, .num_i2c_devs = ARRAY_SIZE(wm1254_devs) },
{ .id = 0x3a, .rev = 0xff, .name = "1259-EV1 Tobermory",
.i2c_devs = wm1259_devs, .num_i2c_devs = ARRAY_SIZE(wm1259_devs) },
{ .id = 0x3b, .rev = 0xff, .name = "1255-EV1 Kilchoman",
.i2c_devs = wm1255_devs, .num_i2c_devs = ARRAY_SIZE(wm1255_devs) },
{ .id = 0x3c, .rev = 0xff, .name = "1273-EV1 Longmorn" },
{ .id = 0x3d, .rev = 0xff, .name = "1277-EV1 Littlemill",
.i2c_devs = wm1277_devs, .num_i2c_devs = ARRAY_SIZE(wm1277_devs) },
{ .id = 0x3e, .rev = 0, .name = "WM5102-6271-EV1-CS127 Amrut",
.spi_devs = wm5102_reva_spi_devs,
.num_spi_devs = ARRAY_SIZE(wm5102_reva_spi_devs) },
{ .id = 0x3e, .rev = -1, .name = "WM5102-6271-EV1-CS127 Amrut",
.spi_devs = wm5102_spi_devs,
.num_spi_devs = ARRAY_SIZE(wm5102_spi_devs) },
{ .id = 0x3f, .rev = -1, .name = "WM2200-6271-CS90-M-REV1",
.i2c_devs = wm2200_i2c, .num_i2c_devs = ARRAY_SIZE(wm2200_i2c) },
};
static int wlf_gf_module_probe(struct i2c_client *i2c,
const struct i2c_device_id *i2c_id)
{
int ret, i, j, id, rev;
ret = i2c_smbus_read_byte_data(i2c, 0);
if (ret < 0) {
dev_err(&i2c->dev, "Failed to read ID: %d\n", ret);
return ret;
}
id = (ret & 0xfe) >> 2;
rev = ret & 0x3;
for (i = 0; i < ARRAY_SIZE(gf_mods); i++)
if (id == gf_mods[i].id && (gf_mods[i].rev == 0xff ||
rev == gf_mods[i].rev))
break;
if (i < ARRAY_SIZE(gf_mods)) {
dev_info(&i2c->dev, "%s revision %d\n",
gf_mods[i].name, rev + 1);
for (j = 0; j < gf_mods[i].num_i2c_devs; j++) {
if (!i2c_new_device(i2c->adapter,
&(gf_mods[i].i2c_devs[j])))
dev_err(&i2c->dev,
"Failed to register dev: %d\n", ret);
}
spi_register_board_info(gf_mods[i].spi_devs,
gf_mods[i].num_spi_devs);
} else {
dev_warn(&i2c->dev, "Unknown module ID 0x%x revision %d\n",
id, rev + 1);
}
return 0;
}
static const struct i2c_device_id wlf_gf_module_id[] = {
{ "wlf-gf-module", 0 },
{ }
};
static struct i2c_driver wlf_gf_module_driver = {
.driver = {
.name = "wlf-gf-module",
.owner = THIS_MODULE,
},
.probe = wlf_gf_module_probe,
.id_table = wlf_gf_module_id,
};
static int __init wlf_gf_module_register(void)
{
return i2c_add_driver(&wlf_gf_module_driver);
}
device_initcall(wlf_gf_module_register);

View file

@ -0,0 +1,863 @@
/* linux/arch/arm/mach-s3c64xx/mach-crag6410.c
*
* Copyright 2011 Wolfson Microelectronics plc
* Mark Brown <broonie@opensource.wolfsonmicro.com>
*
* Copyright 2011 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/kernel.h>
#include <linux/list.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/platform_device.h>
#include <linux/fb.h>
#include <linux/io.h>
#include <linux/init.h>
#include <linux/gpio.h>
#include <linux/leds.h>
#include <linux/delay.h>
#include <linux/mmc/host.h>
#include <linux/regulator/machine.h>
#include <linux/regulator/fixed.h>
#include <linux/pwm_backlight.h>
#include <linux/dm9000.h>
#include <linux/gpio_keys.h>
#include <linux/basic_mmio_gpio.h>
#include <linux/spi/spi.h>
#include <linux/platform_data/pca953x.h>
#include <linux/platform_data/s3c-hsotg.h>
#include <video/platform_lcd.h>
#include <linux/mfd/wm831x/core.h>
#include <linux/mfd/wm831x/pdata.h>
#include <linux/mfd/wm831x/irq.h>
#include <linux/mfd/wm831x/gpio.h>
#include <sound/wm1250-ev1.h>
#include <asm/mach/arch.h>
#include <asm/mach-types.h>
#include <video/samsung_fimd.h>
#include <mach/hardware.h>
#include <mach/map.h>
#include <mach/regs-gpio.h>
#include <mach/gpio-samsung.h>
#include <plat/fb.h>
#include <plat/sdhci.h>
#include <plat/gpio-cfg.h>
#include <linux/platform_data/spi-s3c64xx.h>
#include <plat/keypad.h>
#include <plat/devs.h>
#include <plat/cpu.h>
#include <plat/adc.h>
#include <linux/platform_data/i2c-s3c2410.h>
#include <plat/pm.h>
#include <plat/samsung-time.h>
#include "common.h"
#include "crag6410.h"
#include "regs-gpio-memport.h"
#include "regs-modem.h"
#include "regs-sys.h"
/* serial port setup */
#define UCON (S3C2410_UCON_DEFAULT | S3C2410_UCON_UCLK)
#define ULCON (S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB)
#define UFCON (S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE)
static struct s3c2410_uartcfg crag6410_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[1] = {
.hwport = 1,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[2] = {
.hwport = 2,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[3] = {
.hwport = 3,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
};
static struct platform_pwm_backlight_data crag6410_backlight_data = {
.pwm_id = 0,
.max_brightness = 1000,
.dft_brightness = 600,
.pwm_period_ns = 100000, /* about 1kHz */
.enable_gpio = -1,
};
static struct platform_device crag6410_backlight_device = {
.name = "pwm-backlight",
.id = -1,
.dev = {
.parent = &samsung_device_pwm.dev,
.platform_data = &crag6410_backlight_data,
},
};
static void crag6410_lcd_power_set(struct plat_lcd_data *pd, unsigned int power)
{
pr_debug("%s: setting power %d\n", __func__, power);
if (power) {
gpio_set_value(S3C64XX_GPB(0), 1);
msleep(1);
s3c_gpio_cfgpin(S3C64XX_GPF(14), S3C_GPIO_SFN(2));
} else {
gpio_direction_output(S3C64XX_GPF(14), 0);
gpio_set_value(S3C64XX_GPB(0), 0);
}
}
static struct platform_device crag6410_lcd_powerdev = {
.name = "platform-lcd",
.id = -1,
.dev.parent = &s3c_device_fb.dev,
.dev.platform_data = &(struct plat_lcd_data) {
.set_power = crag6410_lcd_power_set,
},
};
/* 640x480 URT */
static struct s3c_fb_pd_win crag6410_fb_win0 = {
.max_bpp = 32,
.default_bpp = 16,
.xres = 640,
.yres = 480,
.virtual_y = 480 * 2,
.virtual_x = 640,
};
static struct fb_videomode crag6410_lcd_timing = {
.left_margin = 150,
.right_margin = 80,
.upper_margin = 40,
.lower_margin = 5,
.hsync_len = 40,
.vsync_len = 5,
.xres = 640,
.yres = 480,
};
/* 405566 clocks per frame => 60Hz refresh requires 24333960Hz clock */
static struct s3c_fb_platdata crag6410_lcd_pdata = {
.setup_gpio = s3c64xx_fb_gpio_setup_24bpp,
.vtiming = &crag6410_lcd_timing,
.win[0] = &crag6410_fb_win0,
.vidcon0 = VIDCON0_VIDOUT_RGB | VIDCON0_PNRMODE_RGB,
.vidcon1 = VIDCON1_INV_HSYNC | VIDCON1_INV_VSYNC,
};
/* 2x6 keypad */
static uint32_t crag6410_keymap[] = {
/* KEY(row, col, keycode) */
KEY(0, 0, KEY_VOLUMEUP),
KEY(0, 1, KEY_HOME),
KEY(0, 2, KEY_VOLUMEDOWN),
KEY(0, 3, KEY_HELP),
KEY(0, 4, KEY_MENU),
KEY(0, 5, KEY_MEDIA),
KEY(1, 0, 232),
KEY(1, 1, KEY_DOWN),
KEY(1, 2, KEY_LEFT),
KEY(1, 3, KEY_UP),
KEY(1, 4, KEY_RIGHT),
KEY(1, 5, KEY_CAMERA),
};
static struct matrix_keymap_data crag6410_keymap_data = {
.keymap = crag6410_keymap,
.keymap_size = ARRAY_SIZE(crag6410_keymap),
};
static struct samsung_keypad_platdata crag6410_keypad_data = {
.keymap_data = &crag6410_keymap_data,
.rows = 2,
.cols = 6,
};
static struct gpio_keys_button crag6410_gpio_keys[] = {
[0] = {
.code = KEY_SUSPEND,
.gpio = S3C64XX_GPL(10), /* EINT 18 */
.type = EV_KEY,
.wakeup = 1,
.active_low = 1,
},
[1] = {
.code = SW_FRONT_PROXIMITY,
.gpio = S3C64XX_GPN(11), /* EINT 11 */
.type = EV_SW,
},
};
static struct gpio_keys_platform_data crag6410_gpio_keydata = {
.buttons = crag6410_gpio_keys,
.nbuttons = ARRAY_SIZE(crag6410_gpio_keys),
};
static struct platform_device crag6410_gpio_keydev = {
.name = "gpio-keys",
.id = 0,
.dev.platform_data = &crag6410_gpio_keydata,
};
static struct resource crag6410_dm9k_resource[] = {
[0] = DEFINE_RES_MEM(S3C64XX_PA_XM0CSN5, 2),
[1] = DEFINE_RES_MEM(S3C64XX_PA_XM0CSN5 + (1 << 8), 2),
[2] = DEFINE_RES_NAMED(S3C_EINT(17), 1, NULL, IORESOURCE_IRQ \
| IORESOURCE_IRQ_HIGHLEVEL),
};
static struct dm9000_plat_data mini6410_dm9k_pdata = {
.flags = DM9000_PLATF_16BITONLY,
};
static struct platform_device crag6410_dm9k_device = {
.name = "dm9000",
.id = -1,
.num_resources = ARRAY_SIZE(crag6410_dm9k_resource),
.resource = crag6410_dm9k_resource,
.dev.platform_data = &mini6410_dm9k_pdata,
};
static struct resource crag6410_mmgpio_resource[] = {
[0] = DEFINE_RES_MEM_NAMED(S3C64XX_PA_XM0CSN4, 1, "dat"),
};
static struct platform_device crag6410_mmgpio = {
.name = "basic-mmio-gpio",
.id = -1,
.resource = crag6410_mmgpio_resource,
.num_resources = ARRAY_SIZE(crag6410_mmgpio_resource),
.dev.platform_data = &(struct bgpio_pdata) {
.base = MMGPIO_GPIO_BASE,
},
};
static struct platform_device speyside_device = {
.name = "speyside",
.id = -1,
};
static struct platform_device lowland_device = {
.name = "lowland",
.id = -1,
};
static struct platform_device tobermory_device = {
.name = "tobermory",
.id = -1,
};
static struct platform_device littlemill_device = {
.name = "littlemill",
.id = -1,
};
static struct platform_device bells_wm2200_device = {
.name = "bells",
.id = 0,
};
static struct platform_device bells_wm5102_device = {
.name = "bells",
.id = 1,
};
static struct platform_device bells_wm5110_device = {
.name = "bells",
.id = 2,
};
static struct regulator_consumer_supply wallvdd_consumers[] = {
REGULATOR_SUPPLY("SPKVDD", "1-001a"),
REGULATOR_SUPPLY("SPKVDD1", "1-001a"),
REGULATOR_SUPPLY("SPKVDD2", "1-001a"),
REGULATOR_SUPPLY("SPKVDDL", "1-001a"),
REGULATOR_SUPPLY("SPKVDDR", "1-001a"),
REGULATOR_SUPPLY("SPKVDDL", "spi0.1"),
REGULATOR_SUPPLY("SPKVDDR", "spi0.1"),
REGULATOR_SUPPLY("DC1VDD", "0-0034"),
REGULATOR_SUPPLY("DC2VDD", "0-0034"),
REGULATOR_SUPPLY("DC3VDD", "0-0034"),
REGULATOR_SUPPLY("LDO1VDD", "0-0034"),
REGULATOR_SUPPLY("LDO2VDD", "0-0034"),
REGULATOR_SUPPLY("LDO4VDD", "0-0034"),
REGULATOR_SUPPLY("LDO5VDD", "0-0034"),
REGULATOR_SUPPLY("LDO6VDD", "0-0034"),
REGULATOR_SUPPLY("LDO7VDD", "0-0034"),
REGULATOR_SUPPLY("LDO8VDD", "0-0034"),
REGULATOR_SUPPLY("LDO9VDD", "0-0034"),
REGULATOR_SUPPLY("LDO10VDD", "0-0034"),
REGULATOR_SUPPLY("LDO11VDD", "0-0034"),
REGULATOR_SUPPLY("DC1VDD", "1-0034"),
REGULATOR_SUPPLY("DC2VDD", "1-0034"),
REGULATOR_SUPPLY("DC3VDD", "1-0034"),
REGULATOR_SUPPLY("LDO1VDD", "1-0034"),
REGULATOR_SUPPLY("LDO2VDD", "1-0034"),
REGULATOR_SUPPLY("LDO4VDD", "1-0034"),
REGULATOR_SUPPLY("LDO5VDD", "1-0034"),
REGULATOR_SUPPLY("LDO6VDD", "1-0034"),
REGULATOR_SUPPLY("LDO7VDD", "1-0034"),
REGULATOR_SUPPLY("LDO8VDD", "1-0034"),
REGULATOR_SUPPLY("LDO9VDD", "1-0034"),
REGULATOR_SUPPLY("LDO10VDD", "1-0034"),
REGULATOR_SUPPLY("LDO11VDD", "1-0034"),
};
static struct regulator_init_data wallvdd_data = {
.constraints = {
.always_on = 1,
},
.num_consumer_supplies = ARRAY_SIZE(wallvdd_consumers),
.consumer_supplies = wallvdd_consumers,
};
static struct fixed_voltage_config wallvdd_pdata = {
.supply_name = "WALLVDD",
.microvolts = 5000000,
.init_data = &wallvdd_data,
.gpio = -EINVAL,
};
static struct platform_device wallvdd_device = {
.name = "reg-fixed-voltage",
.id = -1,
.dev = {
.platform_data = &wallvdd_pdata,
},
};
static struct platform_device *crag6410_devices[] __initdata = {
&s3c_device_hsmmc0,
&s3c_device_hsmmc2,
&s3c_device_i2c0,
&s3c_device_i2c1,
&s3c_device_fb,
&s3c_device_ohci,
&s3c_device_usb_hsotg,
&samsung_device_pwm,
&s3c64xx_device_iis0,
&s3c64xx_device_iis1,
&samsung_device_keypad,
&crag6410_gpio_keydev,
&crag6410_dm9k_device,
&s3c64xx_device_spi0,
&crag6410_mmgpio,
&crag6410_lcd_powerdev,
&crag6410_backlight_device,
&speyside_device,
&tobermory_device,
&littlemill_device,
&lowland_device,
&bells_wm2200_device,
&bells_wm5102_device,
&bells_wm5110_device,
&wallvdd_device,
};
static struct pca953x_platform_data crag6410_pca_data = {
.gpio_base = PCA935X_GPIO_BASE,
.irq_base = -1,
};
/* VDDARM is controlled by DVS1 connected to GPK(0) */
static struct wm831x_buckv_pdata vddarm_pdata = {
.dvs_control_src = 1,
.dvs_gpio = S3C64XX_GPK(0),
};
static struct regulator_consumer_supply vddarm_consumers[] = {
REGULATOR_SUPPLY("vddarm", NULL),
};
static struct regulator_init_data vddarm = {
.constraints = {
.name = "VDDARM",
.min_uV = 1000000,
.max_uV = 1300000,
.always_on = 1,
.valid_ops_mask = REGULATOR_CHANGE_VOLTAGE,
},
.num_consumer_supplies = ARRAY_SIZE(vddarm_consumers),
.consumer_supplies = vddarm_consumers,
.supply_regulator = "WALLVDD",
.driver_data = &vddarm_pdata,
};
static struct regulator_consumer_supply vddint_consumers[] = {
REGULATOR_SUPPLY("vddint", NULL),
};
static struct regulator_init_data vddint = {
.constraints = {
.name = "VDDINT",
.min_uV = 1000000,
.max_uV = 1200000,
.always_on = 1,
.valid_ops_mask = REGULATOR_CHANGE_VOLTAGE,
},
.num_consumer_supplies = ARRAY_SIZE(vddint_consumers),
.consumer_supplies = vddint_consumers,
.supply_regulator = "WALLVDD",
};
static struct regulator_init_data vddmem = {
.constraints = {
.name = "VDDMEM",
.always_on = 1,
},
};
static struct regulator_init_data vddsys = {
.constraints = {
.name = "VDDSYS,VDDEXT,VDDPCM,VDDSS",
.always_on = 1,
},
};
static struct regulator_consumer_supply vddmmc_consumers[] = {
REGULATOR_SUPPLY("vmmc", "s3c-sdhci.0"),
REGULATOR_SUPPLY("vmmc", "s3c-sdhci.1"),
REGULATOR_SUPPLY("vmmc", "s3c-sdhci.2"),
};
static struct regulator_init_data vddmmc = {
.constraints = {
.name = "VDDMMC,UH",
.always_on = 1,
},
.num_consumer_supplies = ARRAY_SIZE(vddmmc_consumers),
.consumer_supplies = vddmmc_consumers,
.supply_regulator = "WALLVDD",
};
static struct regulator_init_data vddotgi = {
.constraints = {
.name = "VDDOTGi",
.always_on = 1,
},
.supply_regulator = "WALLVDD",
};
static struct regulator_init_data vddotg = {
.constraints = {
.name = "VDDOTG",
.always_on = 1,
},
.supply_regulator = "WALLVDD",
};
static struct regulator_init_data vddhi = {
.constraints = {
.name = "VDDHI",
.always_on = 1,
},
.supply_regulator = "WALLVDD",
};
static struct regulator_init_data vddadc = {
.constraints = {
.name = "VDDADC,VDDDAC",
.always_on = 1,
},
.supply_regulator = "WALLVDD",
};
static struct regulator_init_data vddmem0 = {
.constraints = {
.name = "VDDMEM0",
.always_on = 1,
},
.supply_regulator = "WALLVDD",
};
static struct regulator_init_data vddpll = {
.constraints = {
.name = "VDDPLL",
.always_on = 1,
},
.supply_regulator = "WALLVDD",
};
static struct regulator_init_data vddlcd = {
.constraints = {
.name = "VDDLCD",
.always_on = 1,
},
.supply_regulator = "WALLVDD",
};
static struct regulator_init_data vddalive = {
.constraints = {
.name = "VDDALIVE",
.always_on = 1,
},
.supply_regulator = "WALLVDD",
};
static struct wm831x_backup_pdata banff_backup_pdata = {
.charger_enable = 1,
.vlim = 2500, /* mV */
.ilim = 200, /* uA */
};
static struct wm831x_status_pdata banff_red_led = {
.name = "banff:red:",
.default_src = WM831X_STATUS_MANUAL,
};
static struct wm831x_status_pdata banff_green_led = {
.name = "banff:green:",
.default_src = WM831X_STATUS_MANUAL,
};
static struct wm831x_touch_pdata touch_pdata = {
.data_irq = S3C_EINT(26),
.pd_irq = S3C_EINT(27),
};
static struct wm831x_pdata crag_pmic_pdata = {
.wm831x_num = 1,
.irq_base = BANFF_PMIC_IRQ_BASE,
.gpio_base = BANFF_PMIC_GPIO_BASE,
.soft_shutdown = true,
.backup = &banff_backup_pdata,
.gpio_defaults = {
/* GPIO5: DVS1_REQ - CMOS, DBVDD, active high */
[4] = WM831X_GPN_DIR | WM831X_GPN_POL | WM831X_GPN_ENA | 0x8,
/* GPIO11: Touchscreen data - CMOS, DBVDD, active high*/
[10] = WM831X_GPN_POL | WM831X_GPN_ENA | 0x6,
/* GPIO12: Touchscreen pen down - CMOS, DBVDD, active high*/
[11] = WM831X_GPN_POL | WM831X_GPN_ENA | 0x7,
},
.dcdc = {
&vddarm, /* DCDC1 */
&vddint, /* DCDC2 */
&vddmem, /* DCDC3 */
},
.ldo = {
&vddsys, /* LDO1 */
&vddmmc, /* LDO2 */
NULL, /* LDO3 */
&vddotgi, /* LDO4 */
&vddotg, /* LDO5 */
&vddhi, /* LDO6 */
&vddadc, /* LDO7 */
&vddmem0, /* LDO8 */
&vddpll, /* LDO9 */
&vddlcd, /* LDO10 */
&vddalive, /* LDO11 */
},
.status = {
&banff_green_led,
&banff_red_led,
},
.touch = &touch_pdata,
};
static struct i2c_board_info i2c_devs0[] = {
{ I2C_BOARD_INFO("24c08", 0x50), },
{ I2C_BOARD_INFO("tca6408", 0x20),
.platform_data = &crag6410_pca_data,
},
{ I2C_BOARD_INFO("wm8312", 0x34),
.platform_data = &crag_pmic_pdata,
.irq = S3C_EINT(23),
},
};
static struct s3c2410_platform_i2c i2c0_pdata = {
.frequency = 400000,
};
static struct regulator_consumer_supply pvdd_1v2_consumers[] = {
REGULATOR_SUPPLY("DCVDD", "spi0.0"),
REGULATOR_SUPPLY("AVDD", "spi0.0"),
REGULATOR_SUPPLY("AVDD", "spi0.1"),
};
static struct regulator_init_data pvdd_1v2 = {
.constraints = {
.name = "PVDD_1V2",
.valid_ops_mask = REGULATOR_CHANGE_STATUS,
},
.consumer_supplies = pvdd_1v2_consumers,
.num_consumer_supplies = ARRAY_SIZE(pvdd_1v2_consumers),
};
static struct regulator_consumer_supply pvdd_1v8_consumers[] = {
REGULATOR_SUPPLY("LDOVDD", "1-001a"),
REGULATOR_SUPPLY("PLLVDD", "1-001a"),
REGULATOR_SUPPLY("DBVDD", "1-001a"),
REGULATOR_SUPPLY("DBVDD1", "1-001a"),
REGULATOR_SUPPLY("DBVDD2", "1-001a"),
REGULATOR_SUPPLY("DBVDD3", "1-001a"),
REGULATOR_SUPPLY("CPVDD", "1-001a"),
REGULATOR_SUPPLY("AVDD2", "1-001a"),
REGULATOR_SUPPLY("DCVDD", "1-001a"),
REGULATOR_SUPPLY("AVDD", "1-001a"),
REGULATOR_SUPPLY("DBVDD", "spi0.0"),
REGULATOR_SUPPLY("DBVDD", "1-003a"),
REGULATOR_SUPPLY("LDOVDD", "1-003a"),
REGULATOR_SUPPLY("CPVDD", "1-003a"),
REGULATOR_SUPPLY("AVDD", "1-003a"),
REGULATOR_SUPPLY("DBVDD1", "spi0.1"),
REGULATOR_SUPPLY("DBVDD2", "spi0.1"),
REGULATOR_SUPPLY("DBVDD3", "spi0.1"),
REGULATOR_SUPPLY("LDOVDD", "spi0.1"),
REGULATOR_SUPPLY("CPVDD", "spi0.1"),
};
static struct regulator_init_data pvdd_1v8 = {
.constraints = {
.name = "PVDD_1V8",
.always_on = 1,
},
.consumer_supplies = pvdd_1v8_consumers,
.num_consumer_supplies = ARRAY_SIZE(pvdd_1v8_consumers),
};
static struct regulator_consumer_supply pvdd_3v3_consumers[] = {
REGULATOR_SUPPLY("MICVDD", "1-001a"),
REGULATOR_SUPPLY("AVDD1", "1-001a"),
};
static struct regulator_init_data pvdd_3v3 = {
.constraints = {
.name = "PVDD_3V3",
.always_on = 1,
},
.consumer_supplies = pvdd_3v3_consumers,
.num_consumer_supplies = ARRAY_SIZE(pvdd_3v3_consumers),
};
static struct wm831x_pdata glenfarclas_pmic_pdata = {
.wm831x_num = 2,
.irq_base = GLENFARCLAS_PMIC_IRQ_BASE,
.gpio_base = GLENFARCLAS_PMIC_GPIO_BASE,
.soft_shutdown = true,
.gpio_defaults = {
/* GPIO1-3: IRQ inputs, rising edge triggered, CMOS */
[0] = WM831X_GPN_DIR | WM831X_GPN_POL | WM831X_GPN_ENA,
[1] = WM831X_GPN_DIR | WM831X_GPN_POL | WM831X_GPN_ENA,
[2] = WM831X_GPN_DIR | WM831X_GPN_POL | WM831X_GPN_ENA,
},
.dcdc = {
&pvdd_1v2, /* DCDC1 */
&pvdd_1v8, /* DCDC2 */
&pvdd_3v3, /* DCDC3 */
},
.disable_touch = true,
};
static struct wm1250_ev1_pdata wm1250_ev1_pdata = {
.gpios = {
[WM1250_EV1_GPIO_CLK_ENA] = S3C64XX_GPN(12),
[WM1250_EV1_GPIO_CLK_SEL0] = S3C64XX_GPL(12),
[WM1250_EV1_GPIO_CLK_SEL1] = S3C64XX_GPL(13),
[WM1250_EV1_GPIO_OSR] = S3C64XX_GPL(14),
[WM1250_EV1_GPIO_MASTER] = S3C64XX_GPL(8),
},
};
static struct i2c_board_info i2c_devs1[] = {
{ I2C_BOARD_INFO("wm8311", 0x34),
.irq = S3C_EINT(0),
.platform_data = &glenfarclas_pmic_pdata },
{ I2C_BOARD_INFO("wlf-gf-module", 0x20) },
{ I2C_BOARD_INFO("wlf-gf-module", 0x22) },
{ I2C_BOARD_INFO("wlf-gf-module", 0x24) },
{ I2C_BOARD_INFO("wlf-gf-module", 0x25) },
{ I2C_BOARD_INFO("wlf-gf-module", 0x26) },
{ I2C_BOARD_INFO("wm1250-ev1", 0x27),
.platform_data = &wm1250_ev1_pdata },
};
static struct s3c2410_platform_i2c i2c1_pdata = {
.frequency = 400000,
.bus_num = 1,
};
static void __init crag6410_map_io(void)
{
s3c64xx_init_io(NULL, 0);
s3c64xx_set_xtal_freq(12000000);
s3c24xx_init_uarts(crag6410_uartcfgs, ARRAY_SIZE(crag6410_uartcfgs));
samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
/* LCD type and Bypass set by bootloader */
}
static struct s3c_sdhci_platdata crag6410_hsmmc2_pdata = {
.max_width = 4,
.cd_type = S3C_SDHCI_CD_PERMANENT,
.host_caps = MMC_CAP_POWER_OFF_CARD,
};
static void crag6410_cfg_sdhci0(struct platform_device *dev, int width)
{
/* Set all the necessary GPG pins to special-function 2 */
s3c_gpio_cfgrange_nopull(S3C64XX_GPG(0), 2 + width, S3C_GPIO_SFN(2));
/* force card-detected for prototype 0 */
s3c_gpio_setpull(S3C64XX_GPG(6), S3C_GPIO_PULL_DOWN);
}
static struct s3c_sdhci_platdata crag6410_hsmmc0_pdata = {
.max_width = 4,
.cd_type = S3C_SDHCI_CD_INTERNAL,
.cfg_gpio = crag6410_cfg_sdhci0,
.host_caps = MMC_CAP_POWER_OFF_CARD,
};
static const struct gpio_led gpio_leds[] = {
{
.name = "d13:green:",
.gpio = MMGPIO_GPIO_BASE + 0,
.default_state = LEDS_GPIO_DEFSTATE_ON,
},
{
.name = "d14:green:",
.gpio = MMGPIO_GPIO_BASE + 1,
.default_state = LEDS_GPIO_DEFSTATE_ON,
},
{
.name = "d15:green:",
.gpio = MMGPIO_GPIO_BASE + 2,
.default_state = LEDS_GPIO_DEFSTATE_ON,
},
{
.name = "d16:green:",
.gpio = MMGPIO_GPIO_BASE + 3,
.default_state = LEDS_GPIO_DEFSTATE_ON,
},
{
.name = "d17:green:",
.gpio = MMGPIO_GPIO_BASE + 4,
.default_state = LEDS_GPIO_DEFSTATE_ON,
},
{
.name = "d18:green:",
.gpio = MMGPIO_GPIO_BASE + 5,
.default_state = LEDS_GPIO_DEFSTATE_ON,
},
{
.name = "d19:green:",
.gpio = MMGPIO_GPIO_BASE + 6,
.default_state = LEDS_GPIO_DEFSTATE_ON,
},
{
.name = "d20:green:",
.gpio = MMGPIO_GPIO_BASE + 7,
.default_state = LEDS_GPIO_DEFSTATE_ON,
},
};
static const struct gpio_led_platform_data gpio_leds_pdata = {
.leds = gpio_leds,
.num_leds = ARRAY_SIZE(gpio_leds),
};
static struct s3c_hsotg_plat crag6410_hsotg_pdata;
static void __init crag6410_machine_init(void)
{
/* Open drain IRQs need pullups */
s3c_gpio_setpull(S3C64XX_GPM(0), S3C_GPIO_PULL_UP);
s3c_gpio_setpull(S3C64XX_GPN(0), S3C_GPIO_PULL_UP);
gpio_request(S3C64XX_GPB(0), "LCD power");
gpio_direction_output(S3C64XX_GPB(0), 0);
gpio_request(S3C64XX_GPF(14), "LCD PWM");
gpio_direction_output(S3C64XX_GPF(14), 0); /* turn off */
gpio_request(S3C64XX_GPB(1), "SD power");
gpio_direction_output(S3C64XX_GPB(1), 0);
gpio_request(S3C64XX_GPF(10), "nRESETSEL");
gpio_direction_output(S3C64XX_GPF(10), 1);
s3c_sdhci0_set_platdata(&crag6410_hsmmc0_pdata);
s3c_sdhci2_set_platdata(&crag6410_hsmmc2_pdata);
s3c_i2c0_set_platdata(&i2c0_pdata);
s3c_i2c1_set_platdata(&i2c1_pdata);
s3c_fb_set_platdata(&crag6410_lcd_pdata);
s3c_hsotg_set_platdata(&crag6410_hsotg_pdata);
i2c_register_board_info(0, i2c_devs0, ARRAY_SIZE(i2c_devs0));
i2c_register_board_info(1, i2c_devs1, ARRAY_SIZE(i2c_devs1));
samsung_keypad_set_platdata(&crag6410_keypad_data);
s3c64xx_spi0_set_platdata(NULL, 0, 2);
platform_add_devices(crag6410_devices, ARRAY_SIZE(crag6410_devices));
gpio_led_register_device(-1, &gpio_leds_pdata);
regulator_has_full_constraints();
s3c64xx_pm_init();
}
MACHINE_START(WLF_CRAGG_6410, "Wolfson Cragganmore 6410")
/* Maintainer: Mark Brown <broonie@opensource.wolfsonmicro.com> */
.atag_offset = 0x100,
.init_irq = s3c6410_init_irq,
.map_io = crag6410_map_io,
.init_machine = crag6410_machine_init,
.init_time = samsung_timer_init,
.restart = s3c64xx_restart,
MACHINE_END

View file

@ -0,0 +1,282 @@
/* mach-hmt.c - Platform code for Airgoo HMT
*
* Copyright 2009 Peter Korsgaard <jacmet@sunsite.dk>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/platform_device.h>
#include <linux/io.h>
#include <linux/i2c.h>
#include <linux/fb.h>
#include <linux/gpio.h>
#include <linux/delay.h>
#include <linux/leds.h>
#include <linux/pwm_backlight.h>
#include <linux/mtd/mtd.h>
#include <linux/mtd/partitions.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <asm/mach/irq.h>
#include <video/samsung_fimd.h>
#include <mach/hardware.h>
#include <mach/map.h>
#include <asm/irq.h>
#include <asm/mach-types.h>
#include <linux/platform_data/i2c-s3c2410.h>
#include <mach/gpio-samsung.h>
#include <plat/fb.h>
#include <linux/platform_data/mtd-nand-s3c2410.h>
#include <plat/devs.h>
#include <plat/cpu.h>
#include <plat/samsung-time.h>
#include "common.h"
#define UCON S3C2410_UCON_DEFAULT
#define ULCON (S3C2410_LCON_CS8 | S3C2410_LCON_PNONE)
#define UFCON (S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE)
static struct s3c2410_uartcfg hmt_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[1] = {
.hwport = 1,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[2] = {
.hwport = 2,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
};
static int hmt_bl_init(struct device *dev)
{
int ret;
ret = gpio_request(S3C64XX_GPB(4), "lcd backlight enable");
if (!ret)
ret = gpio_direction_output(S3C64XX_GPB(4), 0);
return ret;
}
static int hmt_bl_notify(struct device *dev, int brightness)
{
/*
* translate from CIELUV/CIELAB L*->brightness, E.G. from
* perceived luminance to light output. Assumes range 0..25600
*/
if (brightness < 0x800) {
/* Y = Yn * L / 903.3 */
brightness = (100*256 * brightness + 231245/2) / 231245;
} else {
/* Y = Yn * ((L + 16) / 116 )^3 */
int t = (brightness*4 + 16*1024 + 58)/116;
brightness = 25 * ((t * t * t + 0x100000/2) / 0x100000);
}
gpio_set_value(S3C64XX_GPB(4), brightness);
return brightness;
}
static void hmt_bl_exit(struct device *dev)
{
gpio_free(S3C64XX_GPB(4));
}
static struct platform_pwm_backlight_data hmt_backlight_data = {
.pwm_id = 1,
.max_brightness = 100 * 256,
.dft_brightness = 40 * 256,
.pwm_period_ns = 1000000000 / (100 * 256 * 20),
.enable_gpio = -1,
.init = hmt_bl_init,
.notify = hmt_bl_notify,
.exit = hmt_bl_exit,
};
static struct platform_device hmt_backlight_device = {
.name = "pwm-backlight",
.dev = {
.parent = &samsung_device_pwm.dev,
.platform_data = &hmt_backlight_data,
},
};
static struct s3c_fb_pd_win hmt_fb_win0 = {
.max_bpp = 32,
.default_bpp = 16,
.xres = 800,
.yres = 480,
};
static struct fb_videomode hmt_lcd_timing = {
.left_margin = 8,
.right_margin = 13,
.upper_margin = 7,
.lower_margin = 5,
.hsync_len = 3,
.vsync_len = 1,
.xres = 800,
.yres = 480,
};
/* 405566 clocks per frame => 60Hz refresh requires 24333960Hz clock */
static struct s3c_fb_platdata hmt_lcd_pdata __initdata = {
.setup_gpio = s3c64xx_fb_gpio_setup_24bpp,
.vtiming = &hmt_lcd_timing,
.win[0] = &hmt_fb_win0,
.vidcon0 = VIDCON0_VIDOUT_RGB | VIDCON0_PNRMODE_RGB,
.vidcon1 = VIDCON1_INV_HSYNC | VIDCON1_INV_VSYNC,
};
static struct mtd_partition hmt_nand_part[] = {
[0] = {
.name = "uboot",
.size = SZ_512K,
.offset = 0,
},
[1] = {
.name = "uboot-env1",
.size = SZ_256K,
.offset = SZ_512K,
},
[2] = {
.name = "uboot-env2",
.size = SZ_256K,
.offset = SZ_512K + SZ_256K,
},
[3] = {
.name = "kernel",
.size = SZ_2M,
.offset = SZ_1M,
},
[4] = {
.name = "rootfs",
.size = MTDPART_SIZ_FULL,
.offset = SZ_1M + SZ_2M,
},
};
static struct s3c2410_nand_set hmt_nand_sets[] = {
[0] = {
.name = "nand",
.nr_chips = 1,
.nr_partitions = ARRAY_SIZE(hmt_nand_part),
.partitions = hmt_nand_part,
},
};
static struct s3c2410_platform_nand hmt_nand_info = {
.tacls = 25,
.twrph0 = 55,
.twrph1 = 40,
.nr_sets = ARRAY_SIZE(hmt_nand_sets),
.sets = hmt_nand_sets,
};
static struct gpio_led hmt_leds[] = {
{ /* left function keys */
.name = "left:blue",
.gpio = S3C64XX_GPO(12),
.default_trigger = "default-on",
},
{ /* right function keys - red */
.name = "right:red",
.gpio = S3C64XX_GPO(13),
},
{ /* right function keys - green */
.name = "right:green",
.gpio = S3C64XX_GPO(14),
},
{ /* right function keys - blue */
.name = "right:blue",
.gpio = S3C64XX_GPO(15),
.default_trigger = "default-on",
},
};
static struct gpio_led_platform_data hmt_led_data = {
.num_leds = ARRAY_SIZE(hmt_leds),
.leds = hmt_leds,
};
static struct platform_device hmt_leds_device = {
.name = "leds-gpio",
.id = -1,
.dev.platform_data = &hmt_led_data,
};
static struct map_desc hmt_iodesc[] = {};
static struct platform_device *hmt_devices[] __initdata = {
&s3c_device_i2c0,
&s3c_device_nand,
&s3c_device_fb,
&s3c_device_ohci,
&samsung_device_pwm,
&hmt_backlight_device,
&hmt_leds_device,
};
static void __init hmt_map_io(void)
{
s3c64xx_init_io(hmt_iodesc, ARRAY_SIZE(hmt_iodesc));
s3c64xx_set_xtal_freq(12000000);
s3c24xx_init_uarts(hmt_uartcfgs, ARRAY_SIZE(hmt_uartcfgs));
samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
}
static void __init hmt_machine_init(void)
{
s3c_i2c0_set_platdata(NULL);
s3c_fb_set_platdata(&hmt_lcd_pdata);
s3c_nand_set_platdata(&hmt_nand_info);
gpio_request(S3C64XX_GPC(7), "usb power");
gpio_direction_output(S3C64XX_GPC(7), 0);
gpio_request(S3C64XX_GPM(0), "usb power");
gpio_direction_output(S3C64XX_GPM(0), 1);
gpio_request(S3C64XX_GPK(7), "usb power");
gpio_direction_output(S3C64XX_GPK(7), 1);
gpio_request(S3C64XX_GPF(13), "usb power");
gpio_direction_output(S3C64XX_GPF(13), 1);
platform_add_devices(hmt_devices, ARRAY_SIZE(hmt_devices));
}
MACHINE_START(HMT, "Airgoo-HMT")
/* Maintainer: Peter Korsgaard <jacmet@sunsite.dk> */
.atag_offset = 0x100,
.init_irq = s3c6410_init_irq,
.map_io = hmt_map_io,
.init_machine = hmt_machine_init,
.init_time = samsung_timer_init,
.restart = s3c64xx_restart,
MACHINE_END

View file

@ -0,0 +1,371 @@
/* linux/arch/arm/mach-s3c64xx/mach-mini6410.c
*
* Copyright 2010 Darius Augulis <augulis.darius@gmail.com>
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#include <linux/init.h>
#include <linux/interrupt.h>
#include <linux/fb.h>
#include <linux/gpio.h>
#include <linux/kernel.h>
#include <linux/list.h>
#include <linux/dm9000.h>
#include <linux/mtd/mtd.h>
#include <linux/mtd/partitions.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/types.h>
#include <asm/mach-types.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <mach/map.h>
#include <mach/regs-gpio.h>
#include <mach/gpio-samsung.h>
#include <plat/adc.h>
#include <plat/cpu.h>
#include <plat/devs.h>
#include <plat/fb.h>
#include <linux/platform_data/mtd-nand-s3c2410.h>
#include <linux/platform_data/mmc-sdhci-s3c.h>
#include <plat/sdhci.h>
#include <linux/platform_data/touchscreen-s3c2410.h>
#include <video/platform_lcd.h>
#include <video/samsung_fimd.h>
#include <plat/samsung-time.h>
#include "common.h"
#include "regs-modem.h"
#include "regs-srom.h"
#define UCON S3C2410_UCON_DEFAULT
#define ULCON (S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB)
#define UFCON (S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE)
static struct s3c2410_uartcfg mini6410_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[1] = {
.hwport = 1,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[2] = {
.hwport = 2,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[3] = {
.hwport = 3,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
};
/* DM9000AEP 10/100 ethernet controller */
static struct resource mini6410_dm9k_resource[] = {
[0] = DEFINE_RES_MEM(S3C64XX_PA_XM0CSN1, 2),
[1] = DEFINE_RES_MEM(S3C64XX_PA_XM0CSN1 + 4, 2),
[2] = DEFINE_RES_NAMED(S3C_EINT(7), 1, NULL, IORESOURCE_IRQ \
| IORESOURCE_IRQ_HIGHLEVEL),
};
static struct dm9000_plat_data mini6410_dm9k_pdata = {
.flags = (DM9000_PLATF_16BITONLY | DM9000_PLATF_NO_EEPROM),
};
static struct platform_device mini6410_device_eth = {
.name = "dm9000",
.id = -1,
.num_resources = ARRAY_SIZE(mini6410_dm9k_resource),
.resource = mini6410_dm9k_resource,
.dev = {
.platform_data = &mini6410_dm9k_pdata,
},
};
static struct mtd_partition mini6410_nand_part[] = {
[0] = {
.name = "uboot",
.size = SZ_1M,
.offset = 0,
},
[1] = {
.name = "kernel",
.size = SZ_2M,
.offset = SZ_1M,
},
[2] = {
.name = "rootfs",
.size = MTDPART_SIZ_FULL,
.offset = SZ_1M + SZ_2M,
},
};
static struct s3c2410_nand_set mini6410_nand_sets[] = {
[0] = {
.name = "nand",
.nr_chips = 1,
.nr_partitions = ARRAY_SIZE(mini6410_nand_part),
.partitions = mini6410_nand_part,
},
};
static struct s3c2410_platform_nand mini6410_nand_info = {
.tacls = 25,
.twrph0 = 55,
.twrph1 = 40,
.nr_sets = ARRAY_SIZE(mini6410_nand_sets),
.sets = mini6410_nand_sets,
};
static struct s3c_fb_pd_win mini6410_lcd_type0_fb_win = {
.max_bpp = 32,
.default_bpp = 16,
.xres = 480,
.yres = 272,
};
static struct fb_videomode mini6410_lcd_type0_timing = {
/* 4.3" 480x272 */
.left_margin = 3,
.right_margin = 2,
.upper_margin = 1,
.lower_margin = 1,
.hsync_len = 40,
.vsync_len = 1,
.xres = 480,
.yres = 272,
};
static struct s3c_fb_pd_win mini6410_lcd_type1_fb_win = {
.max_bpp = 32,
.default_bpp = 16,
.xres = 800,
.yres = 480,
};
static struct fb_videomode mini6410_lcd_type1_timing = {
/* 7.0" 800x480 */
.left_margin = 8,
.right_margin = 13,
.upper_margin = 7,
.lower_margin = 5,
.hsync_len = 3,
.vsync_len = 1,
.xres = 800,
.yres = 480,
};
static struct s3c_fb_platdata mini6410_lcd_pdata[] __initdata = {
{
.setup_gpio = s3c64xx_fb_gpio_setup_24bpp,
.vtiming = &mini6410_lcd_type0_timing,
.win[0] = &mini6410_lcd_type0_fb_win,
.vidcon0 = VIDCON0_VIDOUT_RGB | VIDCON0_PNRMODE_RGB,
.vidcon1 = VIDCON1_INV_HSYNC | VIDCON1_INV_VSYNC,
}, {
.setup_gpio = s3c64xx_fb_gpio_setup_24bpp,
.vtiming = &mini6410_lcd_type1_timing,
.win[0] = &mini6410_lcd_type1_fb_win,
.vidcon0 = VIDCON0_VIDOUT_RGB | VIDCON0_PNRMODE_RGB,
.vidcon1 = VIDCON1_INV_HSYNC | VIDCON1_INV_VSYNC,
},
{ },
};
static void mini6410_lcd_power_set(struct plat_lcd_data *pd,
unsigned int power)
{
if (power)
gpio_direction_output(S3C64XX_GPE(0), 1);
else
gpio_direction_output(S3C64XX_GPE(0), 0);
}
static struct plat_lcd_data mini6410_lcd_power_data = {
.set_power = mini6410_lcd_power_set,
};
static struct platform_device mini6410_lcd_powerdev = {
.name = "platform-lcd",
.dev.parent = &s3c_device_fb.dev,
.dev.platform_data = &mini6410_lcd_power_data,
};
static struct s3c_sdhci_platdata mini6410_hsmmc1_pdata = {
.max_width = 4,
.cd_type = S3C_SDHCI_CD_GPIO,
.ext_cd_gpio = S3C64XX_GPN(10),
.ext_cd_gpio_invert = true,
};
static struct platform_device *mini6410_devices[] __initdata = {
&mini6410_device_eth,
&s3c_device_hsmmc0,
&s3c_device_hsmmc1,
&s3c_device_ohci,
&s3c_device_nand,
&s3c_device_fb,
&mini6410_lcd_powerdev,
&s3c_device_adc,
&s3c_device_ts,
};
static void __init mini6410_map_io(void)
{
u32 tmp;
s3c64xx_init_io(NULL, 0);
s3c64xx_set_xtal_freq(12000000);
s3c24xx_init_uarts(mini6410_uartcfgs, ARRAY_SIZE(mini6410_uartcfgs));
samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
/* set the LCD type */
tmp = __raw_readl(S3C64XX_SPCON);
tmp &= ~S3C64XX_SPCON_LCD_SEL_MASK;
tmp |= S3C64XX_SPCON_LCD_SEL_RGB;
__raw_writel(tmp, S3C64XX_SPCON);
/* remove the LCD bypass */
tmp = __raw_readl(S3C64XX_MODEM_MIFPCON);
tmp &= ~MIFPCON_LCD_BYPASS;
__raw_writel(tmp, S3C64XX_MODEM_MIFPCON);
}
/*
* mini6410_features string
*
* 0-9 LCD configuration
*
*/
static char mini6410_features_str[12] __initdata = "0";
static int __init mini6410_features_setup(char *str)
{
if (str)
strlcpy(mini6410_features_str, str,
sizeof(mini6410_features_str));
return 1;
}
__setup("mini6410=", mini6410_features_setup);
#define FEATURE_SCREEN (1 << 0)
struct mini6410_features_t {
int done;
int lcd_index;
};
static void mini6410_parse_features(
struct mini6410_features_t *features,
const char *features_str)
{
const char *fp = features_str;
features->done = 0;
features->lcd_index = 0;
while (*fp) {
char f = *fp++;
switch (f) {
case '0'...'9': /* tft screen */
if (features->done & FEATURE_SCREEN) {
printk(KERN_INFO "MINI6410: '%c' ignored, "
"screen type already set\n", f);
} else {
int li = f - '0';
if (li >= ARRAY_SIZE(mini6410_lcd_pdata))
printk(KERN_INFO "MINI6410: '%c' out "
"of range LCD mode\n", f);
else {
features->lcd_index = li;
}
}
features->done |= FEATURE_SCREEN;
break;
}
}
}
static void __init mini6410_machine_init(void)
{
u32 cs1;
struct mini6410_features_t features = { 0 };
printk(KERN_INFO "MINI6410: Option string mini6410=%s\n",
mini6410_features_str);
/* Parse the feature string */
mini6410_parse_features(&features, mini6410_features_str);
printk(KERN_INFO "MINI6410: selected LCD display is %dx%d\n",
mini6410_lcd_pdata[features.lcd_index].win[0]->xres,
mini6410_lcd_pdata[features.lcd_index].win[0]->yres);
s3c_nand_set_platdata(&mini6410_nand_info);
s3c_fb_set_platdata(&mini6410_lcd_pdata[features.lcd_index]);
s3c_sdhci1_set_platdata(&mini6410_hsmmc1_pdata);
s3c24xx_ts_set_platdata(NULL);
/* configure nCS1 width to 16 bits */
cs1 = __raw_readl(S3C64XX_SROM_BW) &
~(S3C64XX_SROM_BW__CS_MASK << S3C64XX_SROM_BW__NCS1__SHIFT);
cs1 |= ((1 << S3C64XX_SROM_BW__DATAWIDTH__SHIFT) |
(1 << S3C64XX_SROM_BW__WAITENABLE__SHIFT) |
(1 << S3C64XX_SROM_BW__BYTEENABLE__SHIFT)) <<
S3C64XX_SROM_BW__NCS1__SHIFT;
__raw_writel(cs1, S3C64XX_SROM_BW);
/* set timing for nCS1 suitable for ethernet chip */
__raw_writel((0 << S3C64XX_SROM_BCX__PMC__SHIFT) |
(6 << S3C64XX_SROM_BCX__TACP__SHIFT) |
(4 << S3C64XX_SROM_BCX__TCAH__SHIFT) |
(1 << S3C64XX_SROM_BCX__TCOH__SHIFT) |
(13 << S3C64XX_SROM_BCX__TACC__SHIFT) |
(4 << S3C64XX_SROM_BCX__TCOS__SHIFT) |
(0 << S3C64XX_SROM_BCX__TACS__SHIFT), S3C64XX_SROM_BC1);
gpio_request(S3C64XX_GPF(15), "LCD power");
gpio_request(S3C64XX_GPE(0), "LCD power");
platform_add_devices(mini6410_devices, ARRAY_SIZE(mini6410_devices));
}
MACHINE_START(MINI6410, "MINI6410")
/* Maintainer: Darius Augulis <augulis.darius@gmail.com> */
.atag_offset = 0x100,
.init_irq = s3c6410_init_irq,
.map_io = mini6410_map_io,
.init_machine = mini6410_machine_init,
.init_time = samsung_timer_init,
.restart = s3c64xx_restart,
MACHINE_END

View file

@ -0,0 +1,108 @@
/*
* linux/arch/arm/mach-s3c64xx/mach-ncp.c
*
* Copyright (C) 2008-2009 Samsung Electronics
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/interrupt.h>
#include <linux/list.h>
#include <linux/timer.h>
#include <linux/init.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/platform_device.h>
#include <linux/io.h>
#include <linux/i2c.h>
#include <linux/fb.h>
#include <linux/gpio.h>
#include <linux/delay.h>
#include <video/platform_lcd.h>
#include <video/samsung_fimd.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <asm/mach/irq.h>
#include <mach/hardware.h>
#include <mach/map.h>
#include <asm/irq.h>
#include <asm/mach-types.h>
#include <linux/platform_data/i2c-s3c2410.h>
#include <plat/fb.h>
#include <plat/devs.h>
#include <plat/cpu.h>
#include <plat/samsung-time.h>
#include "common.h"
#define UCON S3C2410_UCON_DEFAULT
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE
#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
static struct s3c2410_uartcfg ncp_uartcfgs[] __initdata = {
/* REVISIT: NCP uses only serial 1, 2 */
[0] = {
.hwport = 0,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[1] = {
.hwport = 1,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[2] = {
.hwport = 2,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
};
static struct platform_device *ncp_devices[] __initdata = {
&s3c_device_hsmmc1,
&s3c_device_i2c0,
};
static struct map_desc ncp_iodesc[] __initdata = {};
static void __init ncp_map_io(void)
{
s3c64xx_init_io(ncp_iodesc, ARRAY_SIZE(ncp_iodesc));
s3c64xx_set_xtal_freq(12000000);
s3c24xx_init_uarts(ncp_uartcfgs, ARRAY_SIZE(ncp_uartcfgs));
samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
}
static void __init ncp_machine_init(void)
{
s3c_i2c0_set_platdata(NULL);
platform_add_devices(ncp_devices, ARRAY_SIZE(ncp_devices));
}
MACHINE_START(NCP, "NCP")
/* Maintainer: Samsung Electronics */
.atag_offset = 0x100,
.init_irq = s3c6410_init_irq,
.map_io = ncp_map_io,
.init_machine = ncp_machine_init,
.init_time = samsung_timer_init,
.restart = s3c64xx_restart,
MACHINE_END

View file

@ -0,0 +1,340 @@
/* linux/arch/arm/mach-s3c64xx/mach-real6410.c
*
* Copyright 2010 Darius Augulis <augulis.darius@gmail.com>
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#include <linux/init.h>
#include <linux/interrupt.h>
#include <linux/fb.h>
#include <linux/gpio.h>
#include <linux/kernel.h>
#include <linux/list.h>
#include <linux/dm9000.h>
#include <linux/mtd/mtd.h>
#include <linux/mtd/partitions.h>
#include <linux/platform_device.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/types.h>
#include <asm/mach-types.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <mach/map.h>
#include <mach/regs-gpio.h>
#include <mach/gpio-samsung.h>
#include <plat/adc.h>
#include <plat/cpu.h>
#include <plat/devs.h>
#include <plat/fb.h>
#include <linux/platform_data/mtd-nand-s3c2410.h>
#include <linux/platform_data/touchscreen-s3c2410.h>
#include <video/platform_lcd.h>
#include <video/samsung_fimd.h>
#include <plat/samsung-time.h>
#include "common.h"
#include "regs-modem.h"
#include "regs-srom.h"
#define UCON S3C2410_UCON_DEFAULT
#define ULCON (S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB)
#define UFCON (S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE)
static struct s3c2410_uartcfg real6410_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[1] = {
.hwport = 1,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[2] = {
.hwport = 2,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[3] = {
.hwport = 3,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
};
/* DM9000AEP 10/100 ethernet controller */
static struct resource real6410_dm9k_resource[] = {
[0] = DEFINE_RES_MEM(S3C64XX_PA_XM0CSN1, 2),
[1] = DEFINE_RES_MEM(S3C64XX_PA_XM0CSN1 + 4, 2),
[2] = DEFINE_RES_NAMED(S3C_EINT(7), 1, NULL, IORESOURCE_IRQ \
| IORESOURCE_IRQ_HIGHLEVEL),
};
static struct dm9000_plat_data real6410_dm9k_pdata = {
.flags = (DM9000_PLATF_16BITONLY | DM9000_PLATF_NO_EEPROM),
};
static struct platform_device real6410_device_eth = {
.name = "dm9000",
.id = -1,
.num_resources = ARRAY_SIZE(real6410_dm9k_resource),
.resource = real6410_dm9k_resource,
.dev = {
.platform_data = &real6410_dm9k_pdata,
},
};
static struct s3c_fb_pd_win real6410_lcd_type0_fb_win = {
.max_bpp = 32,
.default_bpp = 16,
.xres = 480,
.yres = 272,
};
static struct fb_videomode real6410_lcd_type0_timing = {
/* 4.3" 480x272 */
.left_margin = 3,
.right_margin = 2,
.upper_margin = 1,
.lower_margin = 1,
.hsync_len = 40,
.vsync_len = 1,
};
static struct s3c_fb_pd_win real6410_lcd_type1_fb_win = {
.max_bpp = 32,
.default_bpp = 16,
.xres = 800,
.yres = 480,
};
static struct fb_videomode real6410_lcd_type1_timing = {
/* 7.0" 800x480 */
.left_margin = 8,
.right_margin = 13,
.upper_margin = 7,
.lower_margin = 5,
.hsync_len = 3,
.vsync_len = 1,
.xres = 800,
.yres = 480,
};
static struct s3c_fb_platdata real6410_lcd_pdata[] __initdata = {
{
.setup_gpio = s3c64xx_fb_gpio_setup_24bpp,
.vtiming = &real6410_lcd_type0_timing,
.win[0] = &real6410_lcd_type0_fb_win,
.vidcon0 = VIDCON0_VIDOUT_RGB | VIDCON0_PNRMODE_RGB,
.vidcon1 = VIDCON1_INV_HSYNC | VIDCON1_INV_VSYNC,
}, {
.setup_gpio = s3c64xx_fb_gpio_setup_24bpp,
.vtiming = &real6410_lcd_type1_timing,
.win[0] = &real6410_lcd_type1_fb_win,
.vidcon0 = VIDCON0_VIDOUT_RGB | VIDCON0_PNRMODE_RGB,
.vidcon1 = VIDCON1_INV_HSYNC | VIDCON1_INV_VSYNC,
},
{ },
};
static struct mtd_partition real6410_nand_part[] = {
[0] = {
.name = "uboot",
.size = SZ_1M,
.offset = 0,
},
[1] = {
.name = "kernel",
.size = SZ_2M,
.offset = SZ_1M,
},
[2] = {
.name = "rootfs",
.size = MTDPART_SIZ_FULL,
.offset = SZ_1M + SZ_2M,
},
};
static struct s3c2410_nand_set real6410_nand_sets[] = {
[0] = {
.name = "nand",
.nr_chips = 1,
.nr_partitions = ARRAY_SIZE(real6410_nand_part),
.partitions = real6410_nand_part,
},
};
static struct s3c2410_platform_nand real6410_nand_info = {
.tacls = 25,
.twrph0 = 55,
.twrph1 = 40,
.nr_sets = ARRAY_SIZE(real6410_nand_sets),
.sets = real6410_nand_sets,
};
static struct platform_device *real6410_devices[] __initdata = {
&real6410_device_eth,
&s3c_device_hsmmc0,
&s3c_device_hsmmc1,
&s3c_device_fb,
&s3c_device_nand,
&s3c_device_adc,
&s3c_device_ts,
&s3c_device_ohci,
};
static void __init real6410_map_io(void)
{
u32 tmp;
s3c64xx_init_io(NULL, 0);
s3c24xx_init_clocks(12000000);
s3c24xx_init_uarts(real6410_uartcfgs, ARRAY_SIZE(real6410_uartcfgs));
samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
/* set the LCD type */
tmp = __raw_readl(S3C64XX_SPCON);
tmp &= ~S3C64XX_SPCON_LCD_SEL_MASK;
tmp |= S3C64XX_SPCON_LCD_SEL_RGB;
__raw_writel(tmp, S3C64XX_SPCON);
/* remove the LCD bypass */
tmp = __raw_readl(S3C64XX_MODEM_MIFPCON);
tmp &= ~MIFPCON_LCD_BYPASS;
__raw_writel(tmp, S3C64XX_MODEM_MIFPCON);
}
/*
* real6410_features string
*
* 0-9 LCD configuration
*
*/
static char real6410_features_str[12] __initdata = "0";
static int __init real6410_features_setup(char *str)
{
if (str)
strlcpy(real6410_features_str, str,
sizeof(real6410_features_str));
return 1;
}
__setup("real6410=", real6410_features_setup);
#define FEATURE_SCREEN (1 << 0)
struct real6410_features_t {
int done;
int lcd_index;
};
static void real6410_parse_features(
struct real6410_features_t *features,
const char *features_str)
{
const char *fp = features_str;
features->done = 0;
features->lcd_index = 0;
while (*fp) {
char f = *fp++;
switch (f) {
case '0'...'9': /* tft screen */
if (features->done & FEATURE_SCREEN) {
printk(KERN_INFO "REAL6410: '%c' ignored, "
"screen type already set\n", f);
} else {
int li = f - '0';
if (li >= ARRAY_SIZE(real6410_lcd_pdata))
printk(KERN_INFO "REAL6410: '%c' out "
"of range LCD mode\n", f);
else {
features->lcd_index = li;
}
}
features->done |= FEATURE_SCREEN;
break;
}
}
}
static void __init real6410_machine_init(void)
{
u32 cs1;
struct real6410_features_t features = { 0 };
printk(KERN_INFO "REAL6410: Option string real6410=%s\n",
real6410_features_str);
/* Parse the feature string */
real6410_parse_features(&features, real6410_features_str);
printk(KERN_INFO "REAL6410: selected LCD display is %dx%d\n",
real6410_lcd_pdata[features.lcd_index].win[0]->xres,
real6410_lcd_pdata[features.lcd_index].win[0]->yres);
s3c_fb_set_platdata(&real6410_lcd_pdata[features.lcd_index]);
s3c_nand_set_platdata(&real6410_nand_info);
s3c24xx_ts_set_platdata(NULL);
/* configure nCS1 width to 16 bits */
cs1 = __raw_readl(S3C64XX_SROM_BW) &
~(S3C64XX_SROM_BW__CS_MASK << S3C64XX_SROM_BW__NCS1__SHIFT);
cs1 |= ((1 << S3C64XX_SROM_BW__DATAWIDTH__SHIFT) |
(1 << S3C64XX_SROM_BW__WAITENABLE__SHIFT) |
(1 << S3C64XX_SROM_BW__BYTEENABLE__SHIFT)) <<
S3C64XX_SROM_BW__NCS1__SHIFT;
__raw_writel(cs1, S3C64XX_SROM_BW);
/* set timing for nCS1 suitable for ethernet chip */
__raw_writel((0 << S3C64XX_SROM_BCX__PMC__SHIFT) |
(6 << S3C64XX_SROM_BCX__TACP__SHIFT) |
(4 << S3C64XX_SROM_BCX__TCAH__SHIFT) |
(1 << S3C64XX_SROM_BCX__TCOH__SHIFT) |
(13 << S3C64XX_SROM_BCX__TACC__SHIFT) |
(4 << S3C64XX_SROM_BCX__TCOS__SHIFT) |
(0 << S3C64XX_SROM_BCX__TACS__SHIFT), S3C64XX_SROM_BC1);
gpio_request(S3C64XX_GPF(15), "LCD power");
platform_add_devices(real6410_devices, ARRAY_SIZE(real6410_devices));
}
MACHINE_START(REAL6410, "REAL6410")
/* Maintainer: Darius Augulis <augulis.darius@gmail.com> */
.atag_offset = 0x100,
.init_irq = s3c6410_init_irq,
.map_io = real6410_map_io,
.init_machine = real6410_machine_init,
.init_time = samsung_timer_init,
.restart = s3c64xx_restart,
MACHINE_END

View file

@ -0,0 +1,76 @@
/*
* Samsung's S3C64XX flattened device tree enabled machine
*
* Copyright (c) 2013 Tomasz Figa <tomasz.figa@gmail.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/of_platform.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <asm/system_misc.h>
#include <plat/cpu.h>
#include <plat/watchdog-reset.h>
#include <mach/map.h>
#include "common.h"
/*
* IO mapping for shared system controller IP.
*
* FIXME: Make remaining drivers use dynamic mapping.
*/
static struct map_desc s3c64xx_dt_iodesc[] __initdata = {
{
.virtual = (unsigned long)S3C_VA_SYS,
.pfn = __phys_to_pfn(S3C64XX_PA_SYSCON),
.length = SZ_4K,
.type = MT_DEVICE,
},
};
static void __init s3c64xx_dt_map_io(void)
{
debug_ll_io_init();
iotable_init(s3c64xx_dt_iodesc, ARRAY_SIZE(s3c64xx_dt_iodesc));
s3c64xx_init_cpu();
if (!soc_is_s3c64xx())
panic("SoC is not S3C64xx!");
}
static void __init s3c64xx_dt_init_machine(void)
{
samsung_wdt_reset_of_init();
of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL);
}
static void s3c64xx_dt_restart(enum reboot_mode mode, const char *cmd)
{
if (mode != REBOOT_SOFT)
samsung_wdt_reset();
/* if all else fails, or mode was for soft, jump to 0 */
soft_restart(0);
}
static char const *s3c64xx_dt_compat[] __initdata = {
"samsung,s3c6400",
"samsung,s3c6410",
NULL
};
DT_MACHINE_START(S3C6400_DT, "Samsung S3C64xx (Flattened Device Tree)")
/* Maintainer: Tomasz Figa <tomasz.figa@gmail.com> */
.dt_compat = s3c64xx_dt_compat,
.map_io = s3c64xx_dt_map_io,
.init_machine = s3c64xx_dt_init_machine,
.restart = s3c64xx_dt_restart,
MACHINE_END

View file

@ -0,0 +1,400 @@
/*
* linux/arch/arm/mach-s3c64xx/mach-smartq.c
*
* Copyright (C) 2010 Maurus Cuelenaere
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#include <linux/delay.h>
#include <linux/fb.h>
#include <linux/gpio.h>
#include <linux/init.h>
#include <linux/platform_device.h>
#include <linux/pwm_backlight.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/spi/spi_gpio.h>
#include <linux/usb/gpio_vbus.h>
#include <linux/platform_data/s3c-hsotg.h>
#include <asm/mach-types.h>
#include <asm/mach/map.h>
#include <mach/map.h>
#include <mach/regs-gpio.h>
#include <mach/gpio-samsung.h>
#include <plat/cpu.h>
#include <plat/devs.h>
#include <linux/platform_data/i2c-s3c2410.h>
#include <plat/gpio-cfg.h>
#include <linux/platform_data/hwmon-s3c.h>
#include <linux/platform_data/usb-ohci-s3c2410.h>
#include <plat/sdhci.h>
#include <linux/platform_data/touchscreen-s3c2410.h>
#include <video/platform_lcd.h>
#include <plat/samsung-time.h>
#include "common.h"
#include "regs-modem.h"
#define UCON S3C2410_UCON_DEFAULT
#define ULCON (S3C2410_LCON_CS8 | S3C2410_LCON_PNONE)
#define UFCON (S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE)
static struct s3c2410_uartcfg smartq_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[1] = {
.hwport = 1,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[2] = {
.hwport = 2,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
};
static void smartq_usb_host_powercontrol(int port, int to)
{
pr_debug("%s(%d, %d)\n", __func__, port, to);
if (port == 0) {
gpio_set_value(S3C64XX_GPL(0), to);
gpio_set_value(S3C64XX_GPL(1), to);
}
}
static irqreturn_t smartq_usb_host_ocirq(int irq, void *pw)
{
struct s3c2410_hcd_info *info = pw;
if (gpio_get_value(S3C64XX_GPL(10)) == 0) {
pr_debug("%s: over-current irq (oc detected)\n", __func__);
s3c2410_usb_report_oc(info, 3);
} else {
pr_debug("%s: over-current irq (oc cleared)\n", __func__);
s3c2410_usb_report_oc(info, 0);
}
return IRQ_HANDLED;
}
static void smartq_usb_host_enableoc(struct s3c2410_hcd_info *info, int on)
{
int ret;
/* This isn't present on a SmartQ 5 board */
if (machine_is_smartq5())
return;
if (on) {
ret = request_irq(gpio_to_irq(S3C64XX_GPL(10)),
smartq_usb_host_ocirq,
IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING,
"USB host overcurrent", info);
if (ret != 0)
pr_err("failed to request usb oc irq: %d\n", ret);
} else {
free_irq(gpio_to_irq(S3C64XX_GPL(10)), info);
}
}
static struct s3c2410_hcd_info smartq_usb_host_info = {
.port[0] = {
.flags = S3C_HCDFLG_USED
},
.port[1] = {
.flags = 0
},
.power_control = smartq_usb_host_powercontrol,
.enable_oc = smartq_usb_host_enableoc,
};
static struct gpio_vbus_mach_info smartq_usb_otg_vbus_pdata = {
.gpio_vbus = S3C64XX_GPL(9),
.gpio_pullup = -1,
.gpio_vbus_inverted = true,
};
static struct platform_device smartq_usb_otg_vbus_dev = {
.name = "gpio-vbus",
.dev.platform_data = &smartq_usb_otg_vbus_pdata,
};
static int smartq_bl_init(struct device *dev)
{
s3c_gpio_cfgpin(S3C64XX_GPF(15), S3C_GPIO_SFN(2));
return 0;
}
static struct platform_pwm_backlight_data smartq_backlight_data = {
.pwm_id = 1,
.max_brightness = 1000,
.dft_brightness = 600,
.pwm_period_ns = 1000000000 / (1000 * 20),
.enable_gpio = -1,
.init = smartq_bl_init,
};
static struct platform_device smartq_backlight_device = {
.name = "pwm-backlight",
.dev = {
.parent = &samsung_device_pwm.dev,
.platform_data = &smartq_backlight_data,
},
};
static struct s3c2410_ts_mach_info smartq_touchscreen_pdata __initdata = {
.delay = 65535,
.presc = 99,
.oversampling_shift = 4,
};
static struct s3c_sdhci_platdata smartq_internal_hsmmc_pdata = {
.max_width = 4,
.cd_type = S3C_SDHCI_CD_PERMANENT,
};
static struct s3c_hwmon_pdata smartq_hwmon_pdata __initdata = {
/* Battery voltage (?-4.2V) */
.in[0] = &(struct s3c_hwmon_chcfg) {
.name = "smartq:battery-voltage",
.mult = 3300,
.div = 2048,
},
/* Reference voltage (1.2V) */
.in[1] = &(struct s3c_hwmon_chcfg) {
.name = "smartq:reference-voltage",
.mult = 3300,
.div = 4096,
},
};
static struct s3c_hsotg_plat smartq_hsotg_pdata;
static int __init smartq_lcd_setup_gpio(void)
{
int ret;
ret = gpio_request(S3C64XX_GPM(3), "LCD power");
if (ret < 0)
return ret;
/* turn power off */
gpio_direction_output(S3C64XX_GPM(3), 0);
return 0;
}
/* GPM0 -> CS */
static struct spi_gpio_platform_data smartq_lcd_control = {
.sck = S3C64XX_GPM(1),
.mosi = S3C64XX_GPM(2),
.miso = S3C64XX_GPM(2),
};
static struct platform_device smartq_lcd_control_device = {
.name = "spi-gpio",
.id = 1,
.dev.platform_data = &smartq_lcd_control,
};
static void smartq_lcd_power_set(struct plat_lcd_data *pd, unsigned int power)
{
gpio_direction_output(S3C64XX_GPM(3), power);
}
static struct plat_lcd_data smartq_lcd_power_data = {
.set_power = smartq_lcd_power_set,
};
static struct platform_device smartq_lcd_power_device = {
.name = "platform-lcd",
.dev.parent = &s3c_device_fb.dev,
.dev.platform_data = &smartq_lcd_power_data,
};
static struct i2c_board_info smartq_i2c_devs[] __initdata = {
{ I2C_BOARD_INFO("wm8987", 0x1a), },
};
static struct platform_device *smartq_devices[] __initdata = {
&s3c_device_hsmmc1, /* Init iNAND first, ... */
&s3c_device_hsmmc0, /* ... then the external SD card */
&s3c_device_hsmmc2,
&s3c_device_adc,
&s3c_device_fb,
&s3c_device_hwmon,
&s3c_device_i2c0,
&s3c_device_ohci,
&s3c_device_rtc,
&samsung_device_pwm,
&s3c_device_ts,
&s3c_device_usb_hsotg,
&s3c64xx_device_iis0,
&smartq_backlight_device,
&smartq_lcd_control_device,
&smartq_lcd_power_device,
&smartq_usb_otg_vbus_dev,
};
static void __init smartq_lcd_mode_set(void)
{
u32 tmp;
/* set the LCD type */
tmp = __raw_readl(S3C64XX_SPCON);
tmp &= ~S3C64XX_SPCON_LCD_SEL_MASK;
tmp |= S3C64XX_SPCON_LCD_SEL_RGB;
__raw_writel(tmp, S3C64XX_SPCON);
/* remove the LCD bypass */
tmp = __raw_readl(S3C64XX_MODEM_MIFPCON);
tmp &= ~MIFPCON_LCD_BYPASS;
__raw_writel(tmp, S3C64XX_MODEM_MIFPCON);
}
static void smartq_power_off(void)
{
gpio_direction_output(S3C64XX_GPK(15), 1);
}
static int __init smartq_power_off_init(void)
{
int ret;
ret = gpio_request(S3C64XX_GPK(15), "Power control");
if (ret < 0) {
pr_err("%s: failed to get GPK15\n", __func__);
return ret;
}
/* leave power on */
gpio_direction_output(S3C64XX_GPK(15), 0);
pm_power_off = smartq_power_off;
return ret;
}
static int __init smartq_usb_host_init(void)
{
int ret;
ret = gpio_request(S3C64XX_GPL(0), "USB power control");
if (ret < 0) {
pr_err("%s: failed to get GPL0\n", __func__);
return ret;
}
ret = gpio_request(S3C64XX_GPL(1), "USB host power control");
if (ret < 0) {
pr_err("%s: failed to get GPL1\n", __func__);
goto err;
}
if (!machine_is_smartq5()) {
/* This isn't present on a SmartQ 5 board */
ret = gpio_request(S3C64XX_GPL(10), "USB host overcurrent");
if (ret < 0) {
pr_err("%s: failed to get GPL10\n", __func__);
goto err2;
}
}
/* turn power off */
gpio_direction_output(S3C64XX_GPL(0), 0);
gpio_direction_output(S3C64XX_GPL(1), 0);
if (!machine_is_smartq5())
gpio_direction_input(S3C64XX_GPL(10));
s3c_device_ohci.dev.platform_data = &smartq_usb_host_info;
return 0;
err2:
gpio_free(S3C64XX_GPL(1));
err:
gpio_free(S3C64XX_GPL(0));
return ret;
}
static int __init smartq_wifi_init(void)
{
int ret;
ret = gpio_request(S3C64XX_GPK(1), "wifi control");
if (ret < 0) {
pr_err("%s: failed to get GPK1\n", __func__);
return ret;
}
ret = gpio_request(S3C64XX_GPK(2), "wifi reset");
if (ret < 0) {
pr_err("%s: failed to get GPK2\n", __func__);
gpio_free(S3C64XX_GPK(1));
return ret;
}
/* turn power on */
gpio_direction_output(S3C64XX_GPK(1), 1);
/* reset device */
gpio_direction_output(S3C64XX_GPK(2), 0);
mdelay(100);
gpio_set_value(S3C64XX_GPK(2), 1);
gpio_direction_input(S3C64XX_GPK(2));
return 0;
}
static struct map_desc smartq_iodesc[] __initdata = {};
void __init smartq_map_io(void)
{
s3c64xx_init_io(smartq_iodesc, ARRAY_SIZE(smartq_iodesc));
s3c64xx_set_xtal_freq(12000000);
s3c64xx_set_xusbxti_freq(12000000);
s3c24xx_init_uarts(smartq_uartcfgs, ARRAY_SIZE(smartq_uartcfgs));
samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
smartq_lcd_mode_set();
}
void __init smartq_machine_init(void)
{
s3c_i2c0_set_platdata(NULL);
s3c_hsotg_set_platdata(&smartq_hsotg_pdata);
s3c_hwmon_set_platdata(&smartq_hwmon_pdata);
s3c_sdhci1_set_platdata(&smartq_internal_hsmmc_pdata);
s3c_sdhci2_set_platdata(&smartq_internal_hsmmc_pdata);
s3c24xx_ts_set_platdata(&smartq_touchscreen_pdata);
i2c_register_board_info(0, smartq_i2c_devs,
ARRAY_SIZE(smartq_i2c_devs));
WARN_ON(smartq_lcd_setup_gpio());
WARN_ON(smartq_power_off_init());
WARN_ON(smartq_usb_host_init());
WARN_ON(smartq_wifi_init());
platform_add_devices(smartq_devices, ARRAY_SIZE(smartq_devices));
}

View file

@ -0,0 +1,20 @@
/*
* linux/arch/arm/mach-s3c64xx/mach-smartq.h
*
* Copyright (C) 2010 Maurus Cuelenaere
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#ifndef __MACH_SMARTQ_H
#define __MACH_SMARTQ_H __FILE__
#include <linux/init.h>
extern void __init smartq_map_io(void);
extern void __init smartq_machine_init(void);
#endif /* __MACH_SMARTQ_H */

View file

@ -0,0 +1,161 @@
/*
* linux/arch/arm/mach-s3c64xx/mach-smartq5.c
*
* Copyright (C) 2010 Maurus Cuelenaere
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#include <linux/fb.h>
#include <linux/gpio.h>
#include <linux/gpio_keys.h>
#include <linux/init.h>
#include <linux/input.h>
#include <linux/leds.h>
#include <linux/platform_device.h>
#include <asm/mach-types.h>
#include <asm/mach/arch.h>
#include <video/samsung_fimd.h>
#include <mach/map.h>
#include <mach/regs-gpio.h>
#include <mach/gpio-samsung.h>
#include <plat/cpu.h>
#include <plat/devs.h>
#include <plat/fb.h>
#include <plat/gpio-cfg.h>
#include <plat/samsung-time.h>
#include "common.h"
#include "mach-smartq.h"
static struct gpio_led smartq5_leds[] = {
{
.name = "smartq5:green",
.active_low = 1,
.gpio = S3C64XX_GPN(8),
},
{
.name = "smartq5:red",
.active_low = 1,
.gpio = S3C64XX_GPN(9),
},
};
static struct gpio_led_platform_data smartq5_led_data = {
.num_leds = ARRAY_SIZE(smartq5_leds),
.leds = smartq5_leds,
};
static struct platform_device smartq5_leds_device = {
.name = "leds-gpio",
.id = -1,
.dev.platform_data = &smartq5_led_data,
};
/* Labels according to the SmartQ manual */
static struct gpio_keys_button smartq5_buttons[] = {
{
.gpio = S3C64XX_GPL(14),
.code = KEY_POWER,
.desc = "Power",
.active_low = 1,
.debounce_interval = 5,
.type = EV_KEY,
},
{
.gpio = S3C64XX_GPN(2),
.code = KEY_KPMINUS,
.desc = "Minus",
.active_low = 1,
.debounce_interval = 5,
.type = EV_KEY,
},
{
.gpio = S3C64XX_GPN(12),
.code = KEY_KPPLUS,
.desc = "Plus",
.active_low = 1,
.debounce_interval = 5,
.type = EV_KEY,
},
{
.gpio = S3C64XX_GPN(15),
.code = KEY_ENTER,
.desc = "Move",
.active_low = 1,
.debounce_interval = 5,
.type = EV_KEY,
},
};
static struct gpio_keys_platform_data smartq5_buttons_data = {
.buttons = smartq5_buttons,
.nbuttons = ARRAY_SIZE(smartq5_buttons),
};
static struct platform_device smartq5_buttons_device = {
.name = "gpio-keys",
.id = 0,
.num_resources = 0,
.dev = {
.platform_data = &smartq5_buttons_data,
}
};
static struct s3c_fb_pd_win smartq5_fb_win0 = {
.max_bpp = 32,
.default_bpp = 16,
.xres = 800,
.yres = 480,
};
static struct fb_videomode smartq5_lcd_timing = {
.left_margin = 216,
.right_margin = 40,
.upper_margin = 35,
.lower_margin = 10,
.hsync_len = 1,
.vsync_len = 1,
.xres = 800,
.yres = 480,
.refresh = 80,
};
static struct s3c_fb_platdata smartq5_lcd_pdata __initdata = {
.setup_gpio = s3c64xx_fb_gpio_setup_24bpp,
.vtiming = &smartq5_lcd_timing,
.win[0] = &smartq5_fb_win0,
.vidcon0 = VIDCON0_VIDOUT_RGB | VIDCON0_PNRMODE_RGB,
.vidcon1 = VIDCON1_INV_HSYNC | VIDCON1_INV_VSYNC |
VIDCON1_INV_VDEN,
};
static struct platform_device *smartq5_devices[] __initdata = {
&smartq5_leds_device,
&smartq5_buttons_device,
};
static void __init smartq5_machine_init(void)
{
s3c_fb_set_platdata(&smartq5_lcd_pdata);
smartq_machine_init();
platform_add_devices(smartq5_devices, ARRAY_SIZE(smartq5_devices));
}
MACHINE_START(SMARTQ5, "SmartQ 5")
/* Maintainer: Maurus Cuelenaere <mcuelenaere AT gmail DOT com> */
.atag_offset = 0x100,
.init_irq = s3c6410_init_irq,
.map_io = smartq_map_io,
.init_machine = smartq5_machine_init,
.init_time = samsung_timer_init,
.restart = s3c64xx_restart,
MACHINE_END

View file

@ -0,0 +1,177 @@
/*
* linux/arch/arm/mach-s3c64xx/mach-smartq7.c
*
* Copyright (C) 2010 Maurus Cuelenaere
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#include <linux/fb.h>
#include <linux/gpio.h>
#include <linux/gpio_keys.h>
#include <linux/init.h>
#include <linux/input.h>
#include <linux/leds.h>
#include <linux/platform_device.h>
#include <asm/mach-types.h>
#include <asm/mach/arch.h>
#include <video/samsung_fimd.h>
#include <mach/map.h>
#include <mach/regs-gpio.h>
#include <mach/gpio-samsung.h>
#include <plat/cpu.h>
#include <plat/devs.h>
#include <plat/fb.h>
#include <plat/gpio-cfg.h>
#include <plat/samsung-time.h>
#include "common.h"
#include "mach-smartq.h"
static struct gpio_led smartq7_leds[] = {
{
.name = "smartq7:red",
.active_low = 1,
.gpio = S3C64XX_GPN(8),
},
{
.name = "smartq7:green",
.active_low = 1,
.gpio = S3C64XX_GPN(9),
},
};
static struct gpio_led_platform_data smartq7_led_data = {
.num_leds = ARRAY_SIZE(smartq7_leds),
.leds = smartq7_leds,
};
static struct platform_device smartq7_leds_device = {
.name = "leds-gpio",
.id = -1,
.dev.platform_data = &smartq7_led_data,
};
/* Labels according to the SmartQ manual */
static struct gpio_keys_button smartq7_buttons[] = {
{
.gpio = S3C64XX_GPL(14),
.code = KEY_POWER,
.desc = "Power",
.active_low = 1,
.debounce_interval = 5,
.type = EV_KEY,
},
{
.gpio = S3C64XX_GPN(2),
.code = KEY_FN,
.desc = "Function",
.active_low = 1,
.debounce_interval = 5,
.type = EV_KEY,
},
{
.gpio = S3C64XX_GPN(3),
.code = KEY_KPMINUS,
.desc = "Minus",
.active_low = 1,
.debounce_interval = 5,
.type = EV_KEY,
},
{
.gpio = S3C64XX_GPN(4),
.code = KEY_KPPLUS,
.desc = "Plus",
.active_low = 1,
.debounce_interval = 5,
.type = EV_KEY,
},
{
.gpio = S3C64XX_GPN(12),
.code = KEY_ENTER,
.desc = "Enter",
.active_low = 1,
.debounce_interval = 5,
.type = EV_KEY,
},
{
.gpio = S3C64XX_GPN(15),
.code = KEY_ESC,
.desc = "Cancel",
.active_low = 1,
.debounce_interval = 5,
.type = EV_KEY,
},
};
static struct gpio_keys_platform_data smartq7_buttons_data = {
.buttons = smartq7_buttons,
.nbuttons = ARRAY_SIZE(smartq7_buttons),
};
static struct platform_device smartq7_buttons_device = {
.name = "gpio-keys",
.id = 0,
.num_resources = 0,
.dev = {
.platform_data = &smartq7_buttons_data,
}
};
static struct s3c_fb_pd_win smartq7_fb_win0 = {
.max_bpp = 32,
.default_bpp = 16,
.xres = 800,
.yres = 480,
};
static struct fb_videomode smartq7_lcd_timing = {
.left_margin = 3,
.right_margin = 5,
.upper_margin = 1,
.lower_margin = 20,
.hsync_len = 10,
.vsync_len = 3,
.xres = 800,
.yres = 480,
.refresh = 80,
};
static struct s3c_fb_platdata smartq7_lcd_pdata __initdata = {
.setup_gpio = s3c64xx_fb_gpio_setup_24bpp,
.vtiming = &smartq7_lcd_timing,
.win[0] = &smartq7_fb_win0,
.vidcon0 = VIDCON0_VIDOUT_RGB | VIDCON0_PNRMODE_RGB,
.vidcon1 = VIDCON1_INV_HSYNC | VIDCON1_INV_VSYNC |
VIDCON1_INV_VCLK,
};
static struct platform_device *smartq7_devices[] __initdata = {
&smartq7_leds_device,
&smartq7_buttons_device,
};
static void __init smartq7_machine_init(void)
{
s3c_fb_set_platdata(&smartq7_lcd_pdata);
smartq_machine_init();
platform_add_devices(smartq7_devices, ARRAY_SIZE(smartq7_devices));
}
MACHINE_START(SMARTQ7, "SmartQ 7")
/* Maintainer: Maurus Cuelenaere <mcuelenaere AT gmail DOT com> */
.atag_offset = 0x100,
.init_irq = s3c6410_init_irq,
.map_io = smartq_map_io,
.init_machine = smartq7_machine_init,
.init_time = samsung_timer_init,
.restart = s3c64xx_restart,
MACHINE_END

View file

@ -0,0 +1,97 @@
/* linux/arch/arm/mach-s3c64xx/mach-smdk6400.c
*
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/interrupt.h>
#include <linux/list.h>
#include <linux/timer.h>
#include <linux/init.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/platform_device.h>
#include <linux/i2c.h>
#include <linux/io.h>
#include <asm/mach-types.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <asm/mach/irq.h>
#include <mach/hardware.h>
#include <mach/map.h>
#include <plat/devs.h>
#include <plat/cpu.h>
#include <linux/platform_data/i2c-s3c2410.h>
#include <mach/gpio-samsung.h>
#include <plat/samsung-time.h>
#include "common.h"
#define UCON S3C2410_UCON_DEFAULT | S3C2410_UCON_UCLK
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
static struct s3c2410_uartcfg smdk6400_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,
.ucon = 0x3c5,
.ulcon = 0x03,
.ufcon = 0x51,
},
[1] = {
.hwport = 1,
.flags = 0,
.ucon = 0x3c5,
.ulcon = 0x03,
.ufcon = 0x51,
},
};
static struct map_desc smdk6400_iodesc[] = {};
static void __init smdk6400_map_io(void)
{
s3c64xx_init_io(smdk6400_iodesc, ARRAY_SIZE(smdk6400_iodesc));
s3c64xx_set_xtal_freq(12000000);
s3c24xx_init_uarts(smdk6400_uartcfgs, ARRAY_SIZE(smdk6400_uartcfgs));
samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
}
static struct platform_device *smdk6400_devices[] __initdata = {
&s3c_device_hsmmc1,
&s3c_device_i2c0,
};
static struct i2c_board_info i2c_devs[] __initdata = {
{ I2C_BOARD_INFO("wm8753", 0x1A), },
{ I2C_BOARD_INFO("24c08", 0x50), },
};
static void __init smdk6400_machine_init(void)
{
i2c_register_board_info(0, i2c_devs, ARRAY_SIZE(i2c_devs));
platform_add_devices(smdk6400_devices, ARRAY_SIZE(smdk6400_devices));
}
MACHINE_START(SMDK6400, "SMDK6400")
/* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.atag_offset = 0x100,
.init_irq = s3c6400_init_irq,
.map_io = smdk6400_map_io,
.init_machine = smdk6400_machine_init,
.init_time = samsung_timer_init,
.restart = s3c64xx_restart,
MACHINE_END

View file

@ -0,0 +1,710 @@
/* linux/arch/arm/mach-s3c64xx/mach-smdk6410.c
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/interrupt.h>
#include <linux/list.h>
#include <linux/timer.h>
#include <linux/init.h>
#include <linux/input.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/platform_device.h>
#include <linux/io.h>
#include <linux/i2c.h>
#include <linux/leds.h>
#include <linux/fb.h>
#include <linux/gpio.h>
#include <linux/delay.h>
#include <linux/smsc911x.h>
#include <linux/regulator/fixed.h>
#include <linux/regulator/machine.h>
#include <linux/pwm_backlight.h>
#include <linux/platform_data/s3c-hsotg.h>
#ifdef CONFIG_SMDK6410_WM1190_EV1
#include <linux/mfd/wm8350/core.h>
#include <linux/mfd/wm8350/pmic.h>
#endif
#ifdef CONFIG_SMDK6410_WM1192_EV1
#include <linux/mfd/wm831x/core.h>
#include <linux/mfd/wm831x/pdata.h>
#endif
#include <video/platform_lcd.h>
#include <video/samsung_fimd.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <asm/mach/irq.h>
#include <mach/hardware.h>
#include <mach/map.h>
#include <asm/irq.h>
#include <asm/mach-types.h>
#include <mach/regs-gpio.h>
#include <mach/gpio-samsung.h>
#include <linux/platform_data/ata-samsung_cf.h>
#include <linux/platform_data/i2c-s3c2410.h>
#include <plat/fb.h>
#include <plat/gpio-cfg.h>
#include <plat/devs.h>
#include <plat/cpu.h>
#include <plat/adc.h>
#include <linux/platform_data/touchscreen-s3c2410.h>
#include <plat/keypad.h>
#include <plat/backlight.h>
#include <plat/samsung-time.h>
#include "common.h"
#include "regs-modem.h"
#include "regs-srom.h"
#include "regs-sys.h"
#define UCON S3C2410_UCON_DEFAULT | S3C2410_UCON_UCLK
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
static struct s3c2410_uartcfg smdk6410_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[1] = {
.hwport = 1,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[2] = {
.hwport = 2,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
[3] = {
.hwport = 3,
.flags = 0,
.ucon = UCON,
.ulcon = ULCON,
.ufcon = UFCON,
},
};
/* framebuffer and LCD setup. */
/* GPF15 = LCD backlight control
* GPF13 => Panel power
* GPN5 = LCD nRESET signal
* PWM_TOUT1 => backlight brightness
*/
static void smdk6410_lcd_power_set(struct plat_lcd_data *pd,
unsigned int power)
{
if (power) {
gpio_direction_output(S3C64XX_GPF(13), 1);
/* fire nRESET on power up */
gpio_direction_output(S3C64XX_GPN(5), 0);
msleep(10);
gpio_direction_output(S3C64XX_GPN(5), 1);
msleep(1);
} else {
gpio_direction_output(S3C64XX_GPF(13), 0);
}
}
static struct plat_lcd_data smdk6410_lcd_power_data = {
.set_power = smdk6410_lcd_power_set,
};
static struct platform_device smdk6410_lcd_powerdev = {
.name = "platform-lcd",
.dev.parent = &s3c_device_fb.dev,
.dev.platform_data = &smdk6410_lcd_power_data,
};
static struct s3c_fb_pd_win smdk6410_fb_win0 = {
.max_bpp = 32,
.default_bpp = 16,
.xres = 800,
.yres = 480,
.virtual_y = 480 * 2,
.virtual_x = 800,
};
static struct fb_videomode smdk6410_lcd_timing = {
.left_margin = 8,
.right_margin = 13,
.upper_margin = 7,
.lower_margin = 5,
.hsync_len = 3,
.vsync_len = 1,
.xres = 800,
.yres = 480,
};
/* 405566 clocks per frame => 60Hz refresh requires 24333960Hz clock */
static struct s3c_fb_platdata smdk6410_lcd_pdata __initdata = {
.setup_gpio = s3c64xx_fb_gpio_setup_24bpp,
.vtiming = &smdk6410_lcd_timing,
.win[0] = &smdk6410_fb_win0,
.vidcon0 = VIDCON0_VIDOUT_RGB | VIDCON0_PNRMODE_RGB,
.vidcon1 = VIDCON1_INV_HSYNC | VIDCON1_INV_VSYNC,
};
/*
* Configuring Ethernet on SMDK6410
*
* Both CS8900A and LAN9115 chips share one chip select mediated by CFG6.
* The constant address below corresponds to nCS1
*
* 1) Set CFGB2 p3 ON others off, no other CFGB selects "ethernet"
* 2) CFG6 needs to be switched to "LAN9115" side
*/
static struct resource smdk6410_smsc911x_resources[] = {
[0] = DEFINE_RES_MEM(S3C64XX_PA_XM0CSN1, SZ_64K),
[1] = DEFINE_RES_NAMED(S3C_EINT(10), 1, NULL, IORESOURCE_IRQ \
| IRQ_TYPE_LEVEL_LOW),
};
static struct smsc911x_platform_config smdk6410_smsc911x_pdata = {
.irq_polarity = SMSC911X_IRQ_POLARITY_ACTIVE_LOW,
.irq_type = SMSC911X_IRQ_TYPE_OPEN_DRAIN,
.flags = SMSC911X_USE_32BIT | SMSC911X_FORCE_INTERNAL_PHY,
.phy_interface = PHY_INTERFACE_MODE_MII,
};
static struct platform_device smdk6410_smsc911x = {
.name = "smsc911x",
.id = -1,
.num_resources = ARRAY_SIZE(smdk6410_smsc911x_resources),
.resource = &smdk6410_smsc911x_resources[0],
.dev = {
.platform_data = &smdk6410_smsc911x_pdata,
},
};
#ifdef CONFIG_REGULATOR
static struct regulator_consumer_supply smdk6410_b_pwr_5v_consumers[] __initdata = {
REGULATOR_SUPPLY("PVDD", "0-001b"),
REGULATOR_SUPPLY("AVDD", "0-001b"),
};
static struct regulator_init_data smdk6410_b_pwr_5v_data = {
.constraints = {
.always_on = 1,
},
.num_consumer_supplies = ARRAY_SIZE(smdk6410_b_pwr_5v_consumers),
.consumer_supplies = smdk6410_b_pwr_5v_consumers,
};
static struct fixed_voltage_config smdk6410_b_pwr_5v_pdata = {
.supply_name = "B_PWR_5V",
.microvolts = 5000000,
.init_data = &smdk6410_b_pwr_5v_data,
.gpio = -EINVAL,
};
static struct platform_device smdk6410_b_pwr_5v = {
.name = "reg-fixed-voltage",
.id = -1,
.dev = {
.platform_data = &smdk6410_b_pwr_5v_pdata,
},
};
#endif
static struct s3c_ide_platdata smdk6410_ide_pdata __initdata = {
.setup_gpio = s3c64xx_ide_setup_gpio,
};
static uint32_t smdk6410_keymap[] __initdata = {
/* KEY(row, col, keycode) */
KEY(0, 3, KEY_1), KEY(0, 4, KEY_2), KEY(0, 5, KEY_3),
KEY(0, 6, KEY_4), KEY(0, 7, KEY_5),
KEY(1, 3, KEY_A), KEY(1, 4, KEY_B), KEY(1, 5, KEY_C),
KEY(1, 6, KEY_D), KEY(1, 7, KEY_E)
};
static struct matrix_keymap_data smdk6410_keymap_data __initdata = {
.keymap = smdk6410_keymap,
.keymap_size = ARRAY_SIZE(smdk6410_keymap),
};
static struct samsung_keypad_platdata smdk6410_keypad_data __initdata = {
.keymap_data = &smdk6410_keymap_data,
.rows = 2,
.cols = 8,
};
static struct map_desc smdk6410_iodesc[] = {};
static struct platform_device *smdk6410_devices[] __initdata = {
#ifdef CONFIG_SMDK6410_SD_CH0
&s3c_device_hsmmc0,
#endif
#ifdef CONFIG_SMDK6410_SD_CH1
&s3c_device_hsmmc1,
#endif
&s3c_device_i2c0,
&s3c_device_i2c1,
&s3c_device_fb,
&s3c_device_ohci,
&samsung_device_pwm,
&s3c_device_usb_hsotg,
&s3c64xx_device_iisv4,
&samsung_device_keypad,
#ifdef CONFIG_REGULATOR
&smdk6410_b_pwr_5v,
#endif
&smdk6410_lcd_powerdev,
&smdk6410_smsc911x,
&s3c_device_adc,
&s3c_device_cfcon,
&s3c_device_rtc,
&s3c_device_ts,
&s3c_device_wdt,
};
#ifdef CONFIG_REGULATOR
/* ARM core */
static struct regulator_consumer_supply smdk6410_vddarm_consumers[] = {
REGULATOR_SUPPLY("vddarm", NULL),
};
/* VDDARM, BUCK1 on J5 */
static struct regulator_init_data smdk6410_vddarm = {
.constraints = {
.name = "PVDD_ARM",
.min_uV = 1000000,
.max_uV = 1300000,
.always_on = 1,
.valid_ops_mask = REGULATOR_CHANGE_VOLTAGE,
},
.num_consumer_supplies = ARRAY_SIZE(smdk6410_vddarm_consumers),
.consumer_supplies = smdk6410_vddarm_consumers,
};
/* VDD_INT, BUCK2 on J5 */
static struct regulator_init_data smdk6410_vddint = {
.constraints = {
.name = "PVDD_INT",
.min_uV = 1000000,
.max_uV = 1200000,
.always_on = 1,
.valid_ops_mask = REGULATOR_CHANGE_VOLTAGE,
},
};
/* VDD_HI, LDO3 on J5 */
static struct regulator_init_data smdk6410_vddhi = {
.constraints = {
.name = "PVDD_HI",
.always_on = 1,
},
};
/* VDD_PLL, LDO2 on J5 */
static struct regulator_init_data smdk6410_vddpll = {
.constraints = {
.name = "PVDD_PLL",
.always_on = 1,
},
};
/* VDD_UH_MMC, LDO5 on J5 */
static struct regulator_init_data smdk6410_vdduh_mmc = {
.constraints = {
.name = "PVDD_UH+PVDD_MMC",
.always_on = 1,
},
};
/* VCCM3BT, LDO8 on J5 */
static struct regulator_init_data smdk6410_vccmc3bt = {
.constraints = {
.name = "PVCCM3BT",
.always_on = 1,
},
};
/* VCCM2MTV, LDO11 on J5 */
static struct regulator_init_data smdk6410_vccm2mtv = {
.constraints = {
.name = "PVCCM2MTV",
.always_on = 1,
},
};
/* VDD_LCD, LDO12 on J5 */
static struct regulator_init_data smdk6410_vddlcd = {
.constraints = {
.name = "PVDD_LCD",
.always_on = 1,
},
};
/* VDD_OTGI, LDO9 on J5 */
static struct regulator_init_data smdk6410_vddotgi = {
.constraints = {
.name = "PVDD_OTGI",
.always_on = 1,
},
};
/* VDD_OTG, LDO14 on J5 */
static struct regulator_init_data smdk6410_vddotg = {
.constraints = {
.name = "PVDD_OTG",
.always_on = 1,
},
};
/* VDD_ALIVE, LDO15 on J5 */
static struct regulator_init_data smdk6410_vddalive = {
.constraints = {
.name = "PVDD_ALIVE",
.always_on = 1,
},
};
/* VDD_AUDIO, VLDO_AUDIO on J5 */
static struct regulator_init_data smdk6410_vddaudio = {
.constraints = {
.name = "PVDD_AUDIO",
.always_on = 1,
},
};
#endif
#ifdef CONFIG_SMDK6410_WM1190_EV1
/* S3C64xx internal logic & PLL */
static struct regulator_init_data wm8350_dcdc1_data = {
.constraints = {
.name = "PVDD_INT+PVDD_PLL",
.min_uV = 1200000,
.max_uV = 1200000,
.always_on = 1,
.apply_uV = 1,
},
};
/* Memory */
static struct regulator_init_data wm8350_dcdc3_data = {
.constraints = {
.name = "PVDD_MEM",
.min_uV = 1800000,
.max_uV = 1800000,
.always_on = 1,
.state_mem = {
.uV = 1800000,
.mode = REGULATOR_MODE_NORMAL,
.enabled = 1,
},
.initial_state = PM_SUSPEND_MEM,
},
};
/* USB, EXT, PCM, ADC/DAC, USB, MMC */
static struct regulator_consumer_supply wm8350_dcdc4_consumers[] = {
REGULATOR_SUPPLY("DVDD", "0-001b"),
};
static struct regulator_init_data wm8350_dcdc4_data = {
.constraints = {
.name = "PVDD_HI+PVDD_EXT+PVDD_SYS+PVCCM2MTV",
.min_uV = 3000000,
.max_uV = 3000000,
.always_on = 1,
},
.num_consumer_supplies = ARRAY_SIZE(wm8350_dcdc4_consumers),
.consumer_supplies = wm8350_dcdc4_consumers,
};
/* OTGi/1190-EV1 HPVDD & AVDD */
static struct regulator_init_data wm8350_ldo4_data = {
.constraints = {
.name = "PVDD_OTGI+HPVDD+AVDD",
.min_uV = 1200000,
.max_uV = 1200000,
.apply_uV = 1,
.always_on = 1,
},
};
static struct {
int regulator;
struct regulator_init_data *initdata;
} wm1190_regulators[] = {
{ WM8350_DCDC_1, &wm8350_dcdc1_data },
{ WM8350_DCDC_3, &wm8350_dcdc3_data },
{ WM8350_DCDC_4, &wm8350_dcdc4_data },
{ WM8350_DCDC_6, &smdk6410_vddarm },
{ WM8350_LDO_1, &smdk6410_vddalive },
{ WM8350_LDO_2, &smdk6410_vddotg },
{ WM8350_LDO_3, &smdk6410_vddlcd },
{ WM8350_LDO_4, &wm8350_ldo4_data },
};
static int __init smdk6410_wm8350_init(struct wm8350 *wm8350)
{
int i;
/* Configure the IRQ line */
s3c_gpio_setpull(S3C64XX_GPN(12), S3C_GPIO_PULL_UP);
/* Instantiate the regulators */
for (i = 0; i < ARRAY_SIZE(wm1190_regulators); i++)
wm8350_register_regulator(wm8350,
wm1190_regulators[i].regulator,
wm1190_regulators[i].initdata);
return 0;
}
static struct wm8350_platform_data __initdata smdk6410_wm8350_pdata = {
.init = smdk6410_wm8350_init,
.irq_high = 1,
.irq_base = IRQ_BOARD_START,
};
#endif
#ifdef CONFIG_SMDK6410_WM1192_EV1
static struct gpio_led wm1192_pmic_leds[] = {
{
.name = "PMIC:red:power",
.gpio = GPIO_BOARD_START + 3,
.default_state = LEDS_GPIO_DEFSTATE_ON,
},
};
static struct gpio_led_platform_data wm1192_pmic_led = {
.num_leds = ARRAY_SIZE(wm1192_pmic_leds),
.leds = wm1192_pmic_leds,
};
static struct platform_device wm1192_pmic_led_dev = {
.name = "leds-gpio",
.id = -1,
.dev = {
.platform_data = &wm1192_pmic_led,
},
};
static int wm1192_pre_init(struct wm831x *wm831x)
{
int ret;
/* Configure the IRQ line */
s3c_gpio_setpull(S3C64XX_GPN(12), S3C_GPIO_PULL_UP);
ret = platform_device_register(&wm1192_pmic_led_dev);
if (ret != 0)
dev_err(wm831x->dev, "Failed to add PMIC LED: %d\n", ret);
return 0;
}
static struct wm831x_backlight_pdata wm1192_backlight_pdata = {
.isink = 1,
.max_uA = 27554,
};
static struct regulator_init_data wm1192_dcdc3 = {
.constraints = {
.name = "PVDD_MEM+PVDD_GPS",
.always_on = 1,
},
};
static struct regulator_consumer_supply wm1192_ldo1_consumers[] = {
REGULATOR_SUPPLY("DVDD", "0-001b"), /* WM8580 */
};
static struct regulator_init_data wm1192_ldo1 = {
.constraints = {
.name = "PVDD_LCD+PVDD_EXT",
.always_on = 1,
},
.consumer_supplies = wm1192_ldo1_consumers,
.num_consumer_supplies = ARRAY_SIZE(wm1192_ldo1_consumers),
};
static struct wm831x_status_pdata wm1192_led7_pdata = {
.name = "LED7:green:",
};
static struct wm831x_status_pdata wm1192_led8_pdata = {
.name = "LED8:green:",
};
static struct wm831x_pdata smdk6410_wm1192_pdata = {
.pre_init = wm1192_pre_init,
.backlight = &wm1192_backlight_pdata,
.dcdc = {
&smdk6410_vddarm, /* DCDC1 */
&smdk6410_vddint, /* DCDC2 */
&wm1192_dcdc3,
},
.gpio_base = GPIO_BOARD_START,
.ldo = {
&wm1192_ldo1, /* LDO1 */
&smdk6410_vdduh_mmc, /* LDO2 */
NULL, /* LDO3 NC */
&smdk6410_vddotgi, /* LDO4 */
&smdk6410_vddotg, /* LDO5 */
&smdk6410_vddhi, /* LDO6 */
&smdk6410_vddaudio, /* LDO7 */
&smdk6410_vccm2mtv, /* LDO8 */
&smdk6410_vddpll, /* LDO9 */
&smdk6410_vccmc3bt, /* LDO10 */
&smdk6410_vddalive, /* LDO11 */
},
.status = {
&wm1192_led7_pdata,
&wm1192_led8_pdata,
},
};
#endif
static struct i2c_board_info i2c_devs0[] __initdata = {
{ I2C_BOARD_INFO("24c08", 0x50), },
{ I2C_BOARD_INFO("wm8580", 0x1b), },
#ifdef CONFIG_SMDK6410_WM1192_EV1
{ I2C_BOARD_INFO("wm8312", 0x34),
.platform_data = &smdk6410_wm1192_pdata,
.irq = S3C_EINT(12),
},
#endif
#ifdef CONFIG_SMDK6410_WM1190_EV1
{ I2C_BOARD_INFO("wm8350", 0x1a),
.platform_data = &smdk6410_wm8350_pdata,
.irq = S3C_EINT(12),
},
#endif
};
static struct i2c_board_info i2c_devs1[] __initdata = {
{ I2C_BOARD_INFO("24c128", 0x57), }, /* Samsung S524AD0XD1 */
};
/* LCD Backlight data */
static struct samsung_bl_gpio_info smdk6410_bl_gpio_info = {
.no = S3C64XX_GPF(15),
.func = S3C_GPIO_SFN(2),
};
static struct platform_pwm_backlight_data smdk6410_bl_data = {
.pwm_id = 1,
.enable_gpio = -1,
};
static struct s3c_hsotg_plat smdk6410_hsotg_pdata;
static void __init smdk6410_map_io(void)
{
u32 tmp;
s3c64xx_init_io(smdk6410_iodesc, ARRAY_SIZE(smdk6410_iodesc));
s3c64xx_set_xtal_freq(12000000);
s3c24xx_init_uarts(smdk6410_uartcfgs, ARRAY_SIZE(smdk6410_uartcfgs));
samsung_set_timer_source(SAMSUNG_PWM3, SAMSUNG_PWM4);
/* set the LCD type */
tmp = __raw_readl(S3C64XX_SPCON);
tmp &= ~S3C64XX_SPCON_LCD_SEL_MASK;
tmp |= S3C64XX_SPCON_LCD_SEL_RGB;
__raw_writel(tmp, S3C64XX_SPCON);
/* remove the lcd bypass */
tmp = __raw_readl(S3C64XX_MODEM_MIFPCON);
tmp &= ~MIFPCON_LCD_BYPASS;
__raw_writel(tmp, S3C64XX_MODEM_MIFPCON);
}
static void __init smdk6410_machine_init(void)
{
u32 cs1;
s3c_i2c0_set_platdata(NULL);
s3c_i2c1_set_platdata(NULL);
s3c_fb_set_platdata(&smdk6410_lcd_pdata);
s3c_hsotg_set_platdata(&smdk6410_hsotg_pdata);
samsung_keypad_set_platdata(&smdk6410_keypad_data);
s3c24xx_ts_set_platdata(NULL);
/* configure nCS1 width to 16 bits */
cs1 = __raw_readl(S3C64XX_SROM_BW) &
~(S3C64XX_SROM_BW__CS_MASK << S3C64XX_SROM_BW__NCS1__SHIFT);
cs1 |= ((1 << S3C64XX_SROM_BW__DATAWIDTH__SHIFT) |
(1 << S3C64XX_SROM_BW__WAITENABLE__SHIFT) |
(1 << S3C64XX_SROM_BW__BYTEENABLE__SHIFT)) <<
S3C64XX_SROM_BW__NCS1__SHIFT;
__raw_writel(cs1, S3C64XX_SROM_BW);
/* set timing for nCS1 suitable for ethernet chip */
__raw_writel((0 << S3C64XX_SROM_BCX__PMC__SHIFT) |
(6 << S3C64XX_SROM_BCX__TACP__SHIFT) |
(4 << S3C64XX_SROM_BCX__TCAH__SHIFT) |
(1 << S3C64XX_SROM_BCX__TCOH__SHIFT) |
(0xe << S3C64XX_SROM_BCX__TACC__SHIFT) |
(4 << S3C64XX_SROM_BCX__TCOS__SHIFT) |
(0 << S3C64XX_SROM_BCX__TACS__SHIFT), S3C64XX_SROM_BC1);
gpio_request(S3C64XX_GPN(5), "LCD power");
gpio_request(S3C64XX_GPF(13), "LCD power");
i2c_register_board_info(0, i2c_devs0, ARRAY_SIZE(i2c_devs0));
i2c_register_board_info(1, i2c_devs1, ARRAY_SIZE(i2c_devs1));
s3c_ide_set_platdata(&smdk6410_ide_pdata);
platform_add_devices(smdk6410_devices, ARRAY_SIZE(smdk6410_devices));
samsung_bl_set(&smdk6410_bl_gpio_info, &smdk6410_bl_data);
}
MACHINE_START(SMDK6410, "SMDK6410")
/* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.atag_offset = 0x100,
.init_irq = s3c6410_init_irq,
.map_io = smdk6410_map_io,
.init_machine = smdk6410_machine_init,
.init_time = samsung_timer_init,
.restart = s3c64xx_restart,
MACHINE_END

View file

@ -0,0 +1,244 @@
/*
* Samsung's S3C64XX generic DMA support using amba-pl08x driver.
*
* Copyright (c) 2013 Tomasz Figa <tomasz.figa@gmail.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/kernel.h>
#include <linux/amba/bus.h>
#include <linux/amba/pl080.h>
#include <linux/amba/pl08x.h>
#include <linux/of.h>
#include <mach/irqs.h>
#include <mach/map.h>
#include "regs-sys.h"
static int pl08x_get_xfer_signal(const struct pl08x_channel_data *cd)
{
return cd->min_signal;
}
static void pl08x_put_xfer_signal(const struct pl08x_channel_data *cd, int ch)
{
}
/*
* DMA0
*/
static struct pl08x_channel_data s3c64xx_dma0_info[] = {
{
.bus_id = "uart0_tx",
.min_signal = 0,
.max_signal = 0,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "uart0_rx",
.min_signal = 1,
.max_signal = 1,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "uart1_tx",
.min_signal = 2,
.max_signal = 2,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "uart1_rx",
.min_signal = 3,
.max_signal = 3,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "uart2_tx",
.min_signal = 4,
.max_signal = 4,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "uart2_rx",
.min_signal = 5,
.max_signal = 5,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "uart3_tx",
.min_signal = 6,
.max_signal = 6,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "uart3_rx",
.min_signal = 7,
.max_signal = 7,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "pcm0_tx",
.min_signal = 8,
.max_signal = 8,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "pcm0_rx",
.min_signal = 9,
.max_signal = 9,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "i2s0_tx",
.min_signal = 10,
.max_signal = 10,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "i2s0_rx",
.min_signal = 11,
.max_signal = 11,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "spi0_tx",
.min_signal = 12,
.max_signal = 12,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "spi0_rx",
.min_signal = 13,
.max_signal = 13,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "i2s2_tx",
.min_signal = 14,
.max_signal = 14,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "i2s2_rx",
.min_signal = 15,
.max_signal = 15,
.periph_buses = PL08X_AHB2,
}
};
struct pl08x_platform_data s3c64xx_dma0_plat_data = {
.memcpy_channel = {
.bus_id = "memcpy",
.cctl_memcpy =
(PL080_BSIZE_4 << PL080_CONTROL_SB_SIZE_SHIFT |
PL080_BSIZE_4 << PL080_CONTROL_DB_SIZE_SHIFT |
PL080_WIDTH_32BIT << PL080_CONTROL_SWIDTH_SHIFT |
PL080_WIDTH_32BIT << PL080_CONTROL_DWIDTH_SHIFT |
PL080_CONTROL_PROT_BUFF | PL080_CONTROL_PROT_CACHE |
PL080_CONTROL_PROT_SYS),
},
.lli_buses = PL08X_AHB1,
.mem_buses = PL08X_AHB1,
.get_xfer_signal = pl08x_get_xfer_signal,
.put_xfer_signal = pl08x_put_xfer_signal,
.slave_channels = s3c64xx_dma0_info,
.num_slave_channels = ARRAY_SIZE(s3c64xx_dma0_info),
};
static AMBA_AHB_DEVICE(s3c64xx_dma0, "dma-pl080s.0", 0,
0x75000000, {IRQ_DMA0}, &s3c64xx_dma0_plat_data);
/*
* DMA1
*/
static struct pl08x_channel_data s3c64xx_dma1_info[] = {
{
.bus_id = "pcm1_tx",
.min_signal = 0,
.max_signal = 0,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "pcm1_rx",
.min_signal = 1,
.max_signal = 1,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "i2s1_tx",
.min_signal = 2,
.max_signal = 2,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "i2s1_rx",
.min_signal = 3,
.max_signal = 3,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "spi1_tx",
.min_signal = 4,
.max_signal = 4,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "spi1_rx",
.min_signal = 5,
.max_signal = 5,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "ac97_out",
.min_signal = 6,
.max_signal = 6,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "ac97_in",
.min_signal = 7,
.max_signal = 7,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "ac97_mic",
.min_signal = 8,
.max_signal = 8,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "pwm",
.min_signal = 9,
.max_signal = 9,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "irda",
.min_signal = 10,
.max_signal = 10,
.periph_buses = PL08X_AHB2,
}, {
.bus_id = "external",
.min_signal = 11,
.max_signal = 11,
.periph_buses = PL08X_AHB2,
},
};
struct pl08x_platform_data s3c64xx_dma1_plat_data = {
.memcpy_channel = {
.bus_id = "memcpy",
.cctl_memcpy =
(PL080_BSIZE_4 << PL080_CONTROL_SB_SIZE_SHIFT |
PL080_BSIZE_4 << PL080_CONTROL_DB_SIZE_SHIFT |
PL080_WIDTH_32BIT << PL080_CONTROL_SWIDTH_SHIFT |
PL080_WIDTH_32BIT << PL080_CONTROL_DWIDTH_SHIFT |
PL080_CONTROL_PROT_BUFF | PL080_CONTROL_PROT_CACHE |
PL080_CONTROL_PROT_SYS),
},
.lli_buses = PL08X_AHB1,
.mem_buses = PL08X_AHB1,
.get_xfer_signal = pl08x_get_xfer_signal,
.put_xfer_signal = pl08x_put_xfer_signal,
.slave_channels = s3c64xx_dma1_info,
.num_slave_channels = ARRAY_SIZE(s3c64xx_dma1_info),
};
static AMBA_AHB_DEVICE(s3c64xx_dma1, "dma-pl080s.1", 0,
0x75100000, {IRQ_DMA1}, &s3c64xx_dma1_plat_data);
static int __init s3c64xx_pl080_init(void)
{
/* Set all DMA configuration to be DMA, not SDMA */
writel(0xffffff, S3C64XX_SDMA_SEL);
if (of_have_populated_dt())
return 0;
amba_device_register(&s3c64xx_dma0_device, &iomem_resource);
amba_device_register(&s3c64xx_dma1_device, &iomem_resource);
return 0;
}
arch_initcall(s3c64xx_pl080_init);

349
arch/arm/mach-s3c64xx/pm.c Normal file
View file

@ -0,0 +1,349 @@
/* linux/arch/arm/plat-s3c64xx/pm.c
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C64XX CPU PM support.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/init.h>
#include <linux/suspend.h>
#include <linux/serial_core.h>
#include <linux/io.h>
#include <linux/gpio.h>
#include <linux/pm_domain.h>
#include <mach/map.h>
#include <mach/irqs.h>
#include <plat/devs.h>
#include <plat/pm.h>
#include <plat/wakeup-mask.h>
#include <mach/regs-gpio.h>
#include <mach/regs-clock.h>
#include <mach/gpio-samsung.h>
#include "regs-gpio-memport.h"
#include "regs-modem.h"
#include "regs-sys.h"
#include "regs-syscon-power.h"
struct s3c64xx_pm_domain {
char *const name;
u32 ena;
u32 pwr_stat;
struct generic_pm_domain pd;
};
static int s3c64xx_pd_off(struct generic_pm_domain *domain)
{
struct s3c64xx_pm_domain *pd;
u32 val;
pd = container_of(domain, struct s3c64xx_pm_domain, pd);
val = __raw_readl(S3C64XX_NORMAL_CFG);
val &= ~(pd->ena);
__raw_writel(val, S3C64XX_NORMAL_CFG);
return 0;
}
static int s3c64xx_pd_on(struct generic_pm_domain *domain)
{
struct s3c64xx_pm_domain *pd;
u32 val;
long retry = 1000000L;
pd = container_of(domain, struct s3c64xx_pm_domain, pd);
val = __raw_readl(S3C64XX_NORMAL_CFG);
val |= pd->ena;
__raw_writel(val, S3C64XX_NORMAL_CFG);
/* Not all domains provide power status readback */
if (pd->pwr_stat) {
do {
cpu_relax();
if (__raw_readl(S3C64XX_BLK_PWR_STAT) & pd->pwr_stat)
break;
} while (retry--);
if (!retry) {
pr_err("Failed to start domain %s\n", pd->name);
return -EBUSY;
}
}
return 0;
}
static struct s3c64xx_pm_domain s3c64xx_pm_irom = {
.name = "IROM",
.ena = S3C64XX_NORMALCFG_IROM_ON,
.pd = {
.power_off = s3c64xx_pd_off,
.power_on = s3c64xx_pd_on,
},
};
static struct s3c64xx_pm_domain s3c64xx_pm_etm = {
.name = "ETM",
.ena = S3C64XX_NORMALCFG_DOMAIN_ETM_ON,
.pwr_stat = S3C64XX_BLKPWRSTAT_ETM,
.pd = {
.power_off = s3c64xx_pd_off,
.power_on = s3c64xx_pd_on,
},
};
static struct s3c64xx_pm_domain s3c64xx_pm_s = {
.name = "S",
.ena = S3C64XX_NORMALCFG_DOMAIN_S_ON,
.pwr_stat = S3C64XX_BLKPWRSTAT_S,
.pd = {
.power_off = s3c64xx_pd_off,
.power_on = s3c64xx_pd_on,
},
};
static struct s3c64xx_pm_domain s3c64xx_pm_f = {
.name = "F",
.ena = S3C64XX_NORMALCFG_DOMAIN_F_ON,
.pwr_stat = S3C64XX_BLKPWRSTAT_F,
.pd = {
.power_off = s3c64xx_pd_off,
.power_on = s3c64xx_pd_on,
},
};
static struct s3c64xx_pm_domain s3c64xx_pm_p = {
.name = "P",
.ena = S3C64XX_NORMALCFG_DOMAIN_P_ON,
.pwr_stat = S3C64XX_BLKPWRSTAT_P,
.pd = {
.power_off = s3c64xx_pd_off,
.power_on = s3c64xx_pd_on,
},
};
static struct s3c64xx_pm_domain s3c64xx_pm_i = {
.name = "I",
.ena = S3C64XX_NORMALCFG_DOMAIN_I_ON,
.pwr_stat = S3C64XX_BLKPWRSTAT_I,
.pd = {
.power_off = s3c64xx_pd_off,
.power_on = s3c64xx_pd_on,
},
};
static struct s3c64xx_pm_domain s3c64xx_pm_g = {
.name = "G",
.ena = S3C64XX_NORMALCFG_DOMAIN_G_ON,
.pd = {
.power_off = s3c64xx_pd_off,
.power_on = s3c64xx_pd_on,
},
};
static struct s3c64xx_pm_domain s3c64xx_pm_v = {
.name = "V",
.ena = S3C64XX_NORMALCFG_DOMAIN_V_ON,
.pwr_stat = S3C64XX_BLKPWRSTAT_V,
.pd = {
.power_off = s3c64xx_pd_off,
.power_on = s3c64xx_pd_on,
},
};
static struct s3c64xx_pm_domain *s3c64xx_always_on_pm_domains[] = {
&s3c64xx_pm_irom,
};
static struct s3c64xx_pm_domain *s3c64xx_pm_domains[] = {
&s3c64xx_pm_etm,
&s3c64xx_pm_g,
&s3c64xx_pm_v,
&s3c64xx_pm_i,
&s3c64xx_pm_p,
&s3c64xx_pm_s,
&s3c64xx_pm_f,
};
#ifdef CONFIG_S3C_PM_DEBUG_LED_SMDK
void s3c_pm_debug_smdkled(u32 set, u32 clear)
{
unsigned long flags;
int i;
local_irq_save(flags);
for (i = 0; i < 4; i++) {
if (clear & (1 << i))
gpio_set_value(S3C64XX_GPN(12 + i), 0);
if (set & (1 << i))
gpio_set_value(S3C64XX_GPN(12 + i), 1);
}
local_irq_restore(flags);
}
#endif
static struct sleep_save core_save[] = {
SAVE_ITEM(S3C64XX_MEM0DRVCON),
SAVE_ITEM(S3C64XX_MEM1DRVCON),
};
static struct sleep_save misc_save[] = {
SAVE_ITEM(S3C64XX_AHB_CON0),
SAVE_ITEM(S3C64XX_AHB_CON1),
SAVE_ITEM(S3C64XX_AHB_CON2),
SAVE_ITEM(S3C64XX_SPCON),
SAVE_ITEM(S3C64XX_MEM0CONSTOP),
SAVE_ITEM(S3C64XX_MEM1CONSTOP),
SAVE_ITEM(S3C64XX_MEM0CONSLP0),
SAVE_ITEM(S3C64XX_MEM0CONSLP1),
SAVE_ITEM(S3C64XX_MEM1CONSLP),
SAVE_ITEM(S3C64XX_SDMA_SEL),
SAVE_ITEM(S3C64XX_MODEM_MIFPCON),
SAVE_ITEM(S3C64XX_NORMAL_CFG),
};
void s3c_pm_configure_extint(void)
{
__raw_writel(s3c_irqwake_eintmask, S3C64XX_EINT_MASK);
}
void s3c_pm_restore_core(void)
{
__raw_writel(0, S3C64XX_EINT_MASK);
s3c_pm_debug_smdkled(1 << 2, 0);
s3c_pm_do_restore_core(core_save, ARRAY_SIZE(core_save));
s3c_pm_do_restore(misc_save, ARRAY_SIZE(misc_save));
}
void s3c_pm_save_core(void)
{
s3c_pm_do_save(misc_save, ARRAY_SIZE(misc_save));
s3c_pm_do_save(core_save, ARRAY_SIZE(core_save));
}
/* since both s3c6400 and s3c6410 share the same sleep pm calls, we
* put the per-cpu code in here until any new cpu comes along and changes
* this.
*/
static int s3c64xx_cpu_suspend(unsigned long arg)
{
unsigned long tmp;
/* set our standby method to sleep */
tmp = __raw_readl(S3C64XX_PWR_CFG);
tmp &= ~S3C64XX_PWRCFG_CFG_WFI_MASK;
tmp |= S3C64XX_PWRCFG_CFG_WFI_SLEEP;
__raw_writel(tmp, S3C64XX_PWR_CFG);
/* clear any old wakeup */
__raw_writel(__raw_readl(S3C64XX_WAKEUP_STAT),
S3C64XX_WAKEUP_STAT);
/* set the LED state to 0110 over sleep */
s3c_pm_debug_smdkled(3 << 1, 0xf);
/* issue the standby signal into the pm unit. Note, we
* issue a write-buffer drain just in case */
tmp = 0;
asm("b 1f\n\t"
".align 5\n\t"
"1:\n\t"
"mcr p15, 0, %0, c7, c10, 5\n\t"
"mcr p15, 0, %0, c7, c10, 4\n\t"
"mcr p15, 0, %0, c7, c0, 4" :: "r" (tmp));
/* we should never get past here */
pr_info("Failed to suspend the system\n");
return 1; /* Aborting suspend */
}
/* mapping of interrupts to parts of the wakeup mask */
static struct samsung_wakeup_mask wake_irqs[] = {
{ .irq = IRQ_RTC_ALARM, .bit = S3C64XX_PWRCFG_RTC_ALARM_DISABLE, },
{ .irq = IRQ_RTC_TIC, .bit = S3C64XX_PWRCFG_RTC_TICK_DISABLE, },
{ .irq = IRQ_PENDN, .bit = S3C64XX_PWRCFG_TS_DISABLE, },
{ .irq = IRQ_HSMMC0, .bit = S3C64XX_PWRCFG_MMC0_DISABLE, },
{ .irq = IRQ_HSMMC1, .bit = S3C64XX_PWRCFG_MMC1_DISABLE, },
{ .irq = IRQ_HSMMC2, .bit = S3C64XX_PWRCFG_MMC2_DISABLE, },
{ .irq = NO_WAKEUP_IRQ, .bit = S3C64XX_PWRCFG_BATF_DISABLE},
{ .irq = NO_WAKEUP_IRQ, .bit = S3C64XX_PWRCFG_MSM_DISABLE },
{ .irq = NO_WAKEUP_IRQ, .bit = S3C64XX_PWRCFG_HSI_DISABLE },
{ .irq = NO_WAKEUP_IRQ, .bit = S3C64XX_PWRCFG_MSM_DISABLE },
};
static void s3c64xx_pm_prepare(void)
{
samsung_sync_wakemask(S3C64XX_PWR_CFG,
wake_irqs, ARRAY_SIZE(wake_irqs));
/* store address of resume. */
__raw_writel(virt_to_phys(s3c_cpu_resume), S3C64XX_INFORM0);
/* ensure previous wakeup state is cleared before sleeping */
__raw_writel(__raw_readl(S3C64XX_WAKEUP_STAT), S3C64XX_WAKEUP_STAT);
}
int __init s3c64xx_pm_init(void)
{
int i;
s3c_pm_init();
for (i = 0; i < ARRAY_SIZE(s3c64xx_always_on_pm_domains); i++)
pm_genpd_init(&s3c64xx_always_on_pm_domains[i]->pd,
&pm_domain_always_on_gov, false);
for (i = 0; i < ARRAY_SIZE(s3c64xx_pm_domains); i++)
pm_genpd_init(&s3c64xx_pm_domains[i]->pd, NULL, false);
#ifdef CONFIG_S3C_DEV_FB
if (dev_get_platdata(&s3c_device_fb.dev))
pm_genpd_add_device(&s3c64xx_pm_f.pd, &s3c_device_fb.dev);
#endif
return 0;
}
static __init int s3c64xx_pm_initcall(void)
{
pm_cpu_prep = s3c64xx_pm_prepare;
pm_cpu_sleep = s3c64xx_cpu_suspend;
#ifdef CONFIG_S3C_PM_DEBUG_LED_SMDK
gpio_request(S3C64XX_GPN(12), "DEBUG_LED0");
gpio_request(S3C64XX_GPN(13), "DEBUG_LED1");
gpio_request(S3C64XX_GPN(14), "DEBUG_LED2");
gpio_request(S3C64XX_GPN(15), "DEBUG_LED3");
gpio_direction_output(S3C64XX_GPN(12), 0);
gpio_direction_output(S3C64XX_GPN(13), 0);
gpio_direction_output(S3C64XX_GPN(14), 0);
gpio_direction_output(S3C64XX_GPN(15), 0);
#endif
return 0;
}
arch_initcall(s3c64xx_pm_initcall);

View file

@ -0,0 +1,24 @@
/*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C64XX - GPIO memory port register definitions
*/
#ifndef __MACH_S3C64XX_REGS_GPIO_MEMPORT_H
#define __MACH_S3C64XX_REGS_GPIO_MEMPORT_H __FILE__
#define S3C64XX_MEM0CONSTOP S3C64XX_GPIOREG(0x1B0)
#define S3C64XX_MEM1CONSTOP S3C64XX_GPIOREG(0x1B4)
#define S3C64XX_MEM0CONSLP0 S3C64XX_GPIOREG(0x1C0)
#define S3C64XX_MEM0CONSLP1 S3C64XX_GPIOREG(0x1C4)
#define S3C64XX_MEM1CONSLP S3C64XX_GPIOREG(0x1C8)
#define S3C64XX_MEM0DRVCON S3C64XX_GPIOREG(0x1D0)
#define S3C64XX_MEM1DRVCON S3C64XX_GPIOREG(0x1D4)
#endif /* __MACH_S3C64XX_REGS_GPIO_MEMPORT_H */

View file

@ -0,0 +1,30 @@
/*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* http://armlinux.simtec.co.uk/
* Ben Dooks <ben@simtec.co.uk>
*
* S3C64XX - modem block registers
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef __MACH_S3C64XX_REGS_MODEM_H
#define __MACH_S3C64XX_REGS_MODEM_H __FILE__
#define S3C64XX_MODEMREG(x) (S3C64XX_VA_MODEM + (x))
#define S3C64XX_MODEM_INT2AP S3C64XX_MODEMREG(0x0)
#define S3C64XX_MODEM_INT2MODEM S3C64XX_MODEMREG(0x4)
#define S3C64XX_MODEM_MIFCON S3C64XX_MODEMREG(0x8)
#define S3C64XX_MODEM_MIFPCON S3C64XX_MODEMREG(0xC)
#define S3C64XX_MODEM_INTCLR S3C64XX_MODEMREG(0x10)
#define S3C64XX_MODEM_DMA_TXADDR S3C64XX_MODEMREG(0x14)
#define S3C64XX_MODEM_DMA_RXADDR S3C64XX_MODEMREG(0x18)
#define MIFPCON_INT2M_LEVEL (1 << 4)
#define MIFPCON_LCD_BYPASS (1 << 3)
#endif /* __MACH_S3C64XX_REGS_MODEM_H */

View file

@ -0,0 +1,58 @@
/*
* Copyright 2009 Andy Green <andy@warmcat.com>
*
* S3C64XX SROM definitions
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef __MACH_S3C64XX_REGS_SROM_H
#define __MACH_S3C64XX_REGS_SROM_H __FILE__
#define S3C64XX_SROMREG(x) (S3C_VA_MEM + (x))
#define S3C64XX_SROM_BW S3C64XX_SROMREG(0)
#define S3C64XX_SROM_BC0 S3C64XX_SROMREG(4)
#define S3C64XX_SROM_BC1 S3C64XX_SROMREG(8)
#define S3C64XX_SROM_BC2 S3C64XX_SROMREG(0xc)
#define S3C64XX_SROM_BC3 S3C64XX_SROMREG(0x10)
#define S3C64XX_SROM_BC4 S3C64XX_SROMREG(0x14)
#define S3C64XX_SROM_BC5 S3C64XX_SROMREG(0x18)
/*
* one register BW holds 5 x 4-bit packed settings for NCS0 - NCS4
*/
#define S3C64XX_SROM_BW__DATAWIDTH__SHIFT 0
#define S3C64XX_SROM_BW__WAITENABLE__SHIFT 2
#define S3C64XX_SROM_BW__BYTEENABLE__SHIFT 3
#define S3C64XX_SROM_BW__CS_MASK 0xf
#define S3C64XX_SROM_BW__NCS0__SHIFT 0
#define S3C64XX_SROM_BW__NCS1__SHIFT 4
#define S3C64XX_SROM_BW__NCS2__SHIFT 8
#define S3C64XX_SROM_BW__NCS3__SHIFT 0xc
#define S3C64XX_SROM_BW__NCS4__SHIFT 0x10
/*
* applies to same to BCS0 - BCS4
*/
#define S3C64XX_SROM_BCX__PMC__SHIFT 0
#define S3C64XX_SROM_BCX__PMC__MASK 3
#define S3C64XX_SROM_BCX__TACP__SHIFT 4
#define S3C64XX_SROM_BCX__TACP__MASK 0xf
#define S3C64XX_SROM_BCX__TCAH__SHIFT 8
#define S3C64XX_SROM_BCX__TCAH__MASK 0xf
#define S3C64XX_SROM_BCX__TCOH__SHIFT 12
#define S3C64XX_SROM_BCX__TCOH__MASK 0xf
#define S3C64XX_SROM_BCX__TACC__SHIFT 16
#define S3C64XX_SROM_BCX__TACC__MASK 0x1f
#define S3C64XX_SROM_BCX__TCOS__SHIFT 24
#define S3C64XX_SROM_BCX__TCOS__MASK 0xf
#define S3C64XX_SROM_BCX__TACS__SHIFT 28
#define S3C64XX_SROM_BCX__TACS__MASK 0xf
#endif /* __MACH_S3C64XX_REGS_SROM_H */

View file

@ -0,0 +1,30 @@
/*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C64XX system register definitions
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef __MACH_S3C64XX_REGS_SYS_H
#define __MACH_S3C64XX_REGS_SYS_H __FILE__
#define S3C_SYSREG(x) (S3C_VA_SYS + (x))
#define S3C64XX_AHB_CON0 S3C_SYSREG(0x100)
#define S3C64XX_AHB_CON1 S3C_SYSREG(0x104)
#define S3C64XX_AHB_CON2 S3C_SYSREG(0x108)
#define S3C64XX_SDMA_SEL S3C_SYSREG(0x110)
#define S3C64XX_OTHERS S3C_SYSREG(0x900)
#define S3C64XX_OTHERS_USBMASK (1 << 16)
#define S3C64XX_OTHERS_SYNCMUXSEL (1 << 6)
#endif /* __MACH_S3C64XX_REGS_SYS_H */

View file

@ -0,0 +1,115 @@
/*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* http://armlinux.simtec.co.uk/
* Ben Dooks <ben@simtec.co.uk>
*
* S3C64XX - syscon power and sleep control registers
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#ifndef __MACH_S3C64XX_REGS_SYSCON_POWER_H
#define __MACH_S3C64XX_REGS_SYSCON_POWER_H __FILE__
#define S3C64XX_PWR_CFG S3C_SYSREG(0x804)
#define S3C64XX_PWRCFG_OSC_OTG_DISABLE (1 << 17)
#define S3C64XX_PWRCFG_MMC2_DISABLE (1 << 16)
#define S3C64XX_PWRCFG_MMC1_DISABLE (1 << 15)
#define S3C64XX_PWRCFG_MMC0_DISABLE (1 << 14)
#define S3C64XX_PWRCFG_HSI_DISABLE (1 << 13)
#define S3C64XX_PWRCFG_TS_DISABLE (1 << 12)
#define S3C64XX_PWRCFG_RTC_TICK_DISABLE (1 << 11)
#define S3C64XX_PWRCFG_RTC_ALARM_DISABLE (1 << 10)
#define S3C64XX_PWRCFG_MSM_DISABLE (1 << 9)
#define S3C64XX_PWRCFG_KEY_DISABLE (1 << 8)
#define S3C64XX_PWRCFG_BATF_DISABLE (1 << 7)
#define S3C64XX_PWRCFG_CFG_WFI_MASK (0x3 << 5)
#define S3C64XX_PWRCFG_CFG_WFI_SHIFT (5)
#define S3C64XX_PWRCFG_CFG_WFI_IGNORE (0x0 << 5)
#define S3C64XX_PWRCFG_CFG_WFI_IDLE (0x1 << 5)
#define S3C64XX_PWRCFG_CFG_WFI_STOP (0x2 << 5)
#define S3C64XX_PWRCFG_CFG_WFI_SLEEP (0x3 << 5)
#define S3C64XX_PWRCFG_CFG_BATFLT_MASK (0x3 << 3)
#define S3C64XX_PWRCFG_CFG_BATFLT_SHIFT (3)
#define S3C64XX_PWRCFG_CFG_BATFLT_IGNORE (0x0 << 3)
#define S3C64XX_PWRCFG_CFG_BATFLT_IRQ (0x1 << 3)
#define S3C64XX_PWRCFG_CFG_BATFLT_SLEEP (0x3 << 3)
#define S3C64XX_PWRCFG_CFG_BAT_WAKE (1 << 2)
#define S3C64XX_PWRCFG_OSC27_EN (1 << 0)
#define S3C64XX_EINT_MASK S3C_SYSREG(0x808)
#define S3C64XX_NORMAL_CFG S3C_SYSREG(0x810)
#define S3C64XX_NORMALCFG_IROM_ON (1 << 30)
#define S3C64XX_NORMALCFG_DOMAIN_ETM_ON (1 << 16)
#define S3C64XX_NORMALCFG_DOMAIN_S_ON (1 << 15)
#define S3C64XX_NORMALCFG_DOMAIN_F_ON (1 << 14)
#define S3C64XX_NORMALCFG_DOMAIN_P_ON (1 << 13)
#define S3C64XX_NORMALCFG_DOMAIN_I_ON (1 << 12)
#define S3C64XX_NORMALCFG_DOMAIN_G_ON (1 << 10)
#define S3C64XX_NORMALCFG_DOMAIN_V_ON (1 << 9)
#define S3C64XX_STOP_CFG S3C_SYSREG(0x814)
#define S3C64XX_STOPCFG_MEMORY_ARM_ON (1 << 29)
#define S3C64XX_STOPCFG_TOP_MEMORY_ON (1 << 20)
#define S3C64XX_STOPCFG_ARM_LOGIC_ON (1 << 17)
#define S3C64XX_STOPCFG_TOP_LOGIC_ON (1 << 8)
#define S3C64XX_STOPCFG_OSC_EN (1 << 0)
#define S3C64XX_SLEEP_CFG S3C_SYSREG(0x818)
#define S3C64XX_SLEEPCFG_OSC_EN (1 << 0)
#define S3C64XX_STOP_MEM_CFG S3C_SYSREG(0x81c)
#define S3C64XX_STOPMEMCFG_MODEMIF_RETAIN (1 << 6)
#define S3C64XX_STOPMEMCFG_HOSTIF_RETAIN (1 << 5)
#define S3C64XX_STOPMEMCFG_OTG_RETAIN (1 << 4)
#define S3C64XX_STOPMEMCFG_HSMCC_RETAIN (1 << 3)
#define S3C64XX_STOPMEMCFG_IROM_RETAIN (1 << 2)
#define S3C64XX_STOPMEMCFG_IRDA_RETAIN (1 << 1)
#define S3C64XX_STOPMEMCFG_NFCON_RETAIN (1 << 0)
#define S3C64XX_OSC_STABLE S3C_SYSREG(0x824)
#define S3C64XX_PWR_STABLE S3C_SYSREG(0x828)
#define S3C64XX_WAKEUP_STAT S3C_SYSREG(0x908)
#define S3C64XX_WAKEUPSTAT_MMC2 (1 << 11)
#define S3C64XX_WAKEUPSTAT_MMC1 (1 << 10)
#define S3C64XX_WAKEUPSTAT_MMC0 (1 << 9)
#define S3C64XX_WAKEUPSTAT_HSI (1 << 8)
#define S3C64XX_WAKEUPSTAT_BATFLT (1 << 6)
#define S3C64XX_WAKEUPSTAT_MSM (1 << 5)
#define S3C64XX_WAKEUPSTAT_KEY (1 << 4)
#define S3C64XX_WAKEUPSTAT_TS (1 << 3)
#define S3C64XX_WAKEUPSTAT_RTC_TICK (1 << 2)
#define S3C64XX_WAKEUPSTAT_RTC_ALARM (1 << 1)
#define S3C64XX_WAKEUPSTAT_EINT (1 << 0)
#define S3C64XX_BLK_PWR_STAT S3C_SYSREG(0x90c)
#define S3C64XX_BLKPWRSTAT_G (1 << 7)
#define S3C64XX_BLKPWRSTAT_ETM (1 << 6)
#define S3C64XX_BLKPWRSTAT_S (1 << 5)
#define S3C64XX_BLKPWRSTAT_F (1 << 4)
#define S3C64XX_BLKPWRSTAT_P (1 << 3)
#define S3C64XX_BLKPWRSTAT_I (1 << 2)
#define S3C64XX_BLKPWRSTAT_V (1 << 1)
#define S3C64XX_BLKPWRSTAT_TOP (1 << 0)
#define S3C64XX_INFORM0 S3C_SYSREG(0xA00)
#define S3C64XX_INFORM1 S3C_SYSREG(0xA04)
#define S3C64XX_INFORM2 S3C_SYSREG(0xA08)
#define S3C64XX_INFORM3 S3C_SYSREG(0xA0C)
#endif /* __MACH_S3C64XX_REGS_SYSCON_POWER_H */

View file

@ -0,0 +1,97 @@
/* linux/arch/arm/mach-s3c64xx/cpu.c
*
* Copyright 2009 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
/*
* NOTE: Code in this file is not used when booting with Device Tree support.
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/interrupt.h>
#include <linux/list.h>
#include <linux/timer.h>
#include <linux/init.h>
#include <linux/clk.h>
#include <linux/io.h>
#include <linux/device.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/platform_device.h>
#include <linux/of.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <asm/mach/irq.h>
#include <mach/hardware.h>
#include <asm/irq.h>
#include <plat/cpu-freq.h>
#include <mach/regs-clock.h>
#include <plat/cpu.h>
#include <plat/devs.h>
#include <plat/sdhci.h>
#include <plat/iic-core.h>
#include <plat/onenand-core.h>
#include "common.h"
void __init s3c6400_map_io(void)
{
/* setup SDHCI */
s3c6400_default_sdhci0();
s3c6400_default_sdhci1();
s3c6400_default_sdhci2();
/* the i2c devices are directly compatible with s3c2440 */
s3c_i2c0_setname("s3c2440-i2c");
s3c_device_nand.name = "s3c6400-nand";
s3c_onenand_setname("s3c6400-onenand");
s3c64xx_onenand1_setname("s3c6400-onenand");
}
void __init s3c6400_init_irq(void)
{
/* VIC0 does not have IRQS 5..7,
* VIC1 is fully populated. */
s3c64xx_init_irq(~0 & ~(0xf << 5), ~0);
}
static struct bus_type s3c6400_subsys = {
.name = "s3c6400-core",
.dev_name = "s3c6400-core",
};
static struct device s3c6400_dev = {
.bus = &s3c6400_subsys,
};
static int __init s3c6400_core_init(void)
{
/* Not applicable when using DT. */
if (of_have_populated_dt())
return 0;
return subsys_system_register(&s3c6400_subsys, NULL);
}
core_initcall(s3c6400_core_init);
int __init s3c6400_init(void)
{
printk("S3C6400: Initialising architecture\n");
return device_register(&s3c6400_dev);
}

View file

@ -0,0 +1,100 @@
/* linux/arch/arm/mach-s3c64xx/s3c6410.c
*
* Copyright 2008 Simtec Electronics
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
/*
* NOTE: Code in this file is not used when booting with Device Tree support.
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/interrupt.h>
#include <linux/list.h>
#include <linux/timer.h>
#include <linux/init.h>
#include <linux/clk.h>
#include <linux/io.h>
#include <linux/device.h>
#include <linux/serial_core.h>
#include <linux/serial_s3c.h>
#include <linux/platform_device.h>
#include <linux/of.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <asm/mach/irq.h>
#include <mach/hardware.h>
#include <asm/irq.h>
#include <plat/cpu-freq.h>
#include <mach/regs-clock.h>
#include <plat/cpu.h>
#include <plat/devs.h>
#include <plat/sdhci.h>
#include <plat/ata-core.h>
#include <plat/adc-core.h>
#include <plat/iic-core.h>
#include <plat/onenand-core.h>
#include "common.h"
void __init s3c6410_map_io(void)
{
/* initialise device information early */
s3c6410_default_sdhci0();
s3c6410_default_sdhci1();
s3c6410_default_sdhci2();
/* the i2c devices are directly compatible with s3c2440 */
s3c_i2c0_setname("s3c2440-i2c");
s3c_i2c1_setname("s3c2440-i2c");
s3c_adc_setname("s3c64xx-adc");
s3c_device_nand.name = "s3c6400-nand";
s3c_onenand_setname("s3c6410-onenand");
s3c64xx_onenand1_setname("s3c6410-onenand");
s3c_cfcon_setname("s3c64xx-pata");
}
void __init s3c6410_init_irq(void)
{
/* VIC0 is missing IRQ7, VIC1 is fully populated. */
s3c64xx_init_irq(~0 & ~(1 << 7), ~0);
}
struct bus_type s3c6410_subsys = {
.name = "s3c6410-core",
.dev_name = "s3c6410-core",
};
static struct device s3c6410_dev = {
.bus = &s3c6410_subsys,
};
static int __init s3c6410_core_init(void)
{
/* Not applicable when using DT. */
if (of_have_populated_dt())
return 0;
return subsys_system_register(&s3c6410_subsys, NULL);
}
core_initcall(s3c6410_core_init);
int __init s3c6410_init(void)
{
printk("S3C6410: Initialising architecture\n");
return device_register(&s3c6410_dev);
}

View file

@ -0,0 +1,28 @@
/* linux/arch/arm/plat-s3c64xx/setup-fb-24bpp.c
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* Base S3C64XX setup information for 24bpp LCD framebuffer
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/fb.h>
#include <linux/gpio.h>
#include <plat/fb.h>
#include <plat/gpio-cfg.h>
#include <mach/gpio-samsung.h>
void s3c64xx_fb_gpio_setup_24bpp(void)
{
s3c_gpio_cfgrange_nopull(S3C64XX_GPI(0), 16, S3C_GPIO_SFN(2));
s3c_gpio_cfgrange_nopull(S3C64XX_GPJ(0), 12, S3C_GPIO_SFN(2));
}

View file

@ -0,0 +1,29 @@
/* linux/arch/arm/plat-s3c64xx/setup-i2c0.c
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* Base S3C64XX I2C bus 0 gpio configuration
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/gpio.h>
struct platform_device; /* don't need the contents */
#include <linux/platform_data/i2c-s3c2410.h>
#include <plat/gpio-cfg.h>
#include <mach/gpio-samsung.h>
void s3c_i2c0_cfg_gpio(struct platform_device *dev)
{
s3c_gpio_cfgall_range(S3C64XX_GPB(5), 2,
S3C_GPIO_SFN(2), S3C_GPIO_PULL_UP);
}

View file

@ -0,0 +1,29 @@
/* linux/arch/arm/plat-s3c64xx/setup-i2c1.c
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* Base S3C64XX I2C bus 1 gpio configuration
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/gpio.h>
struct platform_device; /* don't need the contents */
#include <linux/platform_data/i2c-s3c2410.h>
#include <plat/gpio-cfg.h>
#include <mach/gpio-samsung.h>
void s3c_i2c1_cfg_gpio(struct platform_device *dev)
{
s3c_gpio_cfgall_range(S3C64XX_GPB(2), 2,
S3C_GPIO_SFN(6), S3C_GPIO_PULL_UP);
}

View file

@ -0,0 +1,44 @@
/* linux/arch/arm/mach-s3c64xx/setup-ide.c
*
* Copyright (c) 2010 Samsung Electronics Co., Ltd.
* http://www.samsung.com/
*
* S3C64XX setup information for IDE
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/kernel.h>
#include <linux/gpio.h>
#include <linux/io.h>
#include <mach/map.h>
#include <mach/regs-clock.h>
#include <plat/gpio-cfg.h>
#include <mach/gpio-samsung.h>
#include <linux/platform_data/ata-samsung_cf.h>
void s3c64xx_ide_setup_gpio(void)
{
u32 reg;
reg = readl(S3C_MEM_SYS_CFG) & (~0x3f);
/* Independent CF interface, CF chip select configuration */
writel(reg | MEM_SYS_CFG_INDEP_CF |
MEM_SYS_CFG_EBI_FIX_PRI_CFCON, S3C_MEM_SYS_CFG);
s3c_gpio_cfgpin(S3C64XX_GPB(4), S3C_GPIO_SFN(4));
/* Set XhiDATA[15:0] pins as CF Data[15:0] */
s3c_gpio_cfgpin_range(S3C64XX_GPK(0), 16, S3C_GPIO_SFN(5));
/* Set XhiADDR[2:0] pins as CF ADDR[2:0] */
s3c_gpio_cfgpin_range(S3C64XX_GPL(0), 3, S3C_GPIO_SFN(6));
/* Set Xhi ctrl pins as CF ctrl pins(IORDY, IOWR, IORD, CE[0:1]) */
s3c_gpio_cfgpin(S3C64XX_GPM(5), S3C_GPIO_SFN(1));
s3c_gpio_cfgpin_range(S3C64XX_GPM(0), 5, S3C_GPIO_SFN(6));
}

View file

@ -0,0 +1,25 @@
/* linux/arch/arm/mach-s3c64xx/setup-keypad.c
*
* Copyright (c) 2010 Samsung Electronics Co., Ltd.
* http://www.samsung.com/
*
* GPIO configuration for S3C64XX KeyPad device
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/gpio.h>
#include <plat/gpio-cfg.h>
#include <plat/keypad.h>
#include <mach/gpio-samsung.h>
void samsung_keypad_cfg_gpio(unsigned int rows, unsigned int cols)
{
/* Set all the necessary GPK pins to special-function 3: KP_ROW[x] */
s3c_gpio_cfgrange_nopull(S3C64XX_GPK(8), rows, S3C_GPIO_SFN(3));
/* Set all the necessary GPL pins to special-function 3: KP_COL[x] */
s3c_gpio_cfgrange_nopull(S3C64XX_GPL(0), cols, S3C_GPIO_SFN(3));
}

View file

@ -0,0 +1,58 @@
/* linux/arch/arm/plat-s3c64xx/setup-sdhci-gpio.c
*
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C64XX - Helper functions for setting up SDHCI device(s) GPIO (HSMMC)
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/interrupt.h>
#include <linux/platform_device.h>
#include <linux/io.h>
#include <linux/gpio.h>
#include <plat/gpio-cfg.h>
#include <plat/sdhci.h>
#include <mach/gpio-samsung.h>
void s3c64xx_setup_sdhci0_cfg_gpio(struct platform_device *dev, int width)
{
struct s3c_sdhci_platdata *pdata = dev->dev.platform_data;
/* Set all the necessary GPG pins to special-function 2 */
s3c_gpio_cfgrange_nopull(S3C64XX_GPG(0), 2 + width, S3C_GPIO_SFN(2));
if (pdata->cd_type == S3C_SDHCI_CD_INTERNAL) {
s3c_gpio_setpull(S3C64XX_GPG(6), S3C_GPIO_PULL_UP);
s3c_gpio_cfgpin(S3C64XX_GPG(6), S3C_GPIO_SFN(2));
}
}
void s3c64xx_setup_sdhci1_cfg_gpio(struct platform_device *dev, int width)
{
struct s3c_sdhci_platdata *pdata = dev->dev.platform_data;
/* Set all the necessary GPH pins to special-function 2 */
s3c_gpio_cfgrange_nopull(S3C64XX_GPH(0), 2 + width, S3C_GPIO_SFN(2));
if (pdata->cd_type == S3C_SDHCI_CD_INTERNAL) {
s3c_gpio_setpull(S3C64XX_GPG(6), S3C_GPIO_PULL_UP);
s3c_gpio_cfgpin(S3C64XX_GPG(6), S3C_GPIO_SFN(3));
}
}
void s3c64xx_setup_sdhci2_cfg_gpio(struct platform_device *dev, int width)
{
/* Set all the necessary GPH pins to special-function 3 */
s3c_gpio_cfgrange_nopull(S3C64XX_GPH(6), width, S3C_GPIO_SFN(3));
/* Set all the necessary GPC pins to special-function 3 */
s3c_gpio_cfgrange_nopull(S3C64XX_GPC(4), 2, S3C_GPIO_SFN(3));
}

View file

@ -0,0 +1,31 @@
/* linux/arch/arm/mach-s3c64xx/setup-spi.c
*
* Copyright (C) 2011 Samsung Electronics Ltd.
* http://www.samsung.com/
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/gpio.h>
#include <plat/gpio-cfg.h>
#include <mach/gpio-samsung.h>
#ifdef CONFIG_S3C64XX_DEV_SPI0
int s3c64xx_spi0_cfg_gpio(void)
{
s3c_gpio_cfgall_range(S3C64XX_GPC(0), 3,
S3C_GPIO_SFN(2), S3C_GPIO_PULL_UP);
return 0;
}
#endif
#ifdef CONFIG_S3C64XX_DEV_SPI1
int s3c64xx_spi1_cfg_gpio(void)
{
s3c_gpio_cfgall_range(S3C64XX_GPC(4), 3,
S3C_GPIO_SFN(2), S3C_GPIO_PULL_UP);
return 0;
}
#endif

View file

@ -0,0 +1,91 @@
/*
* Copyright (C) 2011 Samsung Electronics Co.Ltd
* Author: Joonyoung Shim <jy0922.shim@samsung.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/clk.h>
#include <linux/delay.h>
#include <linux/err.h>
#include <linux/io.h>
#include <linux/platform_device.h>
#include <mach/map.h>
#include <plat/cpu.h>
#include <plat/regs-usb-hsotg-phy.h>
#include <plat/usb-phy.h>
#include "regs-sys.h"
static int s3c_usb_otgphy_init(struct platform_device *pdev)
{
struct clk *xusbxti;
u32 phyclk;
writel(readl(S3C64XX_OTHERS) | S3C64XX_OTHERS_USBMASK, S3C64XX_OTHERS);
/* set clock frequency for PLL */
phyclk = readl(S3C_PHYCLK) & ~S3C_PHYCLK_CLKSEL_MASK;
xusbxti = clk_get(&pdev->dev, "xusbxti");
if (xusbxti && !IS_ERR(xusbxti)) {
switch (clk_get_rate(xusbxti)) {
case 12 * MHZ:
phyclk |= S3C_PHYCLK_CLKSEL_12M;
break;
case 24 * MHZ:
phyclk |= S3C_PHYCLK_CLKSEL_24M;
break;
default:
case 48 * MHZ:
/* default reference clock */
break;
}
clk_put(xusbxti);
}
/* TODO: select external clock/oscillator */
writel(phyclk | S3C_PHYCLK_CLK_FORCE, S3C_PHYCLK);
/* set to normal OTG PHY */
writel((readl(S3C_PHYPWR) & ~S3C_PHYPWR_NORMAL_MASK), S3C_PHYPWR);
mdelay(1);
/* reset OTG PHY and Link */
writel(S3C_RSTCON_PHY | S3C_RSTCON_HCLK | S3C_RSTCON_PHYCLK,
S3C_RSTCON);
udelay(20); /* at-least 10uS */
writel(0, S3C_RSTCON);
return 0;
}
static int s3c_usb_otgphy_exit(struct platform_device *pdev)
{
writel((readl(S3C_PHYPWR) | S3C_PHYPWR_ANALOG_POWERDOWN |
S3C_PHYPWR_OTG_DISABLE), S3C_PHYPWR);
writel(readl(S3C64XX_OTHERS) & ~S3C64XX_OTHERS_USBMASK, S3C64XX_OTHERS);
return 0;
}
int s5p_usb_phy_init(struct platform_device *pdev, int type)
{
if (type == USB_PHY_TYPE_DEVICE)
return s3c_usb_otgphy_init(pdev);
return -EINVAL;
}
int s5p_usb_phy_exit(struct platform_device *pdev, int type)
{
if (type == USB_PHY_TYPE_DEVICE)
return s3c_usb_otgphy_exit(pdev);
return -EINVAL;
}

View file

@ -0,0 +1,72 @@
/* linux/arch/arm/plat-s3c64xx/sleep.S
*
* Copyright 2008 Openmoko, Inc.
* Copyright 2008 Simtec Electronics
* Ben Dooks <ben@simtec.co.uk>
* http://armlinux.simtec.co.uk/
*
* S3C64XX CPU sleep code
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*/
#include <linux/linkage.h>
#include <asm/assembler.h>
#include <mach/map.h>
#undef S3C64XX_VA_GPIO
#define S3C64XX_VA_GPIO (0x0)
#include <mach/regs-gpio.h>
#define LL_UART (S3C_PA_UART + (0x400 * CONFIG_S3C_LOWLEVEL_UART_PORT))
.text
/* Sleep magic, the word before the resume entry point so that the
* bootloader can check for a resumeable image. */
.word 0x2bedf00d
/* s3c_cpu_reusme
*
* This is the entry point, stored by whatever method the bootloader
* requires to get the kernel runnign again. This code expects to be
* entered with no caches live and the MMU disabled. It will then
* restore the MMU and other basic CP registers saved and restart
* the kernel C code to finish the resume code.
*/
ENTRY(s3c_cpu_resume)
msr cpsr_c, #PSR_I_BIT | PSR_F_BIT | SVC_MODE
ldr r2, =LL_UART /* for debug */
#ifdef CONFIG_S3C_PM_DEBUG_LED_SMDK
#define S3C64XX_GPNCON (S3C64XX_GPN_BASE + 0x00)
#define S3C64XX_GPNDAT (S3C64XX_GPN_BASE + 0x04)
#define S3C64XX_GPN_CONMASK(__gpio) (0x3 << ((__gpio) * 2))
#define S3C64XX_GPN_OUTPUT(__gpio) (0x1 << ((__gpio) * 2))
/* Initialise the GPIO state if we are debugging via the SMDK LEDs,
* as the uboot version supplied resets these to inputs during the
* resume checks.
*/
ldr r3, =S3C64XX_PA_GPIO
ldr r0, [ r3, #S3C64XX_GPNCON ]
bic r0, r0, #(S3C64XX_GPN_CONMASK(12) | S3C64XX_GPN_CONMASK(13) | \
S3C64XX_GPN_CONMASK(14) | S3C64XX_GPN_CONMASK(15))
orr r0, r0, #(S3C64XX_GPN_OUTPUT(12) | S3C64XX_GPN_OUTPUT(13) | \
S3C64XX_GPN_OUTPUT(14) | S3C64XX_GPN_OUTPUT(15))
str r0, [ r3, #S3C64XX_GPNCON ]
ldr r0, [ r3, #S3C64XX_GPNDAT ]
bic r0, r0, #0xf << 12 @ GPN12..15
orr r0, r0, #1 << 15 @ GPN15
str r0, [ r3, #S3C64XX_GPNDAT ]
#endif
b cpu_resume