aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/arm/Makefile2
-rw-r--r--arch/arm/mach-s3c2410/Kconfig8
-rw-r--r--arch/arm/mach-s3c2410/Makefile.boot10
-rw-r--r--arch/arm/mach-s3c2410/include/mach/gpio-nrs.h25
-rw-r--r--arch/arm/mach-s3c2410/include/mach/gpio-track.h4
-rw-r--r--arch/arm/mach-s3c2410/include/mach/gpio.h8
-rw-r--r--arch/arm/mach-s3c2410/include/mach/regs-gpio.h22
-rw-r--r--arch/arm/mach-s3c2410/mach-bast.c2
-rw-r--r--arch/arm/mach-s3c2410/mach-h1940.c9
-rw-r--r--arch/arm/mach-s3c2410/mach-n30.c76
-rw-r--r--arch/arm/mach-s3c2410/pm.c15
-rw-r--r--arch/arm/mach-s3c2412/gpio.c20
-rw-r--r--arch/arm/mach-s3c2412/mach-jive.c2
-rw-r--r--arch/arm/mach-s3c2412/mach-smdk2413.c6
-rw-r--r--arch/arm/mach-s3c2440/Kconfig13
-rw-r--r--arch/arm/mach-s3c2440/Makefile1
-rw-r--r--arch/arm/mach-s3c2440/mach-rx1950.c582
-rw-r--r--arch/arm/mach-s3c2440/mach-rx3715.c2
-rw-r--r--arch/arm/mach-s3c2440/mach-smdk2440.c2
-rw-r--r--arch/arm/mach-s3c2443/mach-smdk2443.c2
-rw-r--r--arch/arm/mach-s3c64xx/clock.c36
-rw-r--r--arch/arm/mach-s3c64xx/dma.c2
-rw-r--r--arch/arm/mach-s3c64xx/include/mach/regs-clock.h1
-rw-r--r--arch/arm/mach-s3c64xx/mach-smdk6400.c2
-rw-r--r--arch/arm/mach-s3c64xx/mach-smdk6410.c2
-rw-r--r--arch/arm/mach-s5p6440/clock.c350
-rw-r--r--arch/arm/mach-s5p6440/cpu.c2
-rw-r--r--arch/arm/mach-s5p6440/include/mach/pwm-clock.h24
-rw-r--r--arch/arm/mach-s5p6442/cpu.c2
-rw-r--r--arch/arm/mach-s5p6442/include/mach/pwm-clock.h21
-rw-r--r--arch/arm/mach-s5pv210/Makefile2
-rw-r--r--arch/arm/mach-s5pv210/clock.c833
-rw-r--r--arch/arm/mach-s5pv210/cpu.c2
-rw-r--r--arch/arm/mach-s5pv210/gpiolib.c261
-rw-r--r--arch/arm/mach-s5pv210/include/mach/gpio.h18
-rw-r--r--arch/arm/mach-s5pv210/include/mach/pwm-clock.h21
-rw-r--r--arch/arm/mm/mmu.c5
-rw-r--r--arch/arm/plat-s3c24xx/devs.c19
-rw-r--r--arch/arm/plat-s3c24xx/dma.c2
-rw-r--r--arch/arm/plat-s3c24xx/gpio.c8
-rw-r--r--arch/arm/plat-s5p/clock.c13
-rw-r--r--arch/arm/plat-s5p/include/plat/irqs.h2
-rw-r--r--arch/arm/plat-s5p/include/plat/s5p-clock.h2
-rw-r--r--arch/arm/plat-samsung/Kconfig5
-rw-r--r--arch/arm/plat-samsung/Makefile1
-rw-r--r--arch/arm/plat-samsung/dev-hwmon.c42
-rw-r--r--arch/arm/plat-samsung/gpio-config.c12
-rw-r--r--arch/arm/plat-samsung/gpio.c15
-rw-r--r--arch/arm/plat-samsung/include/plat/clock.h1
-rw-r--r--arch/arm/plat-samsung/include/plat/cpu.h3
-rw-r--r--arch/arm/plat-samsung/include/plat/dma.h4
-rw-r--r--arch/arm/plat-samsung/include/plat/gpio-core.h14
-rw-r--r--arch/arm/plat-samsung/include/plat/hwmon.h10
-rw-r--r--arch/arm/plat-samsung/pm-gpio.c4
54 files changed, 2195 insertions, 357 deletions
diff --git a/arch/arm/Makefile b/arch/arm/Makefile
index 1594739..9505a70 100644
--- a/arch/arm/Makefile
+++ b/arch/arm/Makefile
@@ -110,6 +110,8 @@ CHECKFLAGS += -D__arm__
head-y := arch/arm/kernel/head$(MMUEXT).o arch/arm/kernel/init_task.o
textofs-y := 0x00008000
textofs-$(CONFIG_ARCH_CLPS711X) := 0x00028000
+# We don't want the htc bootloader to corrupt kernel during resume
+textofs-$(CONFIG_PM_H1940) := 0x00108000
# SA1111 DMA bug: we don't want the kernel to live in precious DMA-able memory
ifeq ($(CONFIG_ARCH_SA1100),y)
textofs-$(CONFIG_SA1111) := 0x00208000
diff --git a/arch/arm/mach-s3c2410/Kconfig b/arch/arm/mach-s3c2410/Kconfig
index 9e5e96f..a4c0b3f 100644
--- a/arch/arm/mach-s3c2410/Kconfig
+++ b/arch/arm/mach-s3c2410/Kconfig
@@ -96,12 +96,19 @@ config PM_H1940
config MACH_N30
bool "Acer N30 family"
select CPU_S3C2410
+ select MACH_N35
select S3C_DEV_USB_HOST
select S3C_DEV_NAND
help
Say Y here if you want suppt for the Acer N30, Acer N35,
Navman PiN570, Yakumo AlphaX or Airis NC05 PDAs.
+config MACH_N35
+ bool
+ help
+ Internal node in order to enable support for Acer N35 if Acer N30 is
+ selected.
+
config ARCH_BAST
bool "Simtec Electronics BAST (EB2410ITX)"
select CPU_S3C2410
@@ -111,6 +118,7 @@ config ARCH_BAST
select MACH_BAST_IDE
select S3C24XX_DCLK
select ISA
+ select S3C_DEV_HWMON
select S3C_DEV_USB_HOST
select S3C_DEV_NAND
help
diff --git a/arch/arm/mach-s3c2410/Makefile.boot b/arch/arm/mach-s3c2410/Makefile.boot
index 7dab2a0..58c1dd7 100644
--- a/arch/arm/mach-s3c2410/Makefile.boot
+++ b/arch/arm/mach-s3c2410/Makefile.boot
@@ -1,3 +1,7 @@
- zreladdr-y := 0x30008000
-params_phys-y := 0x30000100
-
+ifeq ($(CONFIG_PM_H1940),y)
+ zreladdr-y := 0x30108000
+ params_phys-y := 0x30100100
+else
+ zreladdr-y := 0x30008000
+ params_phys-y := 0x30000100
+endif
diff --git a/arch/arm/mach-s3c2410/include/mach/gpio-nrs.h b/arch/arm/mach-s3c2410/include/mach/gpio-nrs.h
index f3182ff..4f7bf32 100644
--- a/arch/arm/mach-s3c2410/include/mach/gpio-nrs.h
+++ b/arch/arm/mach-s3c2410/include/mach/gpio-nrs.h
@@ -16,15 +16,28 @@
#define S3C2410_GPIONO(bank,offset) ((bank) + (offset))
-#define S3C2410_GPIO_BANKA (32*0)
-#define S3C2410_GPIO_BANKB (32*1)
-#define S3C2410_GPIO_BANKC (32*2)
-#define S3C2410_GPIO_BANKD (32*3)
-#define S3C2410_GPIO_BANKE (32*4)
-#define S3C2410_GPIO_BANKF (32*5)
#define S3C2410_GPIO_BANKG (32*6)
#define S3C2410_GPIO_BANKH (32*7)
+/* GPIO sizes for various SoCs:
+ *
+ * 2442
+ * 2410 2412 2440 2443 2416
+ * ---- ---- ---- ---- ----
+ * A 23 22 25 16 25
+ * B 11 11 11 11 9
+ * C 16 15 16 16 16
+ * D 16 16 16 16 16
+ * E 16 16 16 16 16
+ * F 8 8 8 8 8
+ * G 16 16 16 16 8
+ * H 11 11 9 15 15
+ * J -- -- 13 16 --
+ * K -- -- -- -- 16
+ * L -- -- -- 15 7
+ * M -- -- -- 2 2
+ */
+
/* GPIO bank sizes */
#define S3C2410_GPIO_A_NR (32)
#define S3C2410_GPIO_B_NR (32)
diff --git a/arch/arm/mach-s3c2410/include/mach/gpio-track.h b/arch/arm/mach-s3c2410/include/mach/gpio-track.h
index acb2591..d67819d 100644
--- a/arch/arm/mach-s3c2410/include/mach/gpio-track.h
+++ b/arch/arm/mach-s3c2410/include/mach/gpio-track.h
@@ -23,11 +23,11 @@ static inline struct s3c_gpio_chip *s3c_gpiolib_getchip(unsigned int pin)
{
struct s3c_gpio_chip *chip;
- if (pin > S3C2410_GPG(10))
+ if (pin > S3C_GPIO_END)
return NULL;
chip = &s3c24xx_gpios[pin/32];
- return (S3C2410_GPIO_OFFSET(pin) < chip->chip.ngpio) ? chip : NULL;
+ return ((pin - chip->chip.base) < chip->chip.ngpio) ? chip : NULL;
}
#endif /* __ASM_ARCH_GPIO_CORE_H */
diff --git a/arch/arm/mach-s3c2410/include/mach/gpio.h b/arch/arm/mach-s3c2410/include/mach/gpio.h
index 15f0b3e..b649bf2 100644
--- a/arch/arm/mach-s3c2410/include/mach/gpio.h
+++ b/arch/arm/mach-s3c2410/include/mach/gpio.h
@@ -20,10 +20,18 @@
* devices that need GPIO.
*/
+#ifdef CONFIG_CPU_S3C244X
+#define ARCH_NR_GPIOS (32 * 9 + CONFIG_S3C24XX_GPIO_EXTRA)
+#else
#define ARCH_NR_GPIOS (256 + CONFIG_S3C24XX_GPIO_EXTRA)
+#endif
#include <asm-generic/gpio.h>
#include <mach/gpio-nrs.h>
#include <mach/gpio-fns.h>
+#ifdef CONFIG_CPU_S3C24XX
+#define S3C_GPIO_END (S3C2410_GPIO_BANKJ + 32)
+#else
#define S3C_GPIO_END (S3C2410_GPIO_BANKH + 32)
+#endif
diff --git a/arch/arm/mach-s3c2410/include/mach/regs-gpio.h b/arch/arm/mach-s3c2410/include/mach/regs-gpio.h
index a638423..a0a89d4 100644
--- a/arch/arm/mach-s3c2410/include/mach/regs-gpio.h
+++ b/arch/arm/mach-s3c2410/include/mach/regs-gpio.h
@@ -17,29 +17,11 @@
#include <mach/gpio-nrs.h>
#ifdef CONFIG_CPU_S3C2400
-#define S3C24XX_GPIO_BASE(x) S3C2400_GPIO_BASE(x)
-#define S3C24XX_MISCCR S3C2400_MISCCR
+#define S3C24XX_MISCCR S3C2400_MISCCR
#else
-#define S3C24XX_GPIO_BASE(x) S3C2410_GPIO_BASE(x)
-#define S3C24XX_MISCCR S3C24XX_GPIOREG2(0x80)
+#define S3C24XX_MISCCR S3C24XX_GPIOREG2(0x80)
#endif /* CONFIG_CPU_S3C2400 */
-
-/* S3C2400 doesn't have a 1:1 mapping to S3C2410 gpio base pins */
-
-#define S3C2400_BANKNUM(pin) (((pin) & ~31) / 32)
-#define S3C2400_BASEA2B(pin) ((((pin) & ~31) >> 2))
-#define S3C2400_BASEC2H(pin) ((S3C2400_BANKNUM(pin) * 10) + \
- (2 * (S3C2400_BANKNUM(pin)-2)))
-
-#define S3C2400_GPIO_BASE(pin) (pin < S3C2410_GPIO_BANKC ? \
- S3C2400_BASEA2B(pin)+S3C24XX_VA_GPIO : \
- S3C2400_BASEC2H(pin)+S3C24XX_VA_GPIO)
-
-
-#define S3C2410_GPIO_BASE(pin) ((((pin) & ~31) >> 1) + S3C24XX_VA_GPIO)
-#define S3C2410_GPIO_OFFSET(pin) ((pin) & 31)
-
/* general configuration options */
#define S3C2410_GPIO_LEAVE (0xFFFFFFFF)
diff --git a/arch/arm/mach-s3c2410/mach-bast.c b/arch/arm/mach-s3c2410/mach-bast.c
index b061ddc..c1f90f6 100644
--- a/arch/arm/mach-s3c2410/mach-bast.c
+++ b/arch/arm/mach-s3c2410/mach-bast.c
@@ -633,7 +633,7 @@ static void __init bast_map_io(void)
s3c24xx_register_clocks(bast_clocks, ARRAY_SIZE(bast_clocks));
- s3c_device_hwmon.dev.platform_data = &bast_hwmon_info;
+ s3c_hwmon_set_platdata(&bast_hwmon_info);
s3c24xx_init_io(bast_iodesc, ARRAY_SIZE(bast_iodesc));
s3c24xx_init_clocks(0);
diff --git a/arch/arm/mach-s3c2410/mach-h1940.c b/arch/arm/mach-s3c2410/mach-h1940.c
index 9531b4c..d2a2fad 100644
--- a/arch/arm/mach-s3c2410/mach-h1940.c
+++ b/arch/arm/mach-s3c2410/mach-h1940.c
@@ -163,8 +163,8 @@ static struct s3c2410fb_display h1940_lcd __initdata = {
.xres = 240,
.yres = 320,
.bpp = 16,
- .left_margin = 20,
- .right_margin = 8,
+ .left_margin = 8,
+ .right_margin = 20,
.hsync_len = 4,
.upper_margin = 8,
.lower_margin = 7,
@@ -272,7 +272,6 @@ static struct platform_device h1940_lcd_powerdev = {
};
static struct platform_device *h1940_devices[] __initdata = {
- &s3c_device_ts,
&s3c_device_ohci,
&s3c_device_lcd,
&s3c_device_wdt,
@@ -286,6 +285,8 @@ static struct platform_device *h1940_devices[] __initdata = {
&s3c_device_timer[0],
&h1940_backlight,
&h1940_lcd_powerdev,
+ &s3c_device_adc,
+ &s3c_device_ts,
};
static void __init h1940_map_io(void)
@@ -339,7 +340,7 @@ static void __init h1940_init(void)
}
MACHINE_START(H1940, "IPAQ-H1940")
- /* Maintainer: Ben Dooks <ben@fluff.org> */
+ /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.phys_io = S3C2410_PA_UART,
.io_pg_offst = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
.boot_params = S3C2410_SDRAM_PA + 0x100,
diff --git a/arch/arm/mach-s3c2410/mach-n30.c b/arch/arm/mach-s3c2410/mach-n30.c
index 75a9fd3..41f299d 100644
--- a/arch/arm/mach-s3c2410/mach-n30.c
+++ b/arch/arm/mach-s3c2410/mach-n30.c
@@ -26,6 +26,7 @@
#include <linux/serial_core.h>
#include <linux/timer.h>
#include <linux/io.h>
+#include <linux/mmc/host.h>
#include <mach/hardware.h>
#include <asm/irq.h>
@@ -46,6 +47,7 @@
#include <plat/clock.h>
#include <plat/cpu.h>
#include <plat/devs.h>
+#include <plat/mci.h>
#include <plat/s3c2410.h>
#include <plat/udc.h>
@@ -172,8 +174,10 @@ static struct gpio_keys_button n35_buttons[] = {
{
.gpio = S3C2410_GPF(0),
.code = KEY_POWER,
+ .type = EV_PWR,
.desc = "Power",
.active_low = 0,
+ .wakeup = 1,
},
{
.gpio = S3C2410_GPG(9),
@@ -264,6 +268,14 @@ static struct s3c24xx_led_platdata n30_blue_led_pdata = {
.def_trigger = "",
};
+/* This is the blue LED on the device. Originaly used to indicate GPS activity
+ * by flashing. */
+static struct s3c24xx_led_platdata n35_blue_led_pdata = {
+ .name = "blue_led",
+ .gpio = S3C2410_GPD(8),
+ .def_trigger = "",
+};
+
/* This LED is driven by the battery microcontroller, and is blinking
* red, blinking green or solid green when the battery is low,
* charging or full respectively. By driving GPD9 low, it's possible
@@ -275,6 +287,13 @@ static struct s3c24xx_led_platdata n30_warning_led_pdata = {
.def_trigger = "",
};
+static struct s3c24xx_led_platdata n35_warning_led_pdata = {
+ .name = "warning_led",
+ .flags = S3C24XX_LEDF_ACTLOW | S3C24XX_LEDF_TRISTATE,
+ .gpio = S3C2410_GPD(9),
+ .def_trigger = "",
+};
+
static struct platform_device n30_blue_led = {
.name = "s3c24xx_led",
.id = 1,
@@ -283,6 +302,14 @@ static struct platform_device n30_blue_led = {
},
};
+static struct platform_device n35_blue_led = {
+ .name = "s3c24xx_led",
+ .id = 1,
+ .dev = {
+ .platform_data = &n35_blue_led_pdata,
+ },
+};
+
static struct platform_device n30_warning_led = {
.name = "s3c24xx_led",
.id = 2,
@@ -291,6 +318,14 @@ static struct platform_device n30_warning_led = {
},
};
+static struct platform_device n35_warning_led = {
+ .name = "s3c24xx_led",
+ .id = 2,
+ .dev = {
+ .platform_data = &n35_warning_led_pdata,
+ },
+};
+
static struct s3c2410fb_display n30_display __initdata = {
.type = S3C2410_LCDCON1_TFT,
.width = 240,
@@ -317,13 +352,36 @@ static struct s3c2410fb_mach_info n30_fb_info __initdata = {
.lpcsel = 0x06,
};
+static void n30_sdi_set_power(unsigned char power_mode, unsigned short vdd)
+{
+ switch (power_mode) {
+ case MMC_POWER_ON:
+ case MMC_POWER_UP:
+ gpio_set_value(S3C2410_GPG(4), 1);
+ break;
+ case MMC_POWER_OFF:
+ default:
+ gpio_set_value(S3C2410_GPG(4), 0);
+ break;
+ }
+}
+
+static struct s3c24xx_mci_pdata n30_mci_cfg __initdata = {
+ .gpio_detect = S3C2410_GPF(1),
+ .gpio_wprotect = S3C2410_GPG(10),
+ .ocr_avail = MMC_VDD_32_33,
+ .set_power = n30_sdi_set_power,
+};
+
static struct platform_device *n30_devices[] __initdata = {
&s3c_device_lcd,
&s3c_device_wdt,
&s3c_device_i2c0,
&s3c_device_iis,
&s3c_device_ohci,
+ &s3c_device_rtc,
&s3c_device_usbgadget,
+ &s3c_device_sdi,
&n30_button_device,
&n30_blue_led,
&n30_warning_led,
@@ -334,8 +392,12 @@ static struct platform_device *n35_devices[] __initdata = {
&s3c_device_wdt,
&s3c_device_i2c0,
&s3c_device_iis,
+ &s3c_device_rtc,
&s3c_device_usbgadget,
+ &s3c_device_sdi,
&n35_button_device,
+ &n35_blue_led,
+ &n35_warning_led,
};
static struct s3c2410_platform_i2c __initdata n30_i2ccfg = {
@@ -490,17 +552,15 @@ static void __init n30_map_io(void)
s3c24xx_init_uarts(n30_uartcfgs, ARRAY_SIZE(n30_uartcfgs));
}
-static void __init n30_init_irq(void)
-{
- s3c24xx_init_irq();
-}
-
/* GPB3 is the line that controls the pull-up for the USB D+ line */
static void __init n30_init(void)
{
+ WARN_ON(gpio_request(S3C2410_GPG(4), "mmc power"));
+
s3c24xx_fb_set_platdata(&n30_fb_info);
s3c24xx_udc_set_platdata(&n30_udc_cfg);
+ s3c24xx_mci_set_platdata(&n30_mci_cfg);
s3c_i2c0_set_platdata(&n30_i2ccfg);
/* Turn off suspend on both USB ports, and switch the
@@ -532,7 +592,7 @@ static void __init n30_init(void)
s3c2410_modify_misccr(S3C2410_MISCCR_USBHOST |
S3C2410_MISCCR_USBSUSPND0 |
S3C2410_MISCCR_USBSUSPND1,
- S3C2410_MISCCR_USBSUSPND1);
+ S3C2410_MISCCR_USBSUSPND0);
platform_add_devices(n35_devices, ARRAY_SIZE(n35_devices));
}
@@ -550,7 +610,7 @@ MACHINE_START(N30, "Acer-N30")
.boot_params = S3C2410_SDRAM_PA + 0x100,
.timer = &s3c24xx_timer,
.init_machine = n30_init,
- .init_irq = n30_init_irq,
+ .init_irq = s3c24xx_init_irq,
.map_io = n30_map_io,
MACHINE_END
@@ -562,6 +622,6 @@ MACHINE_START(N35, "Acer-N35")
.boot_params = S3C2410_SDRAM_PA + 0x100,
.timer = &s3c24xx_timer,
.init_machine = n30_init,
- .init_irq = n30_init_irq,
+ .init_irq = s3c24xx_init_irq,
.map_io = n30_map_io,
MACHINE_END
diff --git a/arch/arm/mach-s3c2410/pm.c b/arch/arm/mach-s3c2410/pm.c
index 966119c..725636f 100644
--- a/arch/arm/mach-s3c2410/pm.c
+++ b/arch/arm/mach-s3c2410/pm.c
@@ -60,10 +60,10 @@ static void s3c2410_pm_prepare(void)
__raw_writel(calc, phys_to_virt(H1940_SUSPEND_CHECKSUM));
}
- /* the RX3715 uses similar code and the same H1940 and the
+ /* RX3715 and RX1950 use similar to H1940 code and the
* same offsets for resume and checksum pointers */
- if (machine_is_rx3715()) {
+ if (machine_is_rx3715() || machine_is_rx1950()) {
void *base = phys_to_virt(H1940_SUSPEND_CHECK);
unsigned long ptr;
unsigned long calc = 0;
@@ -79,6 +79,17 @@ static void s3c2410_pm_prepare(void)
if ( machine_is_aml_m5900() )
s3c2410_gpio_setpin(S3C2410_GPF(2), 1);
+ if (machine_is_rx1950()) {
+ /* According to S3C2442 user's manual, page 7-17,
+ * when the system is operating in NAND boot mode,
+ * the hardware pin configuration - EINT[23:21] –
+ * must be set as input for starting up after
+ * wakeup from sleep mode
+ */
+ s3c_gpio_cfgpin(S3C2410_GPG(13), S3C2410_GPIO_INPUT);
+ s3c_gpio_cfgpin(S3C2410_GPG(14), S3C2410_GPIO_INPUT);
+ s3c_gpio_cfgpin(S3C2410_GPG(15), S3C2410_GPIO_INPUT);
+ }
}
static int s3c2410_pm_resume(struct sys_device *dev)
diff --git a/arch/arm/mach-s3c2412/gpio.c b/arch/arm/mach-s3c2412/gpio.c
index f7afece..3404a87 100644
--- a/arch/arm/mach-s3c2412/gpio.c
+++ b/arch/arm/mach-s3c2412/gpio.c
@@ -16,41 +16,43 @@
#include <linux/types.h>
#include <linux/module.h>
#include <linux/interrupt.h>
+#include <linux/gpio.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <mach/regs-gpio.h>
-
#include <mach/hardware.h>
+#include <plat/gpio-core.h>
+
int s3c2412_gpio_set_sleepcfg(unsigned int pin, unsigned int state)
{
- void __iomem *base = S3C24XX_GPIO_BASE(pin);
- unsigned long offs = S3C2410_GPIO_OFFSET(pin);
+ struct s3c_gpio_chip *chip = s3c_gpiolib_getchip(pin);
+ unsigned long offs = pin - chip->chip.base;
unsigned long flags;
unsigned long slpcon;
offs *= 2;
- if (pin < S3C2410_GPIO_BANKB)
+ if (pin < S3C2410_GPB(0))
return -EINVAL;
- if (pin >= S3C2410_GPIO_BANKF &&
- pin <= S3C2410_GPIO_BANKG)
+ if (pin >= S3C2410_GPF(0) &&
+ pin <= S3C2410_GPG(16))
return -EINVAL;
- if (pin > (S3C2410_GPIO_BANKH + 32))
+ if (pin > S3C2410_GPH(16))
return -EINVAL;
local_irq_save(flags);
- slpcon = __raw_readl(base + 0x0C);
+ slpcon = __raw_readl(chip->base + 0x0C);
slpcon &= ~(3 << offs);
slpcon |= state << offs;
- __raw_writel(slpcon, base + 0x0C);
+ __raw_writel(slpcon, chip->base + 0x0C);
local_irq_restore(flags);
diff --git a/arch/arm/mach-s3c2412/mach-jive.c b/arch/arm/mach-s3c2412/mach-jive.c
index 4316018..478f4b4 100644
--- a/arch/arm/mach-s3c2412/mach-jive.c
+++ b/arch/arm/mach-s3c2412/mach-jive.c
@@ -674,7 +674,7 @@ static void __init jive_machine_init(void)
}
MACHINE_START(JIVE, "JIVE")
- /* Maintainer: Ben Dooks <ben@fluff.org> */
+ /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.phys_io = S3C2410_PA_UART,
.io_pg_offst = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
.boot_params = S3C2410_SDRAM_PA + 0x100,
diff --git a/arch/arm/mach-s3c2412/mach-smdk2413.c b/arch/arm/mach-s3c2412/mach-smdk2413.c
index faddb36..ba93a35 100644
--- a/arch/arm/mach-s3c2412/mach-smdk2413.c
+++ b/arch/arm/mach-s3c2412/mach-smdk2413.c
@@ -150,7 +150,7 @@ static void __init smdk2413_machine_init(void)
}
MACHINE_START(S3C2413, "S3C2413")
- /* Maintainer: Ben Dooks <ben@fluff.org> */
+ /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.phys_io = S3C2410_PA_UART,
.io_pg_offst = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
.boot_params = S3C2410_SDRAM_PA + 0x100,
@@ -163,7 +163,7 @@ MACHINE_START(S3C2413, "S3C2413")
MACHINE_END
MACHINE_START(SMDK2412, "SMDK2412")
- /* Maintainer: Ben Dooks <ben@fluff.org> */
+ /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.phys_io = S3C2410_PA_UART,
.io_pg_offst = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
.boot_params = S3C2410_SDRAM_PA + 0x100,
@@ -176,7 +176,7 @@ MACHINE_START(SMDK2412, "SMDK2412")
MACHINE_END
MACHINE_START(SMDK2413, "SMDK2413")
- /* Maintainer: Ben Dooks <ben@fluff.org> */
+ /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.phys_io = S3C2410_PA_UART,
.io_pg_offst = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
.boot_params = S3C2410_SDRAM_PA + 0x100,
diff --git a/arch/arm/mach-s3c2440/Kconfig b/arch/arm/mach-s3c2440/Kconfig
index 9d102b9..cd8e7de 100644
--- a/arch/arm/mach-s3c2440/Kconfig
+++ b/arch/arm/mach-s3c2440/Kconfig
@@ -188,4 +188,17 @@ config MACH_MINI2440
Say Y here to select support for the MINI2440. Is a 10cm x 10cm board
available via various sources. It can come with a 3.5" or 7" touch LCD.
+config MACH_RX1950
+ bool "HP iPAQ rx1950"
+ select CPU_S3C2442
+ select S3C24XX_DCLK
+ select PM_H1940 if PM
+ select I2C
+ select S3C2410_PWM
+ select S3C_DEV_NAND
+ select S3C2410_IOTIMING if S3C2440_CPUFREQ
+ select S3C2440_XTAL_16934400
+ help
+ Say Y here if you're using HP iPAQ rx1950
+
endmenu
diff --git a/arch/arm/mach-s3c2440/Makefile b/arch/arm/mach-s3c2440/Makefile
index c85ba32..d5440fa 100644
--- a/arch/arm/mach-s3c2440/Makefile
+++ b/arch/arm/mach-s3c2440/Makefile
@@ -34,6 +34,7 @@ obj-$(CONFIG_MACH_NEXCODER_2440) += mach-nexcoder.o
obj-$(CONFIG_MACH_AT2440EVB) += mach-at2440evb.o
obj-$(CONFIG_MACH_MINI2440) += mach-mini2440.o
obj-$(CONFIG_MACH_NEO1973_GTA02) += mach-gta02.o
+obj-$(CONFIG_MACH_RX1950) += mach-rx1950.o
# extra machine support
diff --git a/arch/arm/mach-s3c2440/mach-rx1950.c b/arch/arm/mach-s3c2440/mach-rx1950.c
new file mode 100644
index 0000000..8603b57
--- /dev/null
+++ b/arch/arm/mach-s3c2440/mach-rx1950.c
@@ -0,0 +1,582 @@
+/* linux/arch/arm/mach-s3c2440/mach-rx1950.c
+ *
+ * Copyright (c) 2006-2009 Victor Chukhantsev, Denis Grigoriev,
+ * Copyright (c) 2007-2010 Vasily Khoruzhick
+ *
+ * based on smdk2440 written by Ben Dooks
+ *
+ * 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/delay.h>
+#include <linux/timer.h>
+#include <linux/init.h>
+#include <linux/gpio.h>
+#include <linux/platform_device.h>
+#include <linux/serial_core.h>
+#include <linux/input.h>
+#include <linux/gpio_keys.h>
+#include <linux/sysdev.h>
+#include <linux/pwm_backlight.h>
+#include <linux/pwm.h>
+
+#include <linux/mtd/mtd.h>
+#include <linux/mtd/partitions.h>
+
+#include <linux/mmc/host.h>
+
+#include <asm/mach/arch.h>
+#include <asm/mach/map.h>
+#include <asm/mach-types.h>
+
+#include <mach/regs-gpio.h>
+#include <mach/regs-gpioj.h>
+#include <mach/h1940.h>
+#include <mach/fb.h>
+
+#include <plat/clock.h>
+#include <plat/regs-serial.h>
+#include <plat/regs-iic.h>
+#include <plat/mci.h>
+#include <plat/udc.h>
+#include <plat/nand.h>
+#include <plat/iic.h>
+#include <plat/devs.h>
+#include <plat/cpu.h>
+#include <plat/pm.h>
+#include <plat/irq.h>
+#include <plat/ts.h>
+
+#define LCD_PWM_PERIOD 192960
+#define LCD_PWM_DUTY 127353
+
+static struct map_desc rx1950_iodesc[] __initdata = {
+};
+
+static struct s3c24xx_uart_clksrc rx1950_serial_clocks[] = {
+ [0] = {
+ .name = "fclk",
+ .divisor = 0x0a,
+ .min_baud = 0,
+ .max_baud = 0,
+ },
+};
+
+static struct s3c2410_uartcfg rx1950_uartcfgs[] __initdata = {
+ [0] = {
+ .hwport = 0,
+ .flags = 0,
+ .ucon = 0x3c5,
+ .ulcon = 0x03,
+ .ufcon = 0x51,
+ .clocks = rx1950_serial_clocks,
+ .clocks_size = ARRAY_SIZE(rx1950_serial_clocks),
+ },
+ [1] = {
+ .hwport = 1,
+ .flags = 0,
+ .ucon = 0x3c5,
+ .ulcon = 0x03,
+ .ufcon = 0x51,
+ .clocks = rx1950_serial_clocks,
+ .clocks_size = ARRAY_SIZE(rx1950_serial_clocks),
+ },
+ /* IR port */
+ [2] = {
+ .hwport = 2,
+ .flags = 0,
+ .ucon = 0x3c5,
+ .ulcon = 0x43,
+ .ufcon = 0xf1,
+ .clocks = rx1950_serial_clocks,
+ .clocks_size = ARRAY_SIZE(rx1950_serial_clocks),
+ },
+};
+
+static struct s3c2410fb_display rx1950_display = {
+ .type = S3C2410_LCDCON1_TFT,
+ .width = 240,
+ .height = 320,
+ .xres = 240,
+ .yres = 320,
+ .bpp = 16,
+
+ .pixclock = 260000,
+ .left_margin = 10,
+ .right_margin = 20,
+ .hsync_len = 10,
+ .upper_margin = 2,
+ .lower_margin = 2,
+ .vsync_len = 2,
+
+ .lcdcon5 = S3C2410_LCDCON5_FRM565 |
+ S3C2410_LCDCON5_INVVCLK |
+ S3C2410_LCDCON5_INVVLINE |
+ S3C2410_LCDCON5_INVVFRAME |
+ S3C2410_LCDCON5_HWSWP |
+ (0x02 << 13) |
+ (0x02 << 15),
+
+};
+
+static struct s3c2410fb_mach_info rx1950_lcd_cfg = {
+ .displays = &rx1950_display,
+ .num_displays = 1,
+ .default_display = 0,
+
+ .lpcsel = 0x02,
+ .gpccon = 0xaa9556a9,
+ .gpccon_mask = 0xffc003fc,
+ .gpcup = 0x0000ffff,
+ .gpcup_mask = 0xffffffff,
+
+ .gpdcon = 0xaa90aaa1,
+ .gpdcon_mask = 0xffc0fff0,
+ .gpdup = 0x0000fcfd,
+ .gpdup_mask = 0xffffffff,
+
+};
+
+static struct pwm_device *lcd_pwm;
+
+void rx1950_lcd_power(int enable)
+{
+ int i;
+ static int enabled;
+ if (enabled == enable)
+ return;
+ if (!enable) {
+
+ /* GPC11-GPC15->OUTPUT */
+ for (i = 11; i < 16; i++)
+ gpio_direction_output(S3C2410_GPC(i), 1);
+
+ /* Wait a bit here... */
+ mdelay(100);
+
+ /* GPD2-GPD7->OUTPUT */
+ /* GPD11-GPD15->OUTPUT */
+ /* GPD2-GPD7->1, GPD11-GPD15->1 */
+ for (i = 2; i < 8; i++)
+ gpio_direction_output(S3C2410_GPD(i), 1);
+ for (i = 11; i < 16; i++)
+ gpio_direction_output(S3C2410_GPD(i), 1);
+
+ /* Wait a bit here...*/
+ mdelay(100);
+
+ /* GPB0->OUTPUT, GPB0->0 */
+ gpio_direction_output(S3C2410_GPB(0), 0);
+
+ /* GPC1-GPC4->OUTPUT, GPC1-4->0 */
+ for (i = 1; i < 5; i++)
+ gpio_direction_output(S3C2410_GPC(i), 0);
+
+ /* GPC15-GPC11->0 */
+ for (i = 11; i < 16; i++)
+ gpio_direction_output(S3C2410_GPC(i), 0);
+
+ /* GPD15-GPD11->0, GPD2->GPD7->0 */
+ for (i = 11; i < 16; i++)
+ gpio_direction_output(S3C2410_GPD(i), 0);
+
+ for (i = 2; i < 8; i++)
+ gpio_direction_output(S3C2410_GPD(i), 0);
+
+ /* GPC6->0, GPC7->0, GPC5->0 */
+ gpio_direction_output(S3C2410_GPC(6), 0);
+ gpio_direction_output(S3C2410_GPC(7), 0);
+ gpio_direction_output(S3C2410_GPC(5), 0);
+
+ /* GPB1->OUTPUT, GPB1->0 */
+ gpio_direction_output(S3C2410_GPB(1), 0);
+ pwm_config(lcd_pwm, 0, LCD_PWM_PERIOD);
+ pwm_disable(lcd_pwm);
+
+ /* GPC0->0, GPC10->0 */
+ gpio_direction_output(S3C2410_GPC(0), 0);
+ gpio_direction_output(S3C2410_GPC(10), 0);
+ } else {
+ pwm_config(lcd_pwm, LCD_PWM_DUTY, LCD_PWM_PERIOD);
+ pwm_enable(lcd_pwm);
+
+ gpio_direction_output(S3C2410_GPC(0), 1);
+ gpio_direction_output(S3C2410_GPC(5), 1);
+
+ s3c_gpio_cfgpin(S3C2410_GPB(1), S3C2410_GPB1_TOUT1);
+ gpio_direction_output(S3C2410_GPC(7), 1);
+
+ for (i = 1; i < 5; i++)
+ s3c_gpio_cfgpin(S3C2410_GPC(i), S3C_GPIO_SFN(2));
+
+ for (i = 11; i < 16; i++)
+ s3c_gpio_cfgpin(S3C2410_GPC(i), S3C_GPIO_SFN(2));
+
+ for (i = 2; i < 8; i++)
+ s3c_gpio_cfgpin(S3C2410_GPD(i), S3C_GPIO_SFN(2));
+
+ for (i = 11; i < 16; i++)
+ s3c_gpio_cfgpin(S3C2410_GPD(i), S3C_GPIO_SFN(2));
+
+ gpio_direction_output(S3C2410_GPC(10), 1);
+ gpio_direction_output(S3C2410_GPC(6), 1);
+ }
+ enabled = enable;
+}
+
+static void rx1950_bl_power(int enable)
+{
+ static int enabled;
+ if (enabled == enable)
+ return;
+ if (!enable) {
+ gpio_direction_output(S3C2410_GPB(0), 0);
+ } else {
+ /* LED driver need a "push" to power on */
+ gpio_direction_output(S3C2410_GPB(0), 1);
+ /* Warm up backlight for one period of PWM.
+ * Without this trick its almost impossible to
+ * enable backlight with low brightness value
+ */
+ ndelay(48000);
+ s3c_gpio_cfgpin(S3C2410_GPB(0), S3C2410_GPB0_TOUT0);
+ }
+ enabled = enable;
+}
+
+static int rx1950_backlight_init(struct device *dev)
+{
+ WARN_ON(gpio_request(S3C2410_GPB(0), "Backlight"));
+ lcd_pwm = pwm_request(1, "RX1950 LCD");
+ if (IS_ERR(lcd_pwm)) {
+ dev_err(dev, "Unable to request PWM for LCD power!\n");
+ return PTR_ERR(lcd_pwm);
+ }
+
+ rx1950_lcd_power(1);
+ rx1950_bl_power(1);
+
+ return 0;
+}
+
+static void rx1950_backlight_exit(struct device *dev)
+{
+ rx1950_bl_power(0);
+ rx1950_lcd_power(0);
+
+ pwm_free(lcd_pwm);
+ gpio_free(S3C2410_GPB(0));
+}
+
+
+static int rx1950_backlight_notify(struct device *dev, int brightness)
+{
+ if (!brightness) {
+ rx1950_bl_power(0);
+ rx1950_lcd_power(0);
+ } else {
+ rx1950_lcd_power(1);
+ rx1950_bl_power(1);
+ }
+ return brightness;
+}
+
+static struct platform_pwm_backlight_data rx1950_backlight_data = {
+ .pwm_id = 0,
+ .max_brightness = 24,
+ .dft_brightness = 4,
+ .pwm_period_ns = 48000,
+ .init = rx1950_backlight_init,
+ .notify = rx1950_backlight_notify,
+ .exit = rx1950_backlight_exit,
+};
+
+static struct platform_device rx1950_backlight = {
+ .name = "pwm-backlight",
+ .dev = {
+ .parent = &s3c_device_timer[0].dev,
+ .platform_data = &rx1950_backlight_data,
+ },
+};
+
+static void rx1950_set_mmc_power(unsigned char power_mode, unsigned short vdd)
+{
+ switch (power_mode) {
+ case MMC_POWER_OFF:
+ gpio_direction_output(S3C2410_GPJ(1), 0);
+ break;
+ case MMC_POWER_UP:
+ case MMC_POWER_ON:
+ gpio_direction_output(S3C2410_GPJ(1), 1);
+ break;
+ default:
+ break;
+ }
+}
+
+static struct s3c24xx_mci_pdata rx1950_mmc_cfg __initdata = {
+ .gpio_detect = S3C2410_GPF(5),
+ .gpio_wprotect = S3C2410_GPH(8),
+ .set_power = rx1950_set_mmc_power,
+ .ocr_avail = MMC_VDD_32_33,
+};
+
+static struct mtd_partition rx1950_nand_part[] = {
+ [0] = {
+ .name = "Boot0",
+ .offset = 0,
+ .size = 0x4000,
+ .mask_flags = MTD_WRITEABLE,
+ },
+ [1] = {
+ .name = "Boot1",
+ .offset = MTDPART_OFS_APPEND,
+ .size = 0x40000,
+ .mask_flags = MTD_WRITEABLE,
+ },
+ [2] = {
+ .name = "Kernel",
+ .offset = MTDPART_OFS_APPEND,
+ .size = 0x300000,
+ .mask_flags = 0,
+ },
+ [3] = {
+ .name = "Filesystem",
+ .offset = MTDPART_OFS_APPEND,
+ .size = MTDPART_SIZ_FULL,
+ .mask_flags = 0,
+ },
+};
+
+static struct s3c2410_nand_set rx1950_nand_sets[] = {
+ [0] = {
+ .name = "Internal",
+ .nr_chips = 1,
+ .nr_partitions = ARRAY_SIZE(rx1950_nand_part),
+ .partitions = rx1950_nand_part,
+ },
+};
+
+static struct s3c2410_platform_nand rx1950_nand_info = {
+ .tacls = 25,
+ .twrph0 = 50,
+ .twrph1 = 15,
+ .nr_sets = ARRAY_SIZE(rx1950_nand_sets),
+ .sets = rx1950_nand_sets,
+};
+
+static void rx1950_udc_pullup(enum s3c2410_udc_cmd_e cmd)
+{
+ switch (cmd) {
+ case S3C2410_UDC_P_ENABLE:
+ gpio_direction_output(S3C2410_GPJ(5), 1);
+ break;
+ case S3C2410_UDC_P_DISABLE:
+ gpio_direction_output(S3C2410_GPJ(5), 0);
+ break;
+ case S3C2410_UDC_P_RESET:
+ break;
+ default:
+ break;
+ }
+}
+
+static struct s3c2410_udc_mach_info rx1950_udc_cfg __initdata = {
+ .udc_command = rx1950_udc_pullup,
+ .vbus_pin = S3C2410_GPG(5),
+ .vbus_pin_inverted = 1,
+};
+
+static struct s3c2410_ts_mach_info rx1950_ts_cfg __initdata = {
+ .delay = 10000,
+ .presc = 49,
+ .oversampling_shift = 3,
+};
+
+static struct gpio_keys_button rx1950_gpio_keys_table[] = {
+ {
+ .code = KEY_POWER,
+ .gpio = S3C2410_GPF(0),
+ .active_low = 1,
+ .desc = "Power button",
+ .wakeup = 1,
+ },
+ {
+ .code = KEY_F5,
+ .gpio = S3C2410_GPF(7),
+ .active_low = 1,
+ .desc = "Record button",
+ },
+ {
+ .code = KEY_F1,
+ .gpio = S3C2410_GPG(0),
+ .active_low = 1,
+ .desc = "Calendar button",
+ },
+ {
+ .code = KEY_F2,
+ .gpio = S3C2410_GPG(2),
+ .active_low = 1,
+ .desc = "Contacts button",
+ },
+ {
+ .code = KEY_F3,
+ .gpio = S3C2410_GPG(3),
+ .active_low = 1,
+ .desc = "Mail button",
+ },
+ {
+ .code = KEY_F4,
+ .gpio = S3C2410_GPG(7),
+ .active_low = 1,
+ .desc = "WLAN button",
+ },
+ {
+ .code = KEY_LEFT,
+ .gpio = S3C2410_GPG(10),
+ .active_low = 1,
+ .desc = "Left button",
+ },
+ {
+ .code = KEY_RIGHT,
+ .gpio = S3C2410_GPG(11),
+ .active_low = 1,
+ .desc = "Right button",
+ },
+ {
+ .code = KEY_UP,
+ .gpio = S3C2410_GPG(4),
+ .active_low = 1,
+ .desc = "Up button",
+ },
+ {
+ .code = KEY_DOWN,
+ .gpio = S3C2410_GPG(6),
+ .active_low = 1,
+ .desc = "Down button",
+ },
+ {
+ .code = KEY_ENTER,
+ .gpio = S3C2410_GPG(9),
+ .active_low = 1,
+ .desc = "Ok button"
+ },
+};
+
+static struct gpio_keys_platform_data rx1950_gpio_keys_data = {
+ .buttons = rx1950_gpio_keys_table,
+ .nbuttons = ARRAY_SIZE(rx1950_gpio_keys_table),
+};
+
+static struct platform_device rx1950_device_gpiokeys = {
+ .name = "gpio-keys",
+ .dev.platform_data = &rx1950_gpio_keys_data,
+};
+
+static struct s3c2410_platform_i2c rx1950_i2c_data = {
+ .flags = 0,
+ .slave_addr = 0x42,
+ .frequency = 400 * 1000,
+ .sda_delay = S3C2410_IICLC_SDA_DELAY5 | S3C2410_IICLC_FILTER_ON,
+};
+
+static struct platform_device *rx1950_devices[] __initdata = {
+ &s3c_device_lcd,
+ &s3c_device_wdt,
+ &s3c_device_i2c0,
+ &s3c_device_iis,
+ &s3c_device_usbgadget,
+ &s3c_device_rtc,
+ &s3c_device_nand,
+ &s3c_device_sdi,
+ &s3c_device_adc,
+ &s3c_device_ts,
+ &s3c_device_timer[0],
+ &s3c_device_timer[1],
+ &rx1950_backlight,
+ &rx1950_device_gpiokeys,
+};
+
+static struct clk *rx1950_clocks[] __initdata = {
+ &s3c24xx_clkout0,
+ &s3c24xx_clkout1,
+};
+
+static void __init rx1950_map_io(void)
+{
+ s3c24xx_clkout0.parent = &clk_h;
+ s3c24xx_clkout1.parent = &clk_f;
+
+ s3c24xx_register_clocks(rx1950_clocks, ARRAY_SIZE(rx1950_clocks));
+
+ s3c24xx_init_io(rx1950_iodesc, ARRAY_SIZE(rx1950_iodesc));
+ s3c24xx_init_clocks(16934000);
+ s3c24xx_init_uarts(rx1950_uartcfgs, ARRAY_SIZE(rx1950_uartcfgs));
+
+ /* setup PM */
+
+#ifdef CONFIG_PM_H1940
+ memcpy(phys_to_virt(H1940_SUSPEND_RESUMEAT), h1940_pm_return, 8);
+#endif
+
+ s3c_pm_init();
+}
+
+static void __init rx1950_init_machine(void)
+{
+ int i;
+
+ s3c24xx_fb_set_platdata(&rx1950_lcd_cfg);
+ s3c24xx_udc_set_platdata(&rx1950_udc_cfg);
+ s3c24xx_ts_set_platdata(&rx1950_ts_cfg);
+ s3c24xx_mci_set_platdata(&rx1950_mmc_cfg);
+ s3c_i2c0_set_platdata(&rx1950_i2c_data);
+ s3c_nand_set_platdata(&rx1950_nand_info);
+
+ /* Turn off suspend on both USB ports, and switch the
+ * selectable USB port to USB device mode. */
+ s3c2410_modify_misccr(S3C2410_MISCCR_USBHOST |
+ S3C2410_MISCCR_USBSUSPND0 |
+ S3C2410_MISCCR_USBSUSPND1, 0x0);
+
+ WARN_ON(gpio_request(S3C2410_GPJ(5), "UDC pullup"));
+ gpio_direction_output(S3C2410_GPJ(5), 0);
+
+ /* mmc power is disabled by default */
+ WARN_ON(gpio_request(S3C2410_GPJ(1), "MMC power"));
+ gpio_direction_output(S3C2410_GPJ(1), 0);
+
+ for (i = 0; i < 8; i++)
+ WARN_ON(gpio_request(S3C2410_GPC(i), "LCD power"));
+
+ for (i = 10; i < 16; i++)
+ WARN_ON(gpio_request(S3C2410_GPC(i), "LCD power"));
+
+ for (i = 2; i < 8; i++)
+ WARN_ON(gpio_request(S3C2410_GPD(i), "LCD power"));
+
+ for (i = 11; i < 16; i++)
+ WARN_ON(gpio_request(S3C2410_GPD(i), "LCD power"));
+
+ WARN_ON(gpio_request(S3C2410_GPB(1), "LCD power"));
+
+ platform_add_devices(rx1950_devices, ARRAY_SIZE(rx1950_devices));
+}
+
+MACHINE_START(RX1950, "HP iPAQ RX1950")
+ /* Maintainers: Vasily Khoruzhick */
+ .phys_io = S3C2410_PA_UART,
+ .io_pg_offst = (((u32) S3C24XX_VA_UART) >> 18) & 0xfffc,
+ .boot_params = S3C2410_SDRAM_PA + 0x100,
+ .map_io = rx1950_map_io,
+ .init_irq = s3c24xx_init_irq,
+ .init_machine = rx1950_init_machine,
+ .timer = &s3c24xx_timer,
+MACHINE_END
diff --git a/arch/arm/mach-s3c2440/mach-rx3715.c b/arch/arm/mach-s3c2440/mach-rx3715.c
index 1e836e5..d2946de 100644
--- a/arch/arm/mach-s3c2440/mach-rx3715.c
+++ b/arch/arm/mach-s3c2440/mach-rx3715.c
@@ -209,7 +209,7 @@ static void __init rx3715_init_machine(void)
}
MACHINE_START(RX3715, "IPAQ-RX3715")
- /* Maintainer: Ben Dooks <ben@fluff.org> */
+ /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.phys_io = S3C2410_PA_UART,
.io_pg_offst = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
.boot_params = S3C2410_SDRAM_PA + 0x100,
diff --git a/arch/arm/mach-s3c2440/mach-smdk2440.c b/arch/arm/mach-s3c2440/mach-smdk2440.c
index 3ac3d63..df83276 100644
--- a/arch/arm/mach-s3c2440/mach-smdk2440.c
+++ b/arch/arm/mach-s3c2440/mach-smdk2440.c
@@ -174,7 +174,7 @@ static void __init smdk2440_machine_init(void)
}
MACHINE_START(S3C2440, "SMDK2440")
- /* Maintainer: Ben Dooks <ben@fluff.org> */
+ /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.phys_io = S3C2410_PA_UART,
.io_pg_offst = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
.boot_params = S3C2410_SDRAM_PA + 0x100,
diff --git a/arch/arm/mach-s3c2443/mach-smdk2443.c b/arch/arm/mach-s3c2443/mach-smdk2443.c
index e2e362b..4c863d3 100644
--- a/arch/arm/mach-s3c2443/mach-smdk2443.c
+++ b/arch/arm/mach-s3c2443/mach-smdk2443.c
@@ -131,7 +131,7 @@ static void __init smdk2443_machine_init(void)
}
MACHINE_START(SMDK2443, "SMDK2443")
- /* Maintainer: Ben Dooks <ben@fluff.org> */
+ /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.phys_io = S3C2410_PA_UART,
.io_pg_offst = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
.boot_params = S3C2410_SDRAM_PA + 0x100,
diff --git a/arch/arm/mach-s3c64xx/clock.c b/arch/arm/mach-s3c64xx/clock.c
index 2ac2e7d..7a4138b 100644
--- a/arch/arm/mach-s3c64xx/clock.c
+++ b/arch/arm/mach-s3c64xx/clock.c
@@ -88,6 +88,12 @@ struct clk clk_48m = {
.enable = clk_48m_ctrl,
};
+struct clk clk_xusbxti = {
+ .name = "xusbxti",
+ .id = -1,
+ .rate = 48000000,
+};
+
static int inline s3c64xx_gate(void __iomem *reg,
struct clk *clk,
int enable)
@@ -518,6 +524,11 @@ static struct clk clk_iis_cd1 = {
.id = -1,
};
+static struct clk clk_iisv4_cd = {
+ .name = "iis_cdclk_v4",
+ .id = -1,
+};
+
static struct clk clk_pcm_cd = {
.name = "pcm_cdclk",
.id = -1,
@@ -549,6 +560,19 @@ static struct clksrc_sources clkset_audio1 = {
.nr_sources = ARRAY_SIZE(clkset_audio1_list),
};
+static struct clk *clkset_audio2_list[] = {
+ [0] = &clk_mout_epll.clk,
+ [1] = &clk_dout_mpll,
+ [2] = &clk_fin_epll,
+ [3] = &clk_iisv4_cd,
+ [4] = &clk_pcm_cd,
+};
+
+static struct clksrc_sources clkset_audio2 = {
+ .sources = clkset_audio2_list,
+ .nr_sources = ARRAY_SIZE(clkset_audio2_list),
+};
+
static struct clk *clkset_camif_list[] = {
&clk_h2,
};
@@ -652,6 +676,16 @@ static struct clksrc_clk clksrcs[] = {
.sources = &clkset_audio1,
}, {
.clk = {
+ .name = "audio-bus",
+ .id = -1, /* There's only one IISv4 port */
+ .ctrlbit = S3C6410_CLKCON_SCLK_AUDIO2,
+ .enable = s3c64xx_sclk_ctrl,
+ },
+ .reg_src = { .reg = S3C6410_CLK_SRC2, .shift = 0, .size = 3 },
+ .reg_div = { .reg = S3C_CLK_DIV2, .shift = 24, .size = 4 },
+ .sources = &clkset_audio2,
+ }, {
+ .clk = {
.name = "irda-bus",
.id = 0,
.ctrlbit = S3C_CLKCON_SCLK_IRDA,
@@ -749,6 +783,7 @@ static struct clk *clks1[] __initdata = {
&clk_ext_xtal_mux,
&clk_iis_cd0,
&clk_iis_cd1,
+ &clk_iisv4_cd,
&clk_pcm_cd,
&clk_mout_epll.clk,
&clk_mout_mpll.clk,
@@ -762,6 +797,7 @@ static struct clk *clks[] __initdata = {
&clk_27m,
&clk_48m,
&clk_h2,
+ &clk_xusbxti,
};
/**
diff --git a/arch/arm/mach-s3c64xx/dma.c b/arch/arm/mach-s3c64xx/dma.c
index 33ccf7b..5567e03 100644
--- a/arch/arm/mach-s3c64xx/dma.c
+++ b/arch/arm/mach-s3c64xx/dma.c
@@ -414,7 +414,7 @@ err_buff:
EXPORT_SYMBOL(s3c2410_dma_enqueue);
-int s3c2410_dma_devconfig(int channel,
+int s3c2410_dma_devconfig(unsigned int channel,
enum s3c2410_dmasrc source,
unsigned long devaddr)
{
diff --git a/arch/arm/mach-s3c64xx/include/mach/regs-clock.h b/arch/arm/mach-s3c64xx/include/mach/regs-clock.h
index 3ef6274..0114eb0 100644
--- a/arch/arm/mach-s3c64xx/include/mach/regs-clock.h
+++ b/arch/arm/mach-s3c64xx/include/mach/regs-clock.h
@@ -33,6 +33,7 @@
#define S3C_PCLK_GATE S3C_CLKREG(0x34)
#define S3C_SCLK_GATE S3C_CLKREG(0x38)
#define S3C_MEM0_GATE S3C_CLKREG(0x3C)
+#define S3C6410_CLK_SRC2 S3C_CLKREG(0x10C)
/* CLKDIV0 */
#define S3C6400_CLKDIV0_PCLK_MASK (0xf << 12)
diff --git a/arch/arm/mach-s3c64xx/mach-smdk6400.c b/arch/arm/mach-s3c64xx/mach-smdk6400.c
index f7b1898..5991667 100644
--- a/arch/arm/mach-s3c64xx/mach-smdk6400.c
+++ b/arch/arm/mach-s3c64xx/mach-smdk6400.c
@@ -84,7 +84,7 @@ static void __init smdk6400_machine_init(void)
}
MACHINE_START(SMDK6400, "SMDK6400")
- /* Maintainer: Ben Dooks <ben@fluff.org> */
+ /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.phys_io = S3C_PA_UART & 0xfff00000,
.io_pg_offst = (((u32)S3C_VA_UART) >> 18) & 0xfffc,
.boot_params = S3C64XX_PA_SDRAM + 0x100,
diff --git a/arch/arm/mach-s3c64xx/mach-smdk6410.c b/arch/arm/mach-s3c64xx/mach-smdk6410.c
index 2d5afd2..9d51455 100644
--- a/arch/arm/mach-s3c64xx/mach-smdk6410.c
+++ b/arch/arm/mach-s3c64xx/mach-smdk6410.c
@@ -656,7 +656,7 @@ static void __init smdk6410_machine_init(void)
}
MACHINE_START(SMDK6410, "SMDK6410")
- /* Maintainer: Ben Dooks <ben@fluff.org> */
+ /* Maintainer: Ben Dooks <ben-linux@fluff.org> */
.phys_io = S3C_PA_UART & 0xfff00000,
.io_pg_offst = (((u32)S3C_VA_UART) >> 18) & 0xfffc,
.boot_params = S3C64XX_PA_SDRAM + 0x100,
diff --git a/arch/arm/mach-s5p6440/clock.c b/arch/arm/mach-s5p6440/clock.c
index b2672e1..ca6e48d 100644
--- a/arch/arm/mach-s5p6440/clock.c
+++ b/arch/arm/mach-s5p6440/clock.c
@@ -134,24 +134,6 @@ static struct clksrc_clk clk_mout_mpll = {
.reg_src = { .reg = S5P_CLK_SRC0, .shift = 1, .size = 1 },
};
-static struct clk clk_h_low = {
- .name = "hclk_low",
- .id = -1,
- .rate = 0,
- .parent = NULL,
- .ctrlbit = 0,
- .ops = &clk_ops_def_setrate,
-};
-
-static struct clk clk_p_low = {
- .name = "pclk_low",
- .id = -1,
- .rate = 0,
- .parent = NULL,
- .ctrlbit = 0,
- .ops = &clk_ops_def_setrate,
-};
-
enum perf_level {
L0 = 532*1000,
L1 = 266*1000,
@@ -247,23 +229,70 @@ static struct clk_ops s5p6440_clkarm_ops = {
.round_rate = s5p6440_armclk_round_rate,
};
-static unsigned long s5p6440_clk_doutmpll_get_rate(struct clk *clk)
-{
- unsigned long rate = clk_get_rate(clk->parent);
+static struct clksrc_clk clk_armclk = {
+ .clk = {
+ .name = "armclk",
+ .id = 1,
+ .parent = &clk_mout_apll.clk,
+ .ops = &s5p6440_clkarm_ops,
+ },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 0, .size = 4 },
+};
- if (__raw_readl(S5P_CLK_DIV0) & S5P_CLKDIV0_MPLL_MASK)
- rate /= 2;
+static struct clksrc_clk clk_dout_mpll = {
+ .clk = {
+ .name = "dout_mpll",
+ .id = -1,
+ .parent = &clk_mout_mpll.clk,
+ },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 4, .size = 1 },
+};
- return rate;
-}
+static struct clksrc_clk clk_hclk = {
+ .clk = {
+ .name = "clk_hclk",
+ .id = -1,
+ .parent = &clk_armclk.clk,
+ },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 8, .size = 4 },
+};
-static struct clk clk_dout_mpll = {
- .name = "dout_mpll",
- .id = -1,
- .parent = &clk_mout_mpll.clk,
- .ops = &(struct clk_ops) {
- .get_rate = s5p6440_clk_doutmpll_get_rate,
+static struct clksrc_clk clk_pclk = {
+ .clk = {
+ .name = "clk_pclk",
+ .id = -1,
+ .parent = &clk_hclk.clk,
},
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 12, .size = 4 },
+};
+
+static struct clk *clkset_hclklow_list[] = {
+ &clk_mout_apll.clk,
+ &clk_mout_mpll.clk,
+};
+
+static struct clksrc_sources clkset_hclklow = {
+ .sources = clkset_hclklow_list,
+ .nr_sources = ARRAY_SIZE(clkset_hclklow_list),
+};
+
+static struct clksrc_clk clk_hclk_low = {
+ .clk = {
+ .name = "hclk_low",
+ .id = -1,
+ },
+ .sources = &clkset_hclklow,
+ .reg_src = { .reg = S5P_SYS_OTHERS, .shift = 6, .size = 1 },
+ .reg_div = { .reg = S5P_CLK_DIV3, .shift = 8, .size = 4 },
+};
+
+static struct clksrc_clk clk_pclk_low = {
+ .clk = {
+ .name = "pclk_low",
+ .id = -1,
+ .parent = &clk_hclk_low.clk,
+ },
+ .reg_div = { .reg = S5P_CLK_DIV3, .shift = 12, .size = 4 },
};
int s5p6440_clk48m_ctrl(struct clk *clk, int enable)
@@ -307,6 +336,11 @@ static int s5p6440_sclk_ctrl(struct clk *clk, int enable)
return s5p_gatectrl(S5P_CLK_GATE_SCLK0, clk, enable);
}
+static int s5p6440_sclk1_ctrl(struct clk *clk, int enable)
+{
+ return s5p_gatectrl(S5P_CLK_GATE_SCLK1, clk, enable);
+}
+
static int s5p6440_mem_ctrl(struct clk *clk, int enable)
{
return s5p_gatectrl(S5P_CLK_GATE_MEM0, clk, enable);
@@ -321,37 +355,37 @@ static struct clk init_clocks_disable[] = {
{
.name = "nand",
.id = -1,
- .parent = &clk_h,
+ .parent = &clk_hclk.clk,
.enable = s5p6440_mem_ctrl,
.ctrlbit = S5P_CLKCON_MEM0_HCLK_NFCON,
}, {
.name = "adc",
.id = -1,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_TSADC,
}, {
.name = "i2c",
.id = -1,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_IIC0,
}, {
.name = "i2s_v40",
.id = 0,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_IIS2,
}, {
.name = "spi",
.id = 0,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_SPI0,
}, {
.name = "spi",
.id = 1,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_SPI1,
}, {
@@ -387,58 +421,124 @@ static struct clk init_clocks_disable[] = {
}, {
.name = "otg",
.id = -1,
- .parent = &clk_h_low,
+ .parent = &clk_hclk_low.clk,
.enable = s5p6440_hclk0_ctrl,
.ctrlbit = S5P_CLKCON_HCLK0_USB
}, {
.name = "post",
.id = -1,
- .parent = &clk_h_low,
+ .parent = &clk_hclk_low.clk,
.enable = s5p6440_hclk0_ctrl,
.ctrlbit = S5P_CLKCON_HCLK0_POST0
}, {
.name = "lcd",
.id = -1,
- .parent = &clk_h_low,
+ .parent = &clk_hclk_low.clk,
.enable = s5p6440_hclk1_ctrl,
.ctrlbit = S5P_CLKCON_HCLK1_DISPCON,
}, {
.name = "hsmmc",
.id = 0,
- .parent = &clk_h_low,
+ .parent = &clk_hclk_low.clk,
.enable = s5p6440_hclk0_ctrl,
.ctrlbit = S5P_CLKCON_HCLK0_HSMMC0,
}, {
.name = "hsmmc",
.id = 1,
- .parent = &clk_h_low,
+ .parent = &clk_hclk_low.clk,
.enable = s5p6440_hclk0_ctrl,
.ctrlbit = S5P_CLKCON_HCLK0_HSMMC1,
}, {
.name = "hsmmc",
.id = 2,
- .parent = &clk_h_low,
+ .parent = &clk_hclk_low.clk,
.enable = s5p6440_hclk0_ctrl,
.ctrlbit = S5P_CLKCON_HCLK0_HSMMC2,
}, {
.name = "rtc",
.id = -1,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_RTC,
}, {
.name = "watchdog",
.id = -1,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_WDT,
}, {
.name = "timers",
.id = -1,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_PWM,
- }
+ }, {
+ .name = "hclk_fimgvg",
+ .id = -1,
+ .parent = &clk_hclk.clk,
+ .enable = s5p6440_hclk1_ctrl,
+ .ctrlbit = (1 << 2),
+ }, {
+ .name = "tsi",
+ .id = -1,
+ .parent = &clk_hclk_low.clk,
+ .enable = s5p6440_hclk1_ctrl,
+ .ctrlbit = (1 << 0),
+ }, {
+ .name = "pclk_fimgvg",
+ .id = -1,
+ .parent = &clk_pclk.clk,
+ .enable = s5p6440_pclk_ctrl,
+ .ctrlbit = (1 << 31),
+ }, {
+ .name = "dmc0",
+ .id = -1,
+ .parent = &clk_pclk.clk,
+ .enable = s5p6440_pclk_ctrl,
+ .ctrlbit = (1 << 30),
+ }, {
+ .name = "etm",
+ .id = -1,
+ .parent = &clk_pclk.clk,
+ .enable = s5p6440_pclk_ctrl,
+ .ctrlbit = (1 << 29),
+ }, {
+ .name = "dsim",
+ .id = -1,
+ .parent = &clk_pclk_low.clk,
+ .enable = s5p6440_pclk_ctrl,
+ .ctrlbit = (1 << 28),
+ }, {
+ .name = "gps",
+ .id = -1,
+ .parent = &clk_pclk_low.clk,
+ .enable = s5p6440_pclk_ctrl,
+ .ctrlbit = (1 << 25),
+ }, {
+ .name = "pcm",
+ .id = -1,
+ .parent = &clk_pclk_low.clk,
+ .enable = s5p6440_pclk_ctrl,
+ .ctrlbit = (1 << 8),
+ }, {
+ .name = "irom",
+ .id = -1,
+ .parent = &clk_hclk.clk,
+ .enable = s5p6440_hclk0_ctrl,
+ .ctrlbit = (1 << 25),
+ }, {
+ .name = "dma",
+ .id = -1,
+ .parent = &clk_hclk_low.clk,
+ .enable = s5p6440_hclk0_ctrl,
+ .ctrlbit = (1 << 12),
+ }, {
+ .name = "2d",
+ .id = -1,
+ .parent = &clk_hclk.clk,
+ .enable = s5p6440_hclk0_ctrl,
+ .ctrlbit = (1 << 8),
+ },
};
/*
@@ -448,34 +548,46 @@ static struct clk init_clocks[] = {
{
.name = "gpio",
.id = -1,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_GPIO,
}, {
.name = "uart",
.id = 0,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_UART0,
}, {
.name = "uart",
.id = 1,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_UART1,
}, {
.name = "uart",
.id = 2,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_UART2,
}, {
.name = "uart",
.id = 3,
- .parent = &clk_p_low,
+ .parent = &clk_pclk_low.clk,
.enable = s5p6440_pclk_ctrl,
.ctrlbit = S5P_CLKCON_PCLK_UART3,
- }
+ }, {
+ .name = "mem",
+ .id = -1,
+ .parent = &clk_hclk.clk,
+ .enable = s5p6440_hclk0_ctrl,
+ .ctrlbit = (1 << 21),
+ }, {
+ .name = "intc",
+ .id = -1,
+ .parent = &clk_hclk.clk,
+ .enable = s5p6440_hclk0_ctrl,
+ .ctrlbit = (1 << 1),
+ },
};
static struct clk clk_iis_cd_v40 = {
@@ -488,20 +600,20 @@ static struct clk clk_pcm_cd = {
.id = -1,
};
-static struct clk *clkset_spi_mmc_list[] = {
+static struct clk *clkset_group1_list[] = {
&clk_mout_epll.clk,
- &clk_dout_mpll,
+ &clk_dout_mpll.clk,
&clk_fin_epll,
};
-static struct clksrc_sources clkset_spi_mmc = {
- .sources = clkset_spi_mmc_list,
- .nr_sources = ARRAY_SIZE(clkset_spi_mmc_list),
+static struct clksrc_sources clkset_group1 = {
+ .sources = clkset_group1_list,
+ .nr_sources = ARRAY_SIZE(clkset_group1_list),
};
static struct clk *clkset_uart_list[] = {
&clk_mout_epll.clk,
- &clk_dout_mpll
+ &clk_dout_mpll.clk,
};
static struct clksrc_sources clkset_uart = {
@@ -509,6 +621,19 @@ static struct clksrc_sources clkset_uart = {
.nr_sources = ARRAY_SIZE(clkset_uart_list),
};
+static struct clk *clkset_audio_list[] = {
+ &clk_mout_epll.clk,
+ &clk_dout_mpll.clk,
+ &clk_fin_epll,
+ &clk_iis_cd_v40,
+ &clk_pcm_cd,
+};
+
+static struct clksrc_sources clkset_audio = {
+ .sources = clkset_audio_list,
+ .nr_sources = ARRAY_SIZE(clkset_audio_list),
+};
+
static struct clksrc_clk clksrcs[] = {
{
.clk = {
@@ -517,7 +642,7 @@ static struct clksrc_clk clksrcs[] = {
.ctrlbit = S5P_CLKCON_SCLK0_MMC0,
.enable = s5p6440_sclk_ctrl,
},
- .sources = &clkset_spi_mmc,
+ .sources = &clkset_group1,
.reg_src = { .reg = S5P_CLK_SRC0, .shift = 18, .size = 2 },
.reg_div = { .reg = S5P_CLK_DIV1, .shift = 0, .size = 4 },
}, {
@@ -527,7 +652,7 @@ static struct clksrc_clk clksrcs[] = {
.ctrlbit = S5P_CLKCON_SCLK0_MMC1,
.enable = s5p6440_sclk_ctrl,
},
- .sources = &clkset_spi_mmc,
+ .sources = &clkset_group1,
.reg_src = { .reg = S5P_CLK_SRC0, .shift = 20, .size = 2 },
.reg_div = { .reg = S5P_CLK_DIV1, .shift = 4, .size = 4 },
}, {
@@ -537,7 +662,7 @@ static struct clksrc_clk clksrcs[] = {
.ctrlbit = S5P_CLKCON_SCLK0_MMC2,
.enable = s5p6440_sclk_ctrl,
},
- .sources = &clkset_spi_mmc,
+ .sources = &clkset_group1,
.reg_src = { .reg = S5P_CLK_SRC0, .shift = 22, .size = 2 },
.reg_div = { .reg = S5P_CLK_DIV1, .shift = 8, .size = 4 },
}, {
@@ -557,7 +682,7 @@ static struct clksrc_clk clksrcs[] = {
.ctrlbit = S5P_CLKCON_SCLK0_SPI0,
.enable = s5p6440_sclk_ctrl,
},
- .sources = &clkset_spi_mmc,
+ .sources = &clkset_group1,
.reg_src = { .reg = S5P_CLK_SRC0, .shift = 14, .size = 2 },
.reg_div = { .reg = S5P_CLK_DIV2, .shift = 0, .size = 4 },
}, {
@@ -567,17 +692,63 @@ static struct clksrc_clk clksrcs[] = {
.ctrlbit = S5P_CLKCON_SCLK0_SPI1,
.enable = s5p6440_sclk_ctrl,
},
- .sources = &clkset_spi_mmc,
+ .sources = &clkset_group1,
.reg_src = { .reg = S5P_CLK_SRC0, .shift = 16, .size = 2 },
.reg_div = { .reg = S5P_CLK_DIV2, .shift = 4, .size = 4 },
- }
+ }, {
+ .clk = {
+ .name = "sclk_post",
+ .id = -1,
+ .ctrlbit = (1 << 10),
+ .enable = s5p6440_sclk_ctrl,
+ },
+ .sources = &clkset_group1,
+ .reg_src = { .reg = S5P_CLK_SRC0, .shift = 26, .size = 2 },
+ .reg_div = { .reg = S5P_CLK_DIV1, .shift = 12, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_dispcon",
+ .id = -1,
+ .ctrlbit = (1 << 1),
+ .enable = s5p6440_sclk1_ctrl,
+ },
+ .sources = &clkset_group1,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 4, .size = 2 },
+ .reg_div = { .reg = S5P_CLK_DIV3, .shift = 0, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_fimgvg",
+ .id = -1,
+ .ctrlbit = (1 << 2),
+ .enable = s5p6440_sclk1_ctrl,
+ },
+ .sources = &clkset_group1,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 8, .size = 2 },
+ .reg_div = { .reg = S5P_CLK_DIV3, .shift = 4, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_audio2",
+ .id = -1,
+ .ctrlbit = (1 << 11),
+ .enable = s5p6440_sclk_ctrl,
+ },
+ .sources = &clkset_audio,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 0, .size = 3 },
+ .reg_div = { .reg = S5P_CLK_DIV2, .shift = 24, .size = 4 },
+ },
};
/* Clock initialisation code */
-static struct clksrc_clk *init_parents[] = {
+static struct clksrc_clk *sysclks[] = {
&clk_mout_apll,
&clk_mout_epll,
&clk_mout_mpll,
+ &clk_dout_mpll,
+ &clk_armclk,
+ &clk_hclk,
+ &clk_pclk,
+ &clk_hclk_low,
+ &clk_pclk_low,
};
void __init_or_cpufreq s5p6440_setup_clocks(void)
@@ -593,21 +764,13 @@ void __init_or_cpufreq s5p6440_setup_clocks(void)
unsigned long apll;
unsigned long mpll;
unsigned int ptr;
- u32 clkdiv0;
- u32 clkdiv3;
/* Set S5P6440 functions for clk_fout_epll */
clk_fout_epll.enable = s5p6440_epll_enable;
clk_fout_epll.ops = &s5p6440_epll_ops;
- /* Set S5P6440 functions for arm clock */
- clk_arm.parent = &clk_mout_apll.clk;
- clk_arm.ops = &s5p6440_clkarm_ops;
clk_48m.enable = s5p6440_clk48m_ctrl;
- clkdiv0 = __raw_readl(S5P_CLK_DIV0);
- clkdiv3 = __raw_readl(S5P_CLK_DIV3);
-
xtal_clk = clk_get(NULL, "ext_xtal");
BUG_ON(IS_ERR(xtal_clk));
@@ -619,41 +782,28 @@ void __init_or_cpufreq s5p6440_setup_clocks(void)
mpll = s5p_get_pll45xx(xtal, __raw_readl(S5P_MPLL_CON), pll_4502);
apll = s5p_get_pll45xx(xtal, __raw_readl(S5P_APLL_CON), pll_4502);
+ clk_fout_mpll.rate = mpll;
+ clk_fout_epll.rate = epll;
+ clk_fout_apll.rate = apll;
+
printk(KERN_INFO "S5P6440: PLL settings, A=%ld.%ldMHz, M=%ld.%ldMHz," \
" E=%ld.%ldMHz\n",
print_mhz(apll), print_mhz(mpll), print_mhz(epll));
- fclk = apll / GET_DIV(clkdiv0, S5P_CLKDIV0_ARM);
- hclk = fclk / GET_DIV(clkdiv0, S5P_CLKDIV0_HCLK);
- pclk = hclk / GET_DIV(clkdiv0, S5P_CLKDIV0_PCLK);
-
- if (__raw_readl(S5P_OTHERS) & S5P_OTHERS_HCLK_LOW_SEL_MPLL) {
- /* Asynchronous mode */
- hclk_low = mpll / GET_DIV(clkdiv3, S5P_CLKDIV3_HCLK_LOW);
- } else {
- /* Synchronous mode */
- hclk_low = apll / GET_DIV(clkdiv3, S5P_CLKDIV3_HCLK_LOW);
- }
-
- pclk_low = hclk_low / GET_DIV(clkdiv3, S5P_CLKDIV3_PCLK_LOW);
+ fclk = clk_get_rate(&clk_armclk.clk);
+ hclk = clk_get_rate(&clk_hclk.clk);
+ pclk = clk_get_rate(&clk_pclk.clk);
+ hclk_low = clk_get_rate(&clk_hclk_low.clk);
+ pclk_low = clk_get_rate(&clk_pclk_low.clk);
printk(KERN_INFO "S5P6440: HCLK=%ld.%ldMHz, HCLK_LOW=%ld.%ldMHz," \
" PCLK=%ld.%ldMHz, PCLK_LOW=%ld.%ldMHz\n",
print_mhz(hclk), print_mhz(hclk_low),
print_mhz(pclk), print_mhz(pclk_low));
- clk_fout_mpll.rate = mpll;
- clk_fout_epll.rate = epll;
- clk_fout_apll.rate = apll;
-
clk_f.rate = fclk;
clk_h.rate = hclk;
clk_p.rate = pclk;
- clk_h_low.rate = hclk_low;
- clk_p_low.rate = pclk_low;
-
- for (ptr = 0; ptr < ARRAY_SIZE(init_parents); ptr++)
- s3c_set_clksrc(init_parents[ptr], true);
for (ptr = 0; ptr < ARRAY_SIZE(clksrcs); ptr++)
s3c_set_clksrc(&clksrcs[ptr], true);
@@ -661,13 +811,8 @@ void __init_or_cpufreq s5p6440_setup_clocks(void)
static struct clk *clks[] __initdata = {
&clk_ext,
- &clk_mout_epll.clk,
- &clk_mout_mpll.clk,
- &clk_dout_mpll,
&clk_iis_cd_v40,
&clk_pcm_cd,
- &clk_p_low,
- &clk_h_low,
};
void __init s5p6440_register_clocks(void)
@@ -680,6 +825,9 @@ void __init s5p6440_register_clocks(void)
if (ret > 0)
printk(KERN_ERR "Failed to register %u clocks\n", ret);
+ for (ptr = 0; ptr < ARRAY_SIZE(sysclks); ptr++)
+ s3c_register_clksrc(sysclks[ptr], 1);
+
s3c_register_clksrc(clksrcs, ARRAY_SIZE(clksrcs));
s3c_register_clocks(init_clocks, ARRAY_SIZE(init_clocks));
diff --git a/arch/arm/mach-s5p6440/cpu.c b/arch/arm/mach-s5p6440/cpu.c
index 1794131a..ca3b320 100644
--- a/arch/arm/mach-s5p6440/cpu.c
+++ b/arch/arm/mach-s5p6440/cpu.c
@@ -88,7 +88,7 @@ void __init s5p6440_init_irq(void)
s5p_init_irq(vic, ARRAY_SIZE(vic));
}
-static struct sysdev_class s5p6440_sysclass = {
+struct sysdev_class s5p6440_sysclass = {
.name = "s5p6440-core",
};
diff --git a/arch/arm/mach-s5p6440/include/mach/pwm-clock.h b/arch/arm/mach-s5p6440/include/mach/pwm-clock.h
index c4bb7c5..6a2a02f 100644
--- a/arch/arm/mach-s5p6440/include/mach/pwm-clock.h
+++ b/arch/arm/mach-s5p6440/include/mach/pwm-clock.h
@@ -1,11 +1,14 @@
/* linux/arch/arm/mach-s5p6440/include/mach/pwm-clock.h
*
+ * Copyright (c) 2009 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/
*
- * Copyright 2009 Samsung Electronics Co., Ltd.
- * http://www.samsung.com/
+ * Based on arch/arm/mach-s3c64xx/include/mach/pwm-clock.h
*
* S5P6440 - pwm clock and timer support
*
@@ -14,16 +17,19 @@
* published by the Free Software Foundation.
*/
+#ifndef __ASM_ARCH_PWMCLK_H
+#define __ASM_ARCH_PWMCLK_H __FILE__
+
/**
* pwm_cfg_src_is_tclk() - return whether the given mux config is a tclk
- * @cfg: The timer TCFG1 register bits shifted down to 0.
+ * @tcfg: The timer TCFG1 register bits shifted down to 0.
*
* Return true if the given configuration from TCFG1 is a TCLK instead
* any of the TDIV clocks.
*/
static inline int pwm_cfg_src_is_tclk(unsigned long tcfg)
{
- return tcfg == S3C2410_TCFG1_MUX_TCLK;
+ return 0;
}
/**
@@ -35,7 +41,7 @@ static inline int pwm_cfg_src_is_tclk(unsigned long tcfg)
*/
static inline unsigned long tcfg_to_divisor(unsigned long tcfg1)
{
- return 1 << (1 + tcfg1);
+ return 1 << tcfg1;
}
/**
@@ -45,7 +51,7 @@ static inline unsigned long tcfg_to_divisor(unsigned long tcfg1)
*/
static inline unsigned int pwm_tdiv_has_div1(void)
{
- return 0;
+ return 1;
}
/**
@@ -56,7 +62,9 @@ static inline unsigned int pwm_tdiv_has_div1(void)
*/
static inline unsigned long pwm_tdiv_div_bits(unsigned int div)
{
- return ilog2(div) - 1;
+ return ilog2(div);
}
-#define S3C_TCFG1_MUX_TCLK S3C2410_TCFG1_MUX_TCLK
+#define S3C_TCFG1_MUX_TCLK 0
+
+#endif /* __ASM_ARCH_PWMCLK_H */
diff --git a/arch/arm/mach-s5p6442/cpu.c b/arch/arm/mach-s5p6442/cpu.c
index bc2524d..a48fb55 100644
--- a/arch/arm/mach-s5p6442/cpu.c
+++ b/arch/arm/mach-s5p6442/cpu.c
@@ -95,7 +95,7 @@ void __init s5p6442_init_irq(void)
s5p_init_irq(vic, ARRAY_SIZE(vic));
}
-static struct sysdev_class s5p6442_sysclass = {
+struct sysdev_class s5p6442_sysclass = {
.name = "s5p6442-core",
};
diff --git a/arch/arm/mach-s5p6442/include/mach/pwm-clock.h b/arch/arm/mach-s5p6442/include/mach/pwm-clock.h
index 15e8525..2724b37 100644
--- a/arch/arm/mach-s5p6442/include/mach/pwm-clock.h
+++ b/arch/arm/mach-s5p6442/include/mach/pwm-clock.h
@@ -1,13 +1,14 @@
/* linux/arch/arm/mach-s5p6442/include/mach/pwm-clock.h
*
+ * Copyright (c) 2010 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/
*
- * Copyright 2010 Samsung Electronics Co., Ltd.
- * http://www.samsung.com/
- *
- * Based on arch/arm/plat-s3c24xx/include/mach/pwm-clock.h
+ * Based on arch/arm/mach-s3c64xx/include/mach/pwm-clock.h
*
* S5P6442 - pwm clock and timer support
*
@@ -21,14 +22,14 @@
/**
* pwm_cfg_src_is_tclk() - return whether the given mux config is a tclk
- * @cfg: The timer TCFG1 register bits shifted down to 0.
+ * @tcfg: The timer TCFG1 register bits shifted down to 0.
*
* Return true if the given configuration from TCFG1 is a TCLK instead
* any of the TDIV clocks.
*/
static inline int pwm_cfg_src_is_tclk(unsigned long tcfg)
{
- return tcfg == S3C2410_TCFG1_MUX_TCLK;
+ return tcfg == S3C64XX_TCFG1_MUX_TCLK;
}
/**
@@ -40,7 +41,7 @@ static inline int pwm_cfg_src_is_tclk(unsigned long tcfg)
*/
static inline unsigned long tcfg_to_divisor(unsigned long tcfg1)
{
- return 1 << (1 + tcfg1);
+ return 1 << tcfg1;
}
/**
@@ -50,7 +51,7 @@ static inline unsigned long tcfg_to_divisor(unsigned long tcfg1)
*/
static inline unsigned int pwm_tdiv_has_div1(void)
{
- return 0;
+ return 1;
}
/**
@@ -61,9 +62,9 @@ static inline unsigned int pwm_tdiv_has_div1(void)
*/
static inline unsigned long pwm_tdiv_div_bits(unsigned int div)
{
- return ilog2(div) - 1;
+ return ilog2(div);
}
-#define S3C_TCFG1_MUX_TCLK S3C2410_TCFG1_MUX_TCLK
+#define S3C_TCFG1_MUX_TCLK S3C64XX_TCFG1_MUX_TCLK
#endif /* __ASM_ARCH_PWMCLK_H */
diff --git a/arch/arm/mach-s5pv210/Makefile b/arch/arm/mach-s5pv210/Makefile
index 8ebf51c..0acbdb3 100644
--- a/arch/arm/mach-s5pv210/Makefile
+++ b/arch/arm/mach-s5pv210/Makefile
@@ -12,7 +12,7 @@ obj- :=
# Core support for S5PV210 system
-obj-$(CONFIG_CPU_S5PV210) += cpu.o init.o clock.o
+obj-$(CONFIG_CPU_S5PV210) += cpu.o init.o clock.o gpiolib.o
# machine support
diff --git a/arch/arm/mach-s5pv210/clock.c b/arch/arm/mach-s5pv210/clock.c
index ccccae2..154bca4 100644
--- a/arch/arm/mach-s5pv210/clock.c
+++ b/arch/arm/mach-s5pv210/clock.c
@@ -31,6 +31,128 @@
#include <plat/clock-clksrc.h>
#include <plat/s5pv210.h>
+static struct clksrc_clk clk_mout_apll = {
+ .clk = {
+ .name = "mout_apll",
+ .id = -1,
+ },
+ .sources = &clk_src_apll,
+ .reg_src = { .reg = S5P_CLK_SRC0, .shift = 0, .size = 1 },
+};
+
+static struct clksrc_clk clk_mout_epll = {
+ .clk = {
+ .name = "mout_epll",
+ .id = -1,
+ },
+ .sources = &clk_src_epll,
+ .reg_src = { .reg = S5P_CLK_SRC0, .shift = 8, .size = 1 },
+};
+
+static struct clksrc_clk clk_mout_mpll = {
+ .clk = {
+ .name = "mout_mpll",
+ .id = -1,
+ },
+ .sources = &clk_src_mpll,
+ .reg_src = { .reg = S5P_CLK_SRC0, .shift = 4, .size = 1 },
+};
+
+static struct clk *clkset_armclk_list[] = {
+ [0] = &clk_mout_apll.clk,
+ [1] = &clk_mout_mpll.clk,
+};
+
+static struct clksrc_sources clkset_armclk = {
+ .sources = clkset_armclk_list,
+ .nr_sources = ARRAY_SIZE(clkset_armclk_list),
+};
+
+static struct clksrc_clk clk_armclk = {
+ .clk = {
+ .name = "armclk",
+ .id = -1,
+ },
+ .sources = &clkset_armclk,
+ .reg_src = { .reg = S5P_CLK_SRC0, .shift = 16, .size = 1 },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 0, .size = 3 },
+};
+
+static struct clksrc_clk clk_hclk_msys = {
+ .clk = {
+ .name = "hclk_msys",
+ .id = -1,
+ .parent = &clk_armclk.clk,
+ },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 8, .size = 3 },
+};
+
+static struct clksrc_clk clk_pclk_msys = {
+ .clk = {
+ .name = "pclk_msys",
+ .id = -1,
+ .parent = &clk_hclk_msys.clk,
+ },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 12, .size = 3 },
+};
+
+static struct clksrc_clk clk_sclk_a2m = {
+ .clk = {
+ .name = "sclk_a2m",
+ .id = -1,
+ .parent = &clk_mout_apll.clk,
+ },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 4, .size = 3 },
+};
+
+static struct clk *clkset_hclk_sys_list[] = {
+ [0] = &clk_mout_mpll.clk,
+ [1] = &clk_sclk_a2m.clk,
+};
+
+static struct clksrc_sources clkset_hclk_sys = {
+ .sources = clkset_hclk_sys_list,
+ .nr_sources = ARRAY_SIZE(clkset_hclk_sys_list),
+};
+
+static struct clksrc_clk clk_hclk_dsys = {
+ .clk = {
+ .name = "hclk_dsys",
+ .id = -1,
+ },
+ .sources = &clkset_hclk_sys,
+ .reg_src = { .reg = S5P_CLK_SRC0, .shift = 20, .size = 1 },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 16, .size = 4 },
+};
+
+static struct clksrc_clk clk_pclk_dsys = {
+ .clk = {
+ .name = "pclk_dsys",
+ .id = -1,
+ .parent = &clk_hclk_dsys.clk,
+ },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 20, .size = 3 },
+};
+
+static struct clksrc_clk clk_hclk_psys = {
+ .clk = {
+ .name = "hclk_psys",
+ .id = -1,
+ },
+ .sources = &clkset_hclk_sys,
+ .reg_src = { .reg = S5P_CLK_SRC0, .shift = 24, .size = 1 },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 24, .size = 4 },
+};
+
+static struct clksrc_clk clk_pclk_psys = {
+ .clk = {
+ .name = "pclk_psys",
+ .id = -1,
+ .parent = &clk_hclk_psys.clk,
+ },
+ .reg_div = { .reg = S5P_CLK_DIV0, .shift = 28, .size = 3 },
+};
+
static int s5pv210_clk_ip0_ctrl(struct clk *clk, int enable)
{
return s5p_gatectrl(S5P_CLKGATE_IP0, clk, enable);
@@ -51,176 +173,226 @@ static int s5pv210_clk_ip3_ctrl(struct clk *clk, int enable)
return s5p_gatectrl(S5P_CLKGATE_IP3, clk, enable);
}
-static struct clk clk_h200 = {
- .name = "hclk200",
+static int s5pv210_clk_ip4_ctrl(struct clk *clk, int enable)
+{
+ return s5p_gatectrl(S5P_CLKGATE_IP4, clk, enable);
+}
+
+static int s5pv210_clk_mask0_ctrl(struct clk *clk, int enable)
+{
+ return s5p_gatectrl(S5P_CLK_SRC_MASK0, clk, enable);
+}
+
+static struct clk clk_sclk_hdmi27m = {
+ .name = "sclk_hdmi27m",
.id = -1,
+ .rate = 27000000,
};
-static struct clk clk_h100 = {
- .name = "hclk100",
+static struct clk clk_sclk_hdmiphy = {
+ .name = "sclk_hdmiphy",
.id = -1,
};
-static struct clk clk_h166 = {
- .name = "hclk166",
+static struct clk clk_sclk_usbphy0 = {
+ .name = "sclk_usbphy0",
.id = -1,
};
-static struct clk clk_h133 = {
- .name = "hclk133",
+static struct clk clk_sclk_usbphy1 = {
+ .name = "sclk_usbphy1",
.id = -1,
};
-static struct clk clk_p100 = {
- .name = "pclk100",
+static struct clk clk_pcmcdclk0 = {
+ .name = "pcmcdclk",
.id = -1,
};
-static struct clk clk_p83 = {
- .name = "pclk83",
+static struct clk clk_pcmcdclk1 = {
+ .name = "pcmcdclk",
.id = -1,
};
-static struct clk clk_p66 = {
- .name = "pclk66",
+static struct clk clk_pcmcdclk2 = {
+ .name = "pcmcdclk",
.id = -1,
};
-static struct clk *sys_clks[] = {
- &clk_h200,
- &clk_h100,
- &clk_h166,
- &clk_h133,
- &clk_p100,
- &clk_p83,
- &clk_p66
+static struct clk *clkset_vpllsrc_list[] = {
+ [0] = &clk_fin_vpll,
+ [1] = &clk_sclk_hdmi27m,
+};
+
+static struct clksrc_sources clkset_vpllsrc = {
+ .sources = clkset_vpllsrc_list,
+ .nr_sources = ARRAY_SIZE(clkset_vpllsrc_list),
+};
+
+static struct clksrc_clk clk_vpllsrc = {
+ .clk = {
+ .name = "vpll_src",
+ .id = -1,
+ .enable = s5pv210_clk_mask0_ctrl,
+ .ctrlbit = (1 << 7),
+ },
+ .sources = &clkset_vpllsrc,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 28, .size = 1 },
+};
+
+static struct clk *clkset_sclk_vpll_list[] = {
+ [0] = &clk_vpllsrc.clk,
+ [1] = &clk_fout_vpll,
+};
+
+static struct clksrc_sources clkset_sclk_vpll = {
+ .sources = clkset_sclk_vpll_list,
+ .nr_sources = ARRAY_SIZE(clkset_sclk_vpll_list),
+};
+
+static struct clksrc_clk clk_sclk_vpll = {
+ .clk = {
+ .name = "sclk_vpll",
+ .id = -1,
+ },
+ .sources = &clkset_sclk_vpll,
+ .reg_src = { .reg = S5P_CLK_SRC0, .shift = 12, .size = 1 },
+};
+
+static unsigned long s5pv210_clk_imem_get_rate(struct clk *clk)
+{
+ return clk_get_rate(clk->parent) / 2;
+}
+
+static struct clk_ops clk_hclk_imem_ops = {
+ .get_rate = s5pv210_clk_imem_get_rate,
};
static struct clk init_clocks_disable[] = {
{
.name = "rot",
.id = -1,
- .parent = &clk_h166,
+ .parent = &clk_hclk_dsys.clk,
.enable = s5pv210_clk_ip0_ctrl,
.ctrlbit = (1<<29),
}, {
.name = "otg",
.id = -1,
- .parent = &clk_h133,
+ .parent = &clk_hclk_psys.clk,
.enable = s5pv210_clk_ip1_ctrl,
.ctrlbit = (1<<16),
}, {
.name = "usb-host",
.id = -1,
- .parent = &clk_h133,
+ .parent = &clk_hclk_psys.clk,
.enable = s5pv210_clk_ip1_ctrl,
.ctrlbit = (1<<17),
}, {
.name = "lcd",
.id = -1,
- .parent = &clk_h166,
+ .parent = &clk_hclk_dsys.clk,
.enable = s5pv210_clk_ip1_ctrl,
.ctrlbit = (1<<0),
}, {
.name = "cfcon",
.id = 0,
- .parent = &clk_h133,
+ .parent = &clk_hclk_psys.clk,
.enable = s5pv210_clk_ip1_ctrl,
.ctrlbit = (1<<25),
}, {
.name = "hsmmc",
.id = 0,
- .parent = &clk_h133,
+ .parent = &clk_hclk_psys.clk,
.enable = s5pv210_clk_ip2_ctrl,
.ctrlbit = (1<<16),
}, {
.name = "hsmmc",
.id = 1,
- .parent = &clk_h133,
+ .parent = &clk_hclk_psys.clk,
.enable = s5pv210_clk_ip2_ctrl,
.ctrlbit = (1<<17),
}, {
.name = "hsmmc",
.id = 2,
- .parent = &clk_h133,
+ .parent = &clk_hclk_psys.clk,
.enable = s5pv210_clk_ip2_ctrl,
.ctrlbit = (1<<18),
}, {
.name = "hsmmc",
.id = 3,
- .parent = &clk_h133,
+ .parent = &clk_hclk_psys.clk,
.enable = s5pv210_clk_ip2_ctrl,
.ctrlbit = (1<<19),
}, {
.name = "systimer",
.id = -1,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<16),
}, {
.name = "watchdog",
.id = -1,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<22),
}, {
.name = "rtc",
.id = -1,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<15),
}, {
.name = "i2c",
.id = 0,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<7),
}, {
.name = "i2c",
.id = 1,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<8),
}, {
.name = "i2c",
.id = 2,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<9),
}, {
.name = "spi",
.id = 0,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<12),
}, {
.name = "spi",
.id = 1,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<13),
}, {
.name = "spi",
.id = 2,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<14),
}, {
.name = "timers",
.id = -1,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<23),
}, {
.name = "adc",
.id = -1,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<24),
}, {
.name = "keypad",
.id = -1,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<21),
}, {
@@ -246,106 +418,537 @@ static struct clk init_clocks_disable[] = {
static struct clk init_clocks[] = {
{
+ .name = "hclk_imem",
+ .id = -1,
+ .parent = &clk_hclk_msys.clk,
+ .ctrlbit = (1 << 5),
+ .enable = s5pv210_clk_ip0_ctrl,
+ .ops = &clk_hclk_imem_ops,
+ }, {
.name = "uart",
.id = 0,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<7),
}, {
.name = "uart",
.id = 1,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<8),
}, {
.name = "uart",
.id = 2,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<9),
}, {
.name = "uart",
.id = 3,
- .parent = &clk_p66,
+ .parent = &clk_pclk_psys.clk,
.enable = s5pv210_clk_ip3_ctrl,
.ctrlbit = (1<<10),
},
};
-static struct clksrc_clk clk_mout_apll = {
- .clk = {
- .name = "mout_apll",
+static struct clk *clkset_uart_list[] = {
+ [6] = &clk_mout_mpll.clk,
+ [7] = &clk_mout_epll.clk,
+};
+
+static struct clksrc_sources clkset_uart = {
+ .sources = clkset_uart_list,
+ .nr_sources = ARRAY_SIZE(clkset_uart_list),
+};
+
+static struct clk *clkset_group1_list[] = {
+ [0] = &clk_sclk_a2m.clk,
+ [1] = &clk_mout_mpll.clk,
+ [2] = &clk_mout_epll.clk,
+ [3] = &clk_sclk_vpll.clk,
+};
+
+static struct clksrc_sources clkset_group1 = {
+ .sources = clkset_group1_list,
+ .nr_sources = ARRAY_SIZE(clkset_group1_list),
+};
+
+static struct clk *clkset_sclk_onenand_list[] = {
+ [0] = &clk_hclk_psys.clk,
+ [1] = &clk_hclk_dsys.clk,
+};
+
+static struct clksrc_sources clkset_sclk_onenand = {
+ .sources = clkset_sclk_onenand_list,
+ .nr_sources = ARRAY_SIZE(clkset_sclk_onenand_list),
+};
+
+static struct clk *clkset_sclk_dac_list[] = {
+ [0] = &clk_sclk_vpll.clk,
+ [1] = &clk_sclk_hdmiphy,
+};
+
+static struct clksrc_sources clkset_sclk_dac = {
+ .sources = clkset_sclk_dac_list,
+ .nr_sources = ARRAY_SIZE(clkset_sclk_dac_list),
+};
+
+static struct clksrc_clk clk_sclk_dac = {
+ .clk = {
+ .name = "sclk_dac",
.id = -1,
+ .ctrlbit = (1 << 10),
+ .enable = s5pv210_clk_ip1_ctrl,
},
- .sources = &clk_src_apll,
- .reg_src = { .reg = S5P_CLK_SRC0, .shift = 0, .size = 1 },
+ .sources = &clkset_sclk_dac,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 8, .size = 1 },
};
-static struct clksrc_clk clk_mout_epll = {
- .clk = {
- .name = "mout_epll",
+static struct clksrc_clk clk_sclk_pixel = {
+ .clk = {
+ .name = "sclk_pixel",
.id = -1,
+ .parent = &clk_sclk_vpll.clk,
},
- .sources = &clk_src_epll,
- .reg_src = { .reg = S5P_CLK_SRC0, .shift = 8, .size = 1 },
+ .reg_div = { .reg = S5P_CLK_DIV1, .shift = 0, .size = 4},
};
-static struct clksrc_clk clk_mout_mpll = {
- .clk = {
- .name = "mout_mpll",
+static struct clk *clkset_sclk_hdmi_list[] = {
+ [0] = &clk_sclk_pixel.clk,
+ [1] = &clk_sclk_hdmiphy,
+};
+
+static struct clksrc_sources clkset_sclk_hdmi = {
+ .sources = clkset_sclk_hdmi_list,
+ .nr_sources = ARRAY_SIZE(clkset_sclk_hdmi_list),
+};
+
+static struct clksrc_clk clk_sclk_hdmi = {
+ .clk = {
+ .name = "sclk_hdmi",
.id = -1,
+ .enable = s5pv210_clk_ip1_ctrl,
+ .ctrlbit = (1 << 11),
},
- .sources = &clk_src_mpll,
- .reg_src = { .reg = S5P_CLK_SRC0, .shift = 4, .size = 1 },
+ .sources = &clkset_sclk_hdmi,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 0, .size = 1 },
};
-static struct clk *clkset_uart_list[] = {
+static struct clk *clkset_sclk_mixer_list[] = {
+ [0] = &clk_sclk_dac.clk,
+ [1] = &clk_sclk_hdmi.clk,
+};
+
+static struct clksrc_sources clkset_sclk_mixer = {
+ .sources = clkset_sclk_mixer_list,
+ .nr_sources = ARRAY_SIZE(clkset_sclk_mixer_list),
+};
+
+static struct clk *clkset_sclk_audio0_list[] = {
+ [0] = &clk_ext_xtal_mux,
+ [1] = &clk_pcmcdclk0,
+ [2] = &clk_sclk_hdmi27m,
+ [3] = &clk_sclk_usbphy0,
+ [4] = &clk_sclk_usbphy1,
+ [5] = &clk_sclk_hdmiphy,
[6] = &clk_mout_mpll.clk,
[7] = &clk_mout_epll.clk,
+ [8] = &clk_sclk_vpll.clk,
};
-static struct clksrc_sources clkset_uart = {
- .sources = clkset_uart_list,
- .nr_sources = ARRAY_SIZE(clkset_uart_list),
+static struct clksrc_sources clkset_sclk_audio0 = {
+ .sources = clkset_sclk_audio0_list,
+ .nr_sources = ARRAY_SIZE(clkset_sclk_audio0_list),
+};
+
+static struct clksrc_clk clk_sclk_audio0 = {
+ .clk = {
+ .name = "sclk_audio",
+ .id = 0,
+ .enable = s5pv210_clk_ip3_ctrl,
+ .ctrlbit = (1 << 4),
+ },
+ .sources = &clkset_sclk_audio0,
+ .reg_src = { .reg = S5P_CLK_SRC6, .shift = 0, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV6, .shift = 0, .size = 4 },
+};
+
+static struct clk *clkset_sclk_audio1_list[] = {
+ [0] = &clk_ext_xtal_mux,
+ [1] = &clk_pcmcdclk1,
+ [2] = &clk_sclk_hdmi27m,
+ [3] = &clk_sclk_usbphy0,
+ [4] = &clk_sclk_usbphy1,
+ [5] = &clk_sclk_hdmiphy,
+ [6] = &clk_mout_mpll.clk,
+ [7] = &clk_mout_epll.clk,
+ [8] = &clk_sclk_vpll.clk,
+};
+
+static struct clksrc_sources clkset_sclk_audio1 = {
+ .sources = clkset_sclk_audio1_list,
+ .nr_sources = ARRAY_SIZE(clkset_sclk_audio1_list),
+};
+
+static struct clksrc_clk clk_sclk_audio1 = {
+ .clk = {
+ .name = "sclk_audio",
+ .id = 1,
+ .enable = s5pv210_clk_ip3_ctrl,
+ .ctrlbit = (1 << 5),
+ },
+ .sources = &clkset_sclk_audio1,
+ .reg_src = { .reg = S5P_CLK_SRC6, .shift = 4, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV6, .shift = 4, .size = 4 },
+};
+
+static struct clk *clkset_sclk_audio2_list[] = {
+ [0] = &clk_ext_xtal_mux,
+ [1] = &clk_pcmcdclk0,
+ [2] = &clk_sclk_hdmi27m,
+ [3] = &clk_sclk_usbphy0,
+ [4] = &clk_sclk_usbphy1,
+ [5] = &clk_sclk_hdmiphy,
+ [6] = &clk_mout_mpll.clk,
+ [7] = &clk_mout_epll.clk,
+ [8] = &clk_sclk_vpll.clk,
+};
+
+static struct clksrc_sources clkset_sclk_audio2 = {
+ .sources = clkset_sclk_audio2_list,
+ .nr_sources = ARRAY_SIZE(clkset_sclk_audio2_list),
+};
+
+static struct clksrc_clk clk_sclk_audio2 = {
+ .clk = {
+ .name = "sclk_audio",
+ .id = 2,
+ .enable = s5pv210_clk_ip3_ctrl,
+ .ctrlbit = (1 << 6),
+ },
+ .sources = &clkset_sclk_audio2,
+ .reg_src = { .reg = S5P_CLK_SRC6, .shift = 8, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV6, .shift = 8, .size = 4 },
+};
+
+static struct clk *clkset_sclk_spdif_list[] = {
+ [0] = &clk_sclk_audio0.clk,
+ [1] = &clk_sclk_audio1.clk,
+ [2] = &clk_sclk_audio2.clk,
+};
+
+static struct clksrc_sources clkset_sclk_spdif = {
+ .sources = clkset_sclk_spdif_list,
+ .nr_sources = ARRAY_SIZE(clkset_sclk_spdif_list),
+};
+
+static struct clk *clkset_group2_list[] = {
+ [0] = &clk_ext_xtal_mux,
+ [1] = &clk_xusbxti,
+ [2] = &clk_sclk_hdmi27m,
+ [3] = &clk_sclk_usbphy0,
+ [4] = &clk_sclk_usbphy1,
+ [5] = &clk_sclk_hdmiphy,
+ [6] = &clk_mout_mpll.clk,
+ [7] = &clk_mout_epll.clk,
+ [8] = &clk_sclk_vpll.clk,
+};
+
+static struct clksrc_sources clkset_group2 = {
+ .sources = clkset_group2_list,
+ .nr_sources = ARRAY_SIZE(clkset_group2_list),
};
static struct clksrc_clk clksrcs[] = {
{
.clk = {
- .name = "uclk1",
+ .name = "sclk_dmc",
.id = -1,
+ },
+ .sources = &clkset_group1,
+ .reg_src = { .reg = S5P_CLK_SRC6, .shift = 24, .size = 2 },
+ .reg_div = { .reg = S5P_CLK_DIV6, .shift = 28, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_onenand",
+ .id = -1,
+ },
+ .sources = &clkset_sclk_onenand,
+ .reg_src = { .reg = S5P_CLK_SRC0, .shift = 28, .size = 1 },
+ .reg_div = { .reg = S5P_CLK_DIV6, .shift = 12, .size = 3 },
+ }, {
+ .clk = {
+ .name = "uclk1",
+ .id = 0,
.ctrlbit = (1<<17),
.enable = s5pv210_clk_ip3_ctrl,
},
.sources = &clkset_uart,
.reg_src = { .reg = S5P_CLK_SRC4, .shift = 16, .size = 4 },
.reg_div = { .reg = S5P_CLK_DIV4, .shift = 16, .size = 4 },
- }
+ }, {
+ .clk = {
+ .name = "uclk1",
+ .id = 1,
+ .enable = s5pv210_clk_ip3_ctrl,
+ .ctrlbit = (1 << 18),
+ },
+ .sources = &clkset_uart,
+ .reg_src = { .reg = S5P_CLK_SRC4, .shift = 20, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV4, .shift = 20, .size = 4 },
+ }, {
+ .clk = {
+ .name = "uclk1",
+ .id = 2,
+ .enable = s5pv210_clk_ip3_ctrl,
+ .ctrlbit = (1 << 19),
+ },
+ .sources = &clkset_uart,
+ .reg_src = { .reg = S5P_CLK_SRC4, .shift = 24, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV4, .shift = 24, .size = 4 },
+ }, {
+ .clk = {
+ .name = "uclk1",
+ .id = 3,
+ .enable = s5pv210_clk_ip3_ctrl,
+ .ctrlbit = (1 << 20),
+ },
+ .sources = &clkset_uart,
+ .reg_src = { .reg = S5P_CLK_SRC4, .shift = 28, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV4, .shift = 28, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_mixer",
+ .id = -1,
+ .enable = s5pv210_clk_ip1_ctrl,
+ .ctrlbit = (1 << 9),
+ },
+ .sources = &clkset_sclk_mixer,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 4, .size = 1 },
+ }, {
+ .clk = {
+ .name = "sclk_spdif",
+ .id = -1,
+ .enable = s5pv210_clk_mask0_ctrl,
+ .ctrlbit = (1 << 27),
+ },
+ .sources = &clkset_sclk_spdif,
+ .reg_src = { .reg = S5P_CLK_SRC6, .shift = 12, .size = 2 },
+ }, {
+ .clk = {
+ .name = "sclk_fimc",
+ .id = 0,
+ .enable = s5pv210_clk_ip0_ctrl,
+ .ctrlbit = (1 << 24),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC3, .shift = 12, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV3, .shift = 12, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_fimc",
+ .id = 1,
+ .enable = s5pv210_clk_ip0_ctrl,
+ .ctrlbit = (1 << 25),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC3, .shift = 16, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV3, .shift = 16, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_fimc",
+ .id = 2,
+ .enable = s5pv210_clk_ip0_ctrl,
+ .ctrlbit = (1 << 26),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC3, .shift = 20, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV3, .shift = 20, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_cam",
+ .id = 0,
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 12, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV1, .shift = 12, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_cam",
+ .id = 1,
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 16, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV1, .shift = 16, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_fimd",
+ .id = -1,
+ .enable = s5pv210_clk_ip1_ctrl,
+ .ctrlbit = (1 << 0),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 20, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV1, .shift = 20, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_mmc",
+ .id = 0,
+ .enable = s5pv210_clk_ip2_ctrl,
+ .ctrlbit = (1 << 16),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC4, .shift = 0, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV4, .shift = 0, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_mmc",
+ .id = 1,
+ .enable = s5pv210_clk_ip2_ctrl,
+ .ctrlbit = (1 << 17),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC4, .shift = 4, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV4, .shift = 4, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_mmc",
+ .id = 2,
+ .enable = s5pv210_clk_ip2_ctrl,
+ .ctrlbit = (1 << 18),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC4, .shift = 8, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV4, .shift = 8, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_mmc",
+ .id = 3,
+ .enable = s5pv210_clk_ip2_ctrl,
+ .ctrlbit = (1 << 19),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC4, .shift = 12, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV4, .shift = 12, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_mfc",
+ .id = -1,
+ .enable = s5pv210_clk_ip0_ctrl,
+ .ctrlbit = (1 << 16),
+ },
+ .sources = &clkset_group1,
+ .reg_src = { .reg = S5P_CLK_SRC2, .shift = 4, .size = 2 },
+ .reg_div = { .reg = S5P_CLK_DIV2, .shift = 4, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_g2d",
+ .id = -1,
+ .enable = s5pv210_clk_ip0_ctrl,
+ .ctrlbit = (1 << 12),
+ },
+ .sources = &clkset_group1,
+ .reg_src = { .reg = S5P_CLK_SRC2, .shift = 8, .size = 2 },
+ .reg_div = { .reg = S5P_CLK_DIV2, .shift = 8, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_g3d",
+ .id = -1,
+ .enable = s5pv210_clk_ip0_ctrl,
+ .ctrlbit = (1 << 8),
+ },
+ .sources = &clkset_group1,
+ .reg_src = { .reg = S5P_CLK_SRC2, .shift = 0, .size = 2 },
+ .reg_div = { .reg = S5P_CLK_DIV2, .shift = 0, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_csis",
+ .id = -1,
+ .enable = s5pv210_clk_ip0_ctrl,
+ .ctrlbit = (1 << 31),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC1, .shift = 24, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV1, .shift = 28, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_spi",
+ .id = 0,
+ .enable = s5pv210_clk_ip3_ctrl,
+ .ctrlbit = (1 << 12),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC5, .shift = 0, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV5, .shift = 0, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_spi",
+ .id = 1,
+ .enable = s5pv210_clk_ip3_ctrl,
+ .ctrlbit = (1 << 13),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC5, .shift = 4, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV5, .shift = 4, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_pwi",
+ .id = -1,
+ .enable = &s5pv210_clk_ip4_ctrl,
+ .ctrlbit = (1 << 2),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC6, .shift = 20, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV6, .shift = 24, .size = 4 },
+ }, {
+ .clk = {
+ .name = "sclk_pwm",
+ .id = -1,
+ .enable = s5pv210_clk_ip3_ctrl,
+ .ctrlbit = (1 << 23),
+ },
+ .sources = &clkset_group2,
+ .reg_src = { .reg = S5P_CLK_SRC5, .shift = 12, .size = 4 },
+ .reg_div = { .reg = S5P_CLK_DIV5, .shift = 12, .size = 4 },
+ },
};
/* Clock initialisation code */
-static struct clksrc_clk *init_parents[] = {
+static struct clksrc_clk *sysclks[] = {
&clk_mout_apll,
&clk_mout_epll,
&clk_mout_mpll,
+ &clk_armclk,
+ &clk_hclk_msys,
+ &clk_sclk_a2m,
+ &clk_hclk_dsys,
+ &clk_hclk_psys,
+ &clk_pclk_msys,
+ &clk_pclk_dsys,
+ &clk_pclk_psys,
+ &clk_vpllsrc,
+ &clk_sclk_vpll,
+ &clk_sclk_dac,
+ &clk_sclk_pixel,
+ &clk_sclk_hdmi,
};
-#define GET_DIV(clk, field) ((((clk) & field##_MASK) >> field##_SHIFT) + 1)
-
void __init_or_cpufreq s5pv210_setup_clocks(void)
{
struct clk *xtal_clk;
unsigned long xtal;
+ unsigned long vpllsrc;
unsigned long armclk;
- unsigned long hclk200;
- unsigned long hclk166;
- unsigned long hclk133;
- unsigned long pclk100;
- unsigned long pclk83;
- unsigned long pclk66;
+ unsigned long hclk_msys;
+ unsigned long hclk_dsys;
+ unsigned long hclk_psys;
+ unsigned long pclk_msys;
+ unsigned long pclk_dsys;
+ unsigned long pclk_psys;
unsigned long apll;
unsigned long mpll;
unsigned long epll;
+ unsigned long vpll;
unsigned int ptr;
u32 clkdiv0, clkdiv1;
@@ -368,59 +971,46 @@ void __init_or_cpufreq s5pv210_setup_clocks(void)
apll = s5p_get_pll45xx(xtal, __raw_readl(S5P_APLL_CON), pll_4508);
mpll = s5p_get_pll45xx(xtal, __raw_readl(S5P_MPLL_CON), pll_4502);
epll = s5p_get_pll45xx(xtal, __raw_readl(S5P_EPLL_CON), pll_4500);
-
- printk(KERN_INFO "S5PV210: PLL settings, A=%ld, M=%ld, E=%ld",
- apll, mpll, epll);
-
- armclk = apll / GET_DIV(clkdiv0, S5P_CLKDIV0_APLL);
- if (__raw_readl(S5P_CLK_SRC0) & S5P_CLKSRC0_MUX200_MASK)
- hclk200 = mpll / GET_DIV(clkdiv0, S5P_CLKDIV0_HCLK200);
- else
- hclk200 = armclk / GET_DIV(clkdiv0, S5P_CLKDIV0_HCLK200);
-
- if (__raw_readl(S5P_CLK_SRC0) & S5P_CLKSRC0_MUX166_MASK) {
- hclk166 = apll / GET_DIV(clkdiv0, S5P_CLKDIV0_A2M);
- hclk166 = hclk166 / GET_DIV(clkdiv0, S5P_CLKDIV0_HCLK166);
- } else
- hclk166 = mpll / GET_DIV(clkdiv0, S5P_CLKDIV0_HCLK166);
-
- if (__raw_readl(S5P_CLK_SRC0) & S5P_CLKSRC0_MUX133_MASK) {
- hclk133 = apll / GET_DIV(clkdiv0, S5P_CLKDIV0_A2M);
- hclk133 = hclk133 / GET_DIV(clkdiv0, S5P_CLKDIV0_HCLK133);
- } else
- hclk133 = mpll / GET_DIV(clkdiv0, S5P_CLKDIV0_HCLK133);
-
- pclk100 = hclk200 / GET_DIV(clkdiv0, S5P_CLKDIV0_PCLK100);
- pclk83 = hclk166 / GET_DIV(clkdiv0, S5P_CLKDIV0_PCLK83);
- pclk66 = hclk133 / GET_DIV(clkdiv0, S5P_CLKDIV0_PCLK66);
-
- printk(KERN_INFO "S5PV210: ARMCLK=%ld, HCLKM=%ld, HCLKD=%ld, \
- HCLKP=%ld, PCLKM=%ld, PCLKD=%ld, PCLKP=%ld\n",
- armclk, hclk200, hclk166, hclk133, pclk100, pclk83, pclk66);
+ vpllsrc = clk_get_rate(&clk_vpllsrc.clk);
+ vpll = s5p_get_pll45xx(vpllsrc, __raw_readl(S5P_VPLL_CON), pll_4502);
clk_fout_apll.rate = apll;
clk_fout_mpll.rate = mpll;
clk_fout_epll.rate = epll;
+ clk_fout_vpll.rate = vpll;
- clk_f.rate = armclk;
- clk_h.rate = hclk133;
- clk_p.rate = pclk66;
- clk_p66.rate = pclk66;
- clk_p83.rate = pclk83;
- clk_h133.rate = hclk133;
- clk_h166.rate = hclk166;
- clk_h200.rate = hclk200;
+ printk(KERN_INFO "S5PV210: PLL settings, A=%ld, M=%ld, E=%ld V=%ld",
+ apll, mpll, epll, vpll);
+
+ armclk = clk_get_rate(&clk_armclk.clk);
+ hclk_msys = clk_get_rate(&clk_hclk_msys.clk);
+ hclk_dsys = clk_get_rate(&clk_hclk_dsys.clk);
+ hclk_psys = clk_get_rate(&clk_hclk_psys.clk);
+ pclk_msys = clk_get_rate(&clk_pclk_msys.clk);
+ pclk_dsys = clk_get_rate(&clk_pclk_dsys.clk);
+ pclk_psys = clk_get_rate(&clk_pclk_psys.clk);
+
+ printk(KERN_INFO "S5PV210: ARMCLK=%ld, HCLKM=%ld, HCLKD=%ld\n"
+ "HCLKP=%ld, PCLKM=%ld, PCLKD=%ld, PCLKP=%ld\n",
+ armclk, hclk_msys, hclk_dsys, hclk_psys,
+ pclk_msys, pclk_dsys, pclk_psys);
- for (ptr = 0; ptr < ARRAY_SIZE(init_parents); ptr++)
- s3c_set_clksrc(init_parents[ptr], true);
+ clk_f.rate = armclk;
+ clk_h.rate = hclk_psys;
+ clk_p.rate = pclk_psys;
for (ptr = 0; ptr < ARRAY_SIZE(clksrcs); ptr++)
s3c_set_clksrc(&clksrcs[ptr], true);
}
static struct clk *clks[] __initdata = {
- &clk_mout_epll.clk,
- &clk_mout_mpll.clk,
+ &clk_sclk_hdmi27m,
+ &clk_sclk_hdmiphy,
+ &clk_sclk_usbphy0,
+ &clk_sclk_usbphy1,
+ &clk_pcmcdclk0,
+ &clk_pcmcdclk1,
+ &clk_pcmcdclk2,
};
void __init s5pv210_register_clocks(void)
@@ -433,13 +1023,12 @@ void __init s5pv210_register_clocks(void)
if (ret > 0)
printk(KERN_ERR "Failed to register %u clocks\n", ret);
+ for (ptr = 0; ptr < ARRAY_SIZE(sysclks); ptr++)
+ s3c_register_clksrc(sysclks[ptr], 1);
+
s3c_register_clksrc(clksrcs, ARRAY_SIZE(clksrcs));
s3c_register_clocks(init_clocks, ARRAY_SIZE(init_clocks));
- ret = s3c24xx_register_clocks(sys_clks, ARRAY_SIZE(sys_clks));
- if (ret > 0)
- printk(KERN_ERR "Failed to register system clocks\n");
-
clkp = init_clocks_disable;
for (ptr = 0; ptr < ARRAY_SIZE(init_clocks_disable); ptr++, clkp++) {
ret = s3c24xx_register_clock(clkp);
diff --git a/arch/arm/mach-s5pv210/cpu.c b/arch/arm/mach-s5pv210/cpu.c
index 0e0f8fd..2b776eb 100644
--- a/arch/arm/mach-s5pv210/cpu.c
+++ b/arch/arm/mach-s5pv210/cpu.c
@@ -100,7 +100,7 @@ void __init s5pv210_init_irq(void)
s5p_init_irq(vic, ARRAY_SIZE(vic));
}
-static struct sysdev_class s5pv210_sysclass = {
+struct sysdev_class s5pv210_sysclass = {
.name = "s5pv210-core",
};
diff --git a/arch/arm/mach-s5pv210/gpiolib.c b/arch/arm/mach-s5pv210/gpiolib.c
new file mode 100644
index 0000000..9ea8972
--- /dev/null
+++ b/arch/arm/mach-s5pv210/gpiolib.c
@@ -0,0 +1,261 @@
+/* linux/arch/arm/mach-s5pv210/gpiolib.c
+ *
+ * Copyright (c) 2010 Samsung Electronics Co., Ltd.
+ * http://www.samsung.com/
+ *
+ * S5PV210 - GPIOlib 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/kernel.h>
+#include <linux/irq.h>
+#include <linux/io.h>
+#include <linux/gpio.h>
+#include <plat/gpio-core.h>
+#include <plat/gpio-cfg.h>
+#include <plat/gpio-cfg-helpers.h>
+#include <mach/map.h>
+
+static struct s3c_gpio_cfg gpio_cfg = {
+ .set_config = s3c_gpio_setcfg_s3c64xx_4bit,
+ .set_pull = s3c_gpio_setpull_updown,
+ .get_pull = s3c_gpio_getpull_updown,
+};
+
+static struct s3c_gpio_cfg gpio_cfg_noint = {
+ .set_config = s3c_gpio_setcfg_s3c64xx_4bit,
+ .set_pull = s3c_gpio_setpull_updown,
+ .get_pull = s3c_gpio_getpull_updown,
+};
+
+/* GPIO bank's base address given the index of the bank in the
+ * list of all gpio banks.
+ */
+#define S5PV210_BANK_BASE(bank_nr) (S5P_VA_GPIO + ((bank_nr) * 0x20))
+
+/*
+ * Following are the gpio banks in v210.
+ *
+ * The 'config' member when left to NULL, is initialized to the default
+ * structure gpio_cfg in the init function below.
+ *
+ * The 'base' member is also initialized in the init function below.
+ * Note: The initialization of 'base' member of s3c_gpio_chip structure
+ * uses the above macro and depends on the banks being listed in order here.
+ */
+static struct s3c_gpio_chip s5pv210_gpio_4bit[] = {
+ {
+ .chip = {
+ .base = S5PV210_GPA0(0),
+ .ngpio = S5PV210_GPIO_A0_NR,
+ .label = "GPA0",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPA1(0),
+ .ngpio = S5PV210_GPIO_A1_NR,
+ .label = "GPA1",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPB(0),
+ .ngpio = S5PV210_GPIO_B_NR,
+ .label = "GPB",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPC0(0),
+ .ngpio = S5PV210_GPIO_C0_NR,
+ .label = "GPC0",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPC1(0),
+ .ngpio = S5PV210_GPIO_C1_NR,
+ .label = "GPC1",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPD0(0),
+ .ngpio = S5PV210_GPIO_D0_NR,
+ .label = "GPD0",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPD1(0),
+ .ngpio = S5PV210_GPIO_D1_NR,
+ .label = "GPD1",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPE0(0),
+ .ngpio = S5PV210_GPIO_E0_NR,
+ .label = "GPE0",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPE1(0),
+ .ngpio = S5PV210_GPIO_E1_NR,
+ .label = "GPE1",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPF0(0),
+ .ngpio = S5PV210_GPIO_F0_NR,
+ .label = "GPF0",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPF1(0),
+ .ngpio = S5PV210_GPIO_F1_NR,
+ .label = "GPF1",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPF2(0),
+ .ngpio = S5PV210_GPIO_F2_NR,
+ .label = "GPF2",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPF3(0),
+ .ngpio = S5PV210_GPIO_F3_NR,
+ .label = "GPF3",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPG0(0),
+ .ngpio = S5PV210_GPIO_G0_NR,
+ .label = "GPG0",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPG1(0),
+ .ngpio = S5PV210_GPIO_G1_NR,
+ .label = "GPG1",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPG2(0),
+ .ngpio = S5PV210_GPIO_G2_NR,
+ .label = "GPG2",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPG3(0),
+ .ngpio = S5PV210_GPIO_G3_NR,
+ .label = "GPG3",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPI(0),
+ .ngpio = S5PV210_GPIO_I_NR,
+ .label = "GPI",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPJ0(0),
+ .ngpio = S5PV210_GPIO_J0_NR,
+ .label = "GPJ0",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPJ1(0),
+ .ngpio = S5PV210_GPIO_J1_NR,
+ .label = "GPJ1",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPJ2(0),
+ .ngpio = S5PV210_GPIO_J2_NR,
+ .label = "GPJ2",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPJ3(0),
+ .ngpio = S5PV210_GPIO_J3_NR,
+ .label = "GPJ3",
+ },
+ }, {
+ .chip = {
+ .base = S5PV210_GPJ4(0),
+ .ngpio = S5PV210_GPIO_J4_NR,
+ .label = "GPJ4",
+ },
+ }, {
+ .config = &gpio_cfg_noint,
+ .chip = {
+ .base = S5PV210_MP01(0),
+ .ngpio = S5PV210_GPIO_MP01_NR,
+ .label = "MP01",
+ },
+ }, {
+ .config = &gpio_cfg_noint,
+ .chip = {
+ .base = S5PV210_MP02(0),
+ .ngpio = S5PV210_GPIO_MP02_NR,
+ .label = "MP02",
+ },
+ }, {
+ .config = &gpio_cfg_noint,
+ .chip = {
+ .base = S5PV210_MP03(0),
+ .ngpio = S5PV210_GPIO_MP03_NR,
+ .label = "MP03",
+ },
+ }, {
+ .base = (S5P_VA_GPIO + 0xC00),
+ .config = &gpio_cfg_noint,
+ .chip = {
+ .base = S5PV210_GPH0(0),
+ .ngpio = S5PV210_GPIO_H0_NR,
+ .label = "GPH0",
+ },
+ }, {
+ .base = (S5P_VA_GPIO + 0xC20),
+ .config = &gpio_cfg_noint,
+ .chip = {
+ .base = S5PV210_GPH1(0),
+ .ngpio = S5PV210_GPIO_H1_NR,
+ .label = "GPH1",
+ },
+ }, {
+ .base = (S5P_VA_GPIO + 0xC40),
+ .config = &gpio_cfg_noint,
+ .chip = {
+ .base = S5PV210_GPH2(0),
+ .ngpio = S5PV210_GPIO_H2_NR,
+ .label = "GPH2",
+ },
+ }, {
+ .base = (S5P_VA_GPIO + 0xC60),
+ .config = &gpio_cfg_noint,
+ .chip = {
+ .base = S5PV210_GPH3(0),
+ .ngpio = S5PV210_GPIO_H3_NR,
+ .label = "GPH3",
+ },
+ },
+};
+
+static __init int s5pv210_gpiolib_init(void)
+{
+ struct s3c_gpio_chip *chip = s5pv210_gpio_4bit;
+ int nr_chips = ARRAY_SIZE(s5pv210_gpio_4bit);
+ int i = 0;
+
+ for (i = 0; i < nr_chips; i++, chip++) {
+ if (chip->config == NULL)
+ chip->config = &gpio_cfg;
+ if (chip->base == NULL)
+ chip->base = S5PV210_BANK_BASE(i);
+ }
+
+ samsung_gpiolib_add_4bit_chips(s5pv210_gpio_4bit, nr_chips);
+
+ return 0;
+}
+core_initcall(s5pv210_gpiolib_init);
diff --git a/arch/arm/mach-s5pv210/include/mach/gpio.h b/arch/arm/mach-s5pv210/include/mach/gpio.h
index 533b020..d6461ba 100644
--- a/arch/arm/mach-s5pv210/include/mach/gpio.h
+++ b/arch/arm/mach-s5pv210/include/mach/gpio.h
@@ -18,6 +18,8 @@
#define gpio_cansleep __gpio_cansleep
#define gpio_to_irq __gpio_to_irq
+/* Practically, GPIO banks upto MP03 are the configurable gpio banks */
+
/* GPIO bank sizes */
#define S5PV210_GPIO_A0_NR (8)
#define S5PV210_GPIO_A1_NR (4)
@@ -47,6 +49,10 @@
#define S5PV210_GPIO_J3_NR (8)
#define S5PV210_GPIO_J4_NR (5)
+#define S5PV210_GPIO_MP01_NR (8)
+#define S5PV210_GPIO_MP02_NR (4)
+#define S5PV210_GPIO_MP03_NR (8)
+
/* GPIO bank numbers */
/* CONFIG_S3C_GPIO_SPACE allows the user to select extra
@@ -85,6 +91,9 @@ enum s5p_gpio_number {
S5PV210_GPIO_J2_START = S5PV210_GPIO_NEXT(S5PV210_GPIO_J1),
S5PV210_GPIO_J3_START = S5PV210_GPIO_NEXT(S5PV210_GPIO_J2),
S5PV210_GPIO_J4_START = S5PV210_GPIO_NEXT(S5PV210_GPIO_J3),
+ S5PV210_GPIO_MP01_START = S5PV210_GPIO_NEXT(S5PV210_GPIO_J4),
+ S5PV210_GPIO_MP02_START = S5PV210_GPIO_NEXT(S5PV210_GPIO_MP01),
+ S5PV210_GPIO_MP03_START = S5PV210_GPIO_NEXT(S5PV210_GPIO_MP02),
};
/* S5PV210 GPIO number definitions */
@@ -115,13 +124,16 @@ enum s5p_gpio_number {
#define S5PV210_GPJ2(_nr) (S5PV210_GPIO_J2_START + (_nr))
#define S5PV210_GPJ3(_nr) (S5PV210_GPIO_J3_START + (_nr))
#define S5PV210_GPJ4(_nr) (S5PV210_GPIO_J4_START + (_nr))
+#define S5PV210_MP01(_nr) (S5PV210_GPIO_MP01_START + (_nr))
+#define S5PV210_MP02(_nr) (S5PV210_GPIO_MP02_START + (_nr))
+#define S5PV210_MP03(_nr) (S5PV210_GPIO_MP03_START + (_nr))
/* the end of the S5PV210 specific gpios */
-#define S5PV210_GPIO_END (S5PV210_GPJ4(S5PV210_GPIO_J4_NR) + 1)
+#define S5PV210_GPIO_END (S5PV210_MP03(S5PV210_GPIO_MP03_NR) + 1)
#define S3C_GPIO_END S5PV210_GPIO_END
-/* define the number of gpios we need to the one after the GPJ4() range */
-#define ARCH_NR_GPIOS (S5PV210_GPJ4(S5PV210_GPIO_J4_NR) + \
+/* define the number of gpios we need to the one after the MP03() range */
+#define ARCH_NR_GPIOS (S5PV210_MP03(S5PV210_GPIO_MP03_NR) + \
CONFIG_SAMSUNG_GPIO_EXTRA + 1)
#include <asm-generic/gpio.h>
diff --git a/arch/arm/mach-s5pv210/include/mach/pwm-clock.h b/arch/arm/mach-s5pv210/include/mach/pwm-clock.h
index 69027fe..f8a9f1b 100644
--- a/arch/arm/mach-s5pv210/include/mach/pwm-clock.h
+++ b/arch/arm/mach-s5pv210/include/mach/pwm-clock.h
@@ -1,13 +1,14 @@
/* linux/arch/arm/mach-s5pv210/include/mach/pwm-clock.h
*
+ * Copyright (c) 2009 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/
*
- * Copyright (c) 2009 Samsung Electronics Co., Ltd.
- * http://www.samsung.com/
- *
- * Based on arch/arm/plat-s3c24xx/include/mach/pwm-clock.h
+ * Based on arch/arm/mach-s3c64xx/include/mach/pwm-clock.h
*
* S5PV210 - pwm clock and timer support
*
@@ -21,14 +22,14 @@
/**
* pwm_cfg_src_is_tclk() - return whether the given mux config is a tclk
- * @cfg: The timer TCFG1 register bits shifted down to 0.
+ * @tcfg: The timer TCFG1 register bits shifted down to 0.
*
* Return true if the given configuration from TCFG1 is a TCLK instead
* any of the TDIV clocks.
*/
static inline int pwm_cfg_src_is_tclk(unsigned long tcfg)
{
- return tcfg == S3C2410_TCFG1_MUX_TCLK;
+ return tcfg == S3C64XX_TCFG1_MUX_TCLK;
}
/**
@@ -40,7 +41,7 @@ static inline int pwm_cfg_src_is_tclk(unsigned long tcfg)
*/
static inline unsigned long tcfg_to_divisor(unsigned long tcfg1)
{
- return 1 << (1 + tcfg1);
+ return 1 << tcfg1;
}
/**
@@ -50,7 +51,7 @@ static inline unsigned long tcfg_to_divisor(unsigned long tcfg1)
*/
static inline unsigned int pwm_tdiv_has_div1(void)
{
- return 0;
+ return 1;
}
/**
@@ -61,9 +62,9 @@ static inline unsigned int pwm_tdiv_has_div1(void)
*/
static inline unsigned long pwm_tdiv_div_bits(unsigned int div)
{
- return ilog2(div) - 1;
+ return ilog2(div);
}
-#define S3C_TCFG1_MUX_TCLK S3C2410_TCFG1_MUX_TCLK
+#define S3C_TCFG1_MUX_TCLK S3C64XX_TCFG1_MUX_TCLK
#endif /* __ASM_ARCH_PWMCLK_H */
diff --git a/arch/arm/mm/mmu.c b/arch/arm/mm/mmu.c
index 241c24a..45a1bc2 100644
--- a/arch/arm/mm/mmu.c
+++ b/arch/arm/mm/mmu.c
@@ -869,9 +869,10 @@ void __init reserve_node_zero(pg_data_t *pgdat)
if (machine_is_p720t())
res_size = 0x00014000;
- /* H1940 and RX3715 need to reserve this for suspend */
+ /* H1940, RX3715 and RX1950 need to reserve this for suspend */
- if (machine_is_h1940() || machine_is_rx3715()) {
+ if (machine_is_h1940() || machine_is_rx3715()
+ || machine_is_rx1950()) {
reserve_bootmem_node(pgdat, 0x30003000, 0x1000,
BOOTMEM_DEFAULT);
reserve_bootmem_node(pgdat, 0x30081000, 0x1000,
diff --git a/arch/arm/plat-s3c24xx/devs.c b/arch/arm/plat-s3c24xx/devs.c
index 9265f09..cd5b41d 100644
--- a/arch/arm/plat-s3c24xx/devs.c
+++ b/arch/arm/plat-s3c24xx/devs.c
@@ -21,6 +21,7 @@
#include <linux/platform_device.h>
#include <linux/io.h>
#include <linux/slab.h>
+#include <linux/string.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
@@ -149,10 +150,14 @@ void __init s3c24xx_fb_set_platdata(struct s3c2410fb_mach_info *pd)
{
struct s3c2410fb_mach_info *npd;
- npd = kmalloc(sizeof(*npd), GFP_KERNEL);
+ npd = kmemdup(pd, sizeof(*npd), GFP_KERNEL);
if (npd) {
- memcpy(npd, pd, sizeof(*npd));
s3c_device_lcd.dev.platform_data = npd;
+ npd->displays = kmemdup(pd->displays,
+ sizeof(struct s3c2410fb_display) * npd->num_displays,
+ GFP_KERNEL);
+ if (!npd->displays)
+ printk(KERN_ERR "no memory for LCD display data\n");
} else {
printk(KERN_ERR "no memory for LCD platform data\n");
}
@@ -338,14 +343,6 @@ struct platform_device s3c_device_adc = {
.resource = s3c_adc_resource,
};
-/* HWMON */
-
-struct platform_device s3c_device_hwmon = {
- .name = "s3c-hwmon",
- .id = -1,
- .dev.parent = &s3c_device_adc.dev,
-};
-
/* SDI */
static struct resource s3c_sdi_resource[] = {
@@ -371,7 +368,7 @@ struct platform_device s3c_device_sdi = {
EXPORT_SYMBOL(s3c_device_sdi);
-void s3c24xx_mci_set_platdata(struct s3c24xx_mci_pdata *pdata)
+void __init s3c24xx_mci_set_platdata(struct s3c24xx_mci_pdata *pdata)
{
struct s3c24xx_mci_pdata *npd;
diff --git a/arch/arm/plat-s3c24xx/dma.c b/arch/arm/plat-s3c24xx/dma.c
index 93827b3..6ad274e 100644
--- a/arch/arm/plat-s3c24xx/dma.c
+++ b/arch/arm/plat-s3c24xx/dma.c
@@ -1104,7 +1104,7 @@ EXPORT_SYMBOL(s3c2410_dma_config);
* devaddr: physical address of the source
*/
-int s3c2410_dma_devconfig(int channel,
+int s3c2410_dma_devconfig(unsigned int channel,
enum s3c2410_dmasrc source,
unsigned long devaddr)
{
diff --git a/arch/arm/plat-s3c24xx/gpio.c b/arch/arm/plat-s3c24xx/gpio.c
index 45126d3..2f3d7c0 100644
--- a/arch/arm/plat-s3c24xx/gpio.c
+++ b/arch/arm/plat-s3c24xx/gpio.c
@@ -34,6 +34,8 @@
#include <mach/regs-gpio.h>
+#include <plat/gpio-core.h>
+
/* gpiolib wrappers until these are totally eliminated */
void s3c2410_gpio_pullup(unsigned int pin, unsigned int to)
@@ -68,10 +70,10 @@ EXPORT_SYMBOL(s3c2410_gpio_setpin);
unsigned int s3c2410_gpio_getpin(unsigned int pin)
{
- void __iomem *base = S3C24XX_GPIO_BASE(pin);
- unsigned long offs = S3C2410_GPIO_OFFSET(pin);
+ struct s3c_gpio_chip *chip = s3c_gpiolib_getchip(pin);
+ unsigned long offs = pin - chip->chip.base;
- return __raw_readl(base + 0x04) & (1<< offs);
+ return __raw_readl(chip->base + 0x04) & (1<< offs);
}
EXPORT_SYMBOL(s3c2410_gpio_getpin);
diff --git a/arch/arm/plat-s5p/clock.c b/arch/arm/plat-s5p/clock.c
index aa96e33..a8bfabf4 100644
--- a/arch/arm/plat-s5p/clock.c
+++ b/arch/arm/plat-s5p/clock.c
@@ -33,6 +33,11 @@ struct clk clk_ext_xtal_mux = {
.id = -1,
};
+struct clk clk_xusbxti = {
+ .name = "xusbxti",
+ .id = -1,
+};
+
static struct clk s5p_clk_27m = {
.name = "clk_27m",
.id = -1,
@@ -69,6 +74,13 @@ struct clk clk_fout_epll = {
.ctrlbit = (1 << 31),
};
+/* VPLL clock output */
+struct clk clk_fout_vpll = {
+ .name = "fout_vpll",
+ .id = -1,
+ .ctrlbit = (1 << 31),
+};
+
/* ARM clock */
struct clk clk_arm = {
.name = "armclk",
@@ -133,6 +145,7 @@ static struct clk *s5p_clks[] __initdata = {
&clk_fout_apll,
&clk_fout_mpll,
&clk_fout_epll,
+ &clk_fout_vpll,
&clk_arm,
&clk_vpll,
};
diff --git a/arch/arm/plat-s5p/include/plat/irqs.h b/arch/arm/plat-s5p/include/plat/irqs.h
index 42e757f..9ff3d71 100644
--- a/arch/arm/plat-s5p/include/plat/irqs.h
+++ b/arch/arm/plat-s5p/include/plat/irqs.h
@@ -79,7 +79,7 @@
#define S5P_IRQ_VIC2(x) (S5P_VIC2_BASE + (x))
#define S5P_IRQ_VIC3(x) (S5P_VIC3_BASE + (x))
-#define S5P_TIMER_IRQ(x) S5P_IRQ(11 + (x))
+#define S5P_TIMER_IRQ(x) (11 + (x))
#define IRQ_TIMER0 S5P_TIMER_IRQ(0)
#define IRQ_TIMER1 S5P_TIMER_IRQ(1)
diff --git a/arch/arm/plat-s5p/include/plat/s5p-clock.h b/arch/arm/plat-s5p/include/plat/s5p-clock.h
index 56fb8b4..aa0447a 100644
--- a/arch/arm/plat-s5p/include/plat/s5p-clock.h
+++ b/arch/arm/plat-s5p/include/plat/s5p-clock.h
@@ -23,10 +23,12 @@
#define clk_fin_vpll clk_ext_xtal_mux
extern struct clk clk_ext_xtal_mux;
+extern struct clk clk_xusbxti;
extern struct clk clk_48m;
extern struct clk clk_fout_apll;
extern struct clk clk_fout_mpll;
extern struct clk clk_fout_epll;
+extern struct clk clk_fout_vpll;
extern struct clk clk_arm;
extern struct clk clk_vpll;
diff --git a/arch/arm/plat-samsung/Kconfig b/arch/arm/plat-samsung/Kconfig
index d552c65..7a36cf8 100644
--- a/arch/arm/plat-samsung/Kconfig
+++ b/arch/arm/plat-samsung/Kconfig
@@ -160,6 +160,11 @@ config S3C_DEV_HSMMC2
help
Compile in platform device definitions for HSMMC channel 2
+config S3C_DEV_HWMON
+ bool
+ help
+ Compile in platform device definitions for HWMON
+
config S3C_DEV_I2C1
bool
help
diff --git a/arch/arm/plat-samsung/Makefile b/arch/arm/plat-samsung/Makefile
index 22c89d0..0ad820a 100644
--- a/arch/arm/plat-samsung/Makefile
+++ b/arch/arm/plat-samsung/Makefile
@@ -33,6 +33,7 @@ obj-$(CONFIG_S3C_ADC) += adc.o
obj-$(CONFIG_S3C_DEV_HSMMC) += dev-hsmmc.o
obj-$(CONFIG_S3C_DEV_HSMMC1) += dev-hsmmc1.o
obj-$(CONFIG_S3C_DEV_HSMMC2) += dev-hsmmc2.o
+obj-$(CONFIG_S3C_DEV_HWMON) += dev-hwmon.o
obj-y += dev-i2c0.o
obj-$(CONFIG_S3C_DEV_I2C1) += dev-i2c1.o
obj-$(CONFIG_S3C_DEV_FB) += dev-fb.o
diff --git a/arch/arm/plat-samsung/dev-hwmon.c b/arch/arm/plat-samsung/dev-hwmon.c
new file mode 100644
index 0000000..b3ffb95
--- /dev/null
+++ b/arch/arm/plat-samsung/dev-hwmon.c
@@ -0,0 +1,42 @@
+/* linux/arch/arm/plat-samsung/dev-hwmon.c
+ *
+ * Copyright 2008 Simtec Electronics
+ * Ben Dooks <ben@simtec.co.uk>
+ * http://armlinux.simtec.co.uk/
+ *
+ * Adapted for HWMON by Maurus Cuelenaere
+ *
+ * Samsung series device definition for HWMON
+ *
+ * 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/platform_device.h>
+
+#include <plat/devs.h>
+#include <plat/hwmon.h>
+
+struct platform_device s3c_device_hwmon = {
+ .name = "s3c-hwmon",
+ .id = -1,
+ .dev.parent = &s3c_device_adc.dev,
+};
+
+void __init s3c_hwmon_set_platdata(struct s3c_hwmon_pdata *pd)
+{
+ struct s3c_hwmon_pdata *npd;
+
+ if (!pd) {
+ printk(KERN_ERR "%s: no platform data\n", __func__);
+ return;
+ }
+
+ npd = kmemdup(pd, sizeof(struct s3c_hwmon_pdata), GFP_KERNEL);
+ if (!npd)
+ printk(KERN_ERR "%s: no memory for platform data\n", __func__);
+
+ s3c_device_hwmon.dev.platform_data = npd;
+}
diff --git a/arch/arm/plat-samsung/gpio-config.c b/arch/arm/plat-samsung/gpio-config.c
index 3282db3..a76eef5 100644
--- a/arch/arm/plat-samsung/gpio-config.c
+++ b/arch/arm/plat-samsung/gpio-config.c
@@ -33,9 +33,9 @@ int s3c_gpio_cfgpin(unsigned int pin, unsigned int config)
offset = pin - chip->chip.base;
- local_irq_save(flags);
+ s3c_gpio_lock(chip, flags);
ret = s3c_gpio_do_setcfg(chip, offset, config);
- local_irq_restore(flags);
+ s3c_gpio_unlock(chip, flags);
return ret;
}
@@ -51,9 +51,9 @@ unsigned s3c_gpio_getcfg(unsigned int pin)
if (chip) {
offset = pin - chip->chip.base;
- local_irq_save(flags);
+ s3c_gpio_lock(chip, flags);
ret = s3c_gpio_do_getcfg(chip, offset);
- local_irq_restore(flags);
+ s3c_gpio_unlock(chip, flags);
}
return ret;
@@ -72,9 +72,9 @@ int s3c_gpio_setpull(unsigned int pin, s3c_gpio_pull_t pull)
offset = pin - chip->chip.base;
- local_irq_save(flags);
+ s3c_gpio_lock(chip, flags);
ret = s3c_gpio_do_setpull(chip, offset, pull);
- local_irq_restore(flags);
+ s3c_gpio_unlock(chip, flags);
return ret;
}
diff --git a/arch/arm/plat-samsung/gpio.c b/arch/arm/plat-samsung/gpio.c
index 28d2ab8..b83a833 100644
--- a/arch/arm/plat-samsung/gpio.c
+++ b/arch/arm/plat-samsung/gpio.c
@@ -15,6 +15,7 @@
#include <linux/init.h>
#include <linux/io.h>
#include <linux/gpio.h>
+#include <linux/spinlock.h>
#include <plat/gpio-core.h>
@@ -52,14 +53,14 @@ static int s3c_gpiolib_input(struct gpio_chip *chip, unsigned offset)
unsigned long flags;
unsigned long con;
- local_irq_save(flags);
+ s3c_gpio_lock(ourchip, flags);
con = __raw_readl(base + 0x00);
con &= ~(3 << (offset * 2));
__raw_writel(con, base + 0x00);
- local_irq_restore(flags);
+ s3c_gpio_unlock(ourchip, flags);
return 0;
}
@@ -72,7 +73,7 @@ static int s3c_gpiolib_output(struct gpio_chip *chip,
unsigned long dat;
unsigned long con;
- local_irq_save(flags);
+ s3c_gpio_lock(ourchip, flags);
dat = __raw_readl(base + 0x04);
dat &= ~(1 << offset);
@@ -87,7 +88,7 @@ static int s3c_gpiolib_output(struct gpio_chip *chip,
__raw_writel(con, base + 0x00);
__raw_writel(dat, base + 0x04);
- local_irq_restore(flags);
+ s3c_gpio_unlock(ourchip, flags);
return 0;
}
@@ -99,7 +100,7 @@ static void s3c_gpiolib_set(struct gpio_chip *chip,
unsigned long flags;
unsigned long dat;
- local_irq_save(flags);
+ s3c_gpio_lock(ourchip, flags);
dat = __raw_readl(base + 0x04);
dat &= ~(1 << offset);
@@ -107,7 +108,7 @@ static void s3c_gpiolib_set(struct gpio_chip *chip,
dat |= 1 << offset;
__raw_writel(dat, base + 0x04);
- local_irq_restore(flags);
+ s3c_gpio_unlock(ourchip, flags);
}
static int s3c_gpiolib_get(struct gpio_chip *chip, unsigned offset)
@@ -131,6 +132,8 @@ __init void s3c_gpiolib_add(struct s3c_gpio_chip *chip)
BUG_ON(!gc->label);
BUG_ON(!gc->ngpio);
+ spin_lock_init(&chip->lock);
+
if (!gc->direction_input)
gc->direction_input = s3c_gpiolib_input;
if (!gc->direction_output)
diff --git a/arch/arm/plat-samsung/include/plat/clock.h b/arch/arm/plat-samsung/include/plat/clock.h
index 12caf48..0fbcd0e 100644
--- a/arch/arm/plat-samsung/include/plat/clock.h
+++ b/arch/arm/plat-samsung/include/plat/clock.h
@@ -74,6 +74,7 @@ extern struct clk clk_ext;
extern struct clk clk_h2;
extern struct clk clk_27m;
extern struct clk clk_48m;
+extern struct clk clk_xusbxti;
extern int clk_default_setrate(struct clk *clk, unsigned long rate);
extern struct clk_ops clk_ops_def_setrate;
diff --git a/arch/arm/plat-samsung/include/plat/cpu.h b/arch/arm/plat-samsung/include/plat/cpu.h
index 5dbeb79..6412933 100644
--- a/arch/arm/plat-samsung/include/plat/cpu.h
+++ b/arch/arm/plat-samsung/include/plat/cpu.h
@@ -79,6 +79,9 @@ extern struct sysdev_class s3c2442_sysclass;
extern struct sysdev_class s3c2443_sysclass;
extern struct sysdev_class s3c6410_sysclass;
extern struct sysdev_class s3c64xx_sysclass;
+extern struct sysdev_class s5p6440_sysclass;
+extern struct sysdev_class s5p6442_sysclass;
+extern struct sysdev_class s5pv210_sysclass;
extern void (*s5pc1xx_idle)(void);
diff --git a/arch/arm/plat-samsung/include/plat/dma.h b/arch/arm/plat-samsung/include/plat/dma.h
index 7584d75..2e8f8c6 100644
--- a/arch/arm/plat-samsung/include/plat/dma.h
+++ b/arch/arm/plat-samsung/include/plat/dma.h
@@ -110,8 +110,8 @@ extern int s3c2410_dma_config(unsigned int channel, int xferunit);
* configure the device we're talking to
*/
-extern int s3c2410_dma_devconfig(int channel, enum s3c2410_dmasrc source,
- unsigned long devaddr);
+extern int s3c2410_dma_devconfig(unsigned int channel,
+ enum s3c2410_dmasrc source, unsigned long devaddr);
/* s3c2410_dma_getposition
*
diff --git a/arch/arm/plat-samsung/include/plat/gpio-core.h b/arch/arm/plat-samsung/include/plat/gpio-core.h
index f0584f2..f3a68d1 100644
--- a/arch/arm/plat-samsung/include/plat/gpio-core.h
+++ b/arch/arm/plat-samsung/include/plat/gpio-core.h
@@ -44,16 +44,26 @@ struct s3c_gpio_cfg;
* @chip: The chip structure to be exported via gpiolib.
* @base: The base pointer to the gpio configuration registers.
* @config: special function and pull-resistor control information.
+ * @lock: Lock for exclusive access to this gpio bank.
* @pm_save: Save information for suspend/resume support.
*
* This wrapper provides the necessary information for the Samsung
* specific gpios being registered with gpiolib.
+ *
+ * The lock protects each gpio bank from multiple access of the shared
+ * configuration registers, or from reading of data whilst another thread
+ * is writing to the register set.
+ *
+ * Each chip has its own lock to avoid any contention between different
+ * CPU cores trying to get one lock for different GPIO banks, where each
+ * bank of GPIO has its own register space and configuration registers.
*/
struct s3c_gpio_chip {
struct gpio_chip chip;
struct s3c_gpio_cfg *config;
struct s3c_gpio_pm *pm;
void __iomem *base;
+ spinlock_t lock;
#ifdef CONFIG_PM
u32 pm_save[4];
#endif
@@ -138,3 +148,7 @@ extern struct s3c_gpio_pm s3c_gpio_pm_4bit;
#define __gpio_pm(x) NULL
#endif /* CONFIG_PM */
+
+/* locking wrappers to deal with multiple access to the same gpio bank */
+#define s3c_gpio_lock(_oc, _fl) spin_lock_irqsave(&(_oc)->lock, _fl)
+#define s3c_gpio_unlock(_oc, _fl) spin_unlock_irqrestore(&(_oc)->lock, _fl)
diff --git a/arch/arm/plat-samsung/include/plat/hwmon.h b/arch/arm/plat-samsung/include/plat/hwmon.h
index 1ba88ea..c167e44 100644
--- a/arch/arm/plat-samsung/include/plat/hwmon.h
+++ b/arch/arm/plat-samsung/include/plat/hwmon.h
@@ -37,5 +37,15 @@ struct s3c_hwmon_pdata {
struct s3c_hwmon_chcfg *in[8];
};
+/**
+ * s3c_hwmon_set_platdata - Set platform data for S3C HWMON device
+ * @pd: Platform data to register to device.
+ *
+ * Register the given platform data for use with the S3C HWMON device.
+ * The call will copy the platform data, so the board definitions can
+ * make the structure itself __initdata.
+ */
+extern void __init s3c_hwmon_set_platdata(struct s3c_hwmon_pdata *pd);
+
#endif /* __ASM_ARCH_ADC_HWMON_H */
diff --git a/arch/arm/plat-samsung/pm-gpio.c b/arch/arm/plat-samsung/pm-gpio.c
index 69a4c7f..d50ab9d 100644
--- a/arch/arm/plat-samsung/pm-gpio.c
+++ b/arch/arm/plat-samsung/pm-gpio.c
@@ -329,7 +329,7 @@ void s3c_pm_save_gpios(void)
struct s3c_gpio_chip *ourchip;
unsigned int gpio_nr;
- for (gpio_nr = 0; gpio_nr < S3C_GPIO_END; gpio_nr++) {
+ for (gpio_nr = 0; gpio_nr < S3C_GPIO_END;) {
ourchip = s3c_gpiolib_getchip(gpio_nr);
if (!ourchip)
continue;
@@ -367,7 +367,7 @@ void s3c_pm_restore_gpios(void)
struct s3c_gpio_chip *ourchip;
unsigned int gpio_nr;
- for (gpio_nr = 0; gpio_nr < S3C_GPIO_END; gpio_nr++) {
+ for (gpio_nr = 0; gpio_nr < S3C_GPIO_END;) {
ourchip = s3c_gpiolib_getchip(gpio_nr);
if (!ourchip)
continue;