2013-01-02 22:47:40 +04:00
/*
2009-11-14 01:54:14 +03:00
* Copyright ( c ) 2003 - 2008 Simtec Electronics
2005-04-17 02:20:36 +04:00
* Ben Dooks < ben @ simtec . co . uk >
*
* Machine support for Thorcom VR1000 board . Designed for Thorcom by
* Simtec Electronics , http : //www.simtec.co.uk/
*
* This program is free software ; you can redistribute it and / or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation .
*
*/
# include <linux/kernel.h>
# include <linux/types.h>
# include <linux/interrupt.h>
# include <linux/list.h>
# include <linux/timer.h>
# include <linux/init.h>
2009-05-14 01:52:24 +04:00
# include <linux/gpio.h>
2005-06-24 00:56:47 +04:00
# include <linux/dm9000.h>
2008-07-03 14:24:42 +04:00
# include <linux/i2c.h>
2005-04-17 02:20:36 +04:00
# include <linux/serial.h>
# include <linux/tty.h>
# include <linux/serial_8250.h>
# include <linux/serial_reg.h>
2014-02-14 05:32:45 +04:00
# include <linux/serial_s3c.h>
2008-09-06 15:10:45 +04:00
# include <linux/io.h>
2005-04-17 02:20:36 +04:00
# include <asm/mach/arch.h>
# include <asm/mach/map.h>
# include <asm/mach/irq.h>
# include <asm/irq.h>
# include <asm/mach-types.h>
2012-08-24 17:22:12 +04:00
# include <linux/platform_data/leds-s3c24xx.h>
2013-01-02 22:47:40 +04:00
# include <linux/platform_data/i2c-s3c2410.h>
# include <linux/platform_data/asoc-s3c24xx_simtec.h>
# include <mach/hardware.h>
# include <mach/regs-gpio.h>
2014-01-14 17:24:24 +04:00
# include <mach/gpio-samsung.h>
2005-04-17 02:20:36 +04:00
2008-10-08 02:09:51 +04:00
# include <plat/clock.h>
2008-10-08 01:26:09 +04:00
# include <plat/cpu.h>
2013-01-02 22:47:40 +04:00
# include <plat/devs.h>
2013-01-10 06:47:04 +04:00
# include <plat/samsung-time.h>
2008-07-03 14:24:39 +04:00
2013-01-02 07:56:20 +04:00
# include "bast.h"
2012-01-03 17:02:03 +04:00
# include "common.h"
2013-01-02 07:56:20 +04:00
# include "simtec.h"
2013-01-02 22:47:40 +04:00
# include "vr1000.h"
2005-04-17 02:20:36 +04:00
/* macros for virtual address mods for the io space entries */
# define VA_C5(item) ((unsigned long)(item) + BAST_VAM_CS5)
# define VA_C4(item) ((unsigned long)(item) + BAST_VAM_CS4)
# define VA_C3(item) ((unsigned long)(item) + BAST_VAM_CS3)
# define VA_C2(item) ((unsigned long)(item) + BAST_VAM_CS2)
/* macros to modify the physical addresses for io space */
2005-11-08 22:15:30 +03:00
# define PA_CS2(item) (__phys_to_pfn((item) + S3C2410_CS2))
# define PA_CS3(item) (__phys_to_pfn((item) + S3C2410_CS3))
# define PA_CS4(item) (__phys_to_pfn((item) + S3C2410_CS4))
# define PA_CS5(item) (__phys_to_pfn((item) + S3C2410_CS5))
2005-04-17 02:20:36 +04:00
static struct map_desc vr1000_iodesc [ ] __initdata = {
/* ISA IO areas */
2005-11-08 22:15:30 +03:00
{
. virtual = ( u32 ) S3C24XX_VA_ISA_BYTE ,
. pfn = PA_CS2 ( BAST_PA_ISAIO ) ,
. length = SZ_16M ,
. type = MT_DEVICE ,
} , {
. virtual = ( u32 ) S3C24XX_VA_ISA_WORD ,
. pfn = PA_CS3 ( BAST_PA_ISAIO ) ,
. length = SZ_16M ,
. type = MT_DEVICE ,
} ,
/* CPLD control registers, and external interrupt controls */
{
. virtual = ( u32 ) VR1000_VA_CTRL1 ,
. pfn = __phys_to_pfn ( VR1000_PA_CTRL1 ) ,
. length = SZ_1M ,
. type = MT_DEVICE ,
} , {
. virtual = ( u32 ) VR1000_VA_CTRL2 ,
. pfn = __phys_to_pfn ( VR1000_PA_CTRL2 ) ,
. length = SZ_1M ,
. type = MT_DEVICE ,
} , {
. virtual = ( u32 ) VR1000_VA_CTRL3 ,
. pfn = __phys_to_pfn ( VR1000_PA_CTRL3 ) ,
. length = SZ_1M ,
. type = MT_DEVICE ,
} , {
. virtual = ( u32 ) VR1000_VA_CTRL4 ,
. pfn = __phys_to_pfn ( VR1000_PA_CTRL4 ) ,
. length = SZ_1M ,
. type = MT_DEVICE ,
} ,
2005-04-17 02:20:36 +04:00
} ;
# define UCON S3C2410_UCON_DEFAULT | S3C2410_UCON_UCLK
# define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
# define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
2006-06-19 02:04:05 +04:00
static struct s3c2410_uartcfg vr1000_uartcfgs [ ] __initdata = {
2005-04-17 02:20:36 +04:00
[ 0 ] = {
. hwport = 0 ,
. flags = 0 ,
. ucon = UCON ,
. ulcon = ULCON ,
. ufcon = UFCON ,
} ,
[ 1 ] = {
. hwport = 1 ,
. flags = 0 ,
. ucon = UCON ,
. ulcon = ULCON ,
. ufcon = UFCON ,
} ,
/* port 2 is not actually used */
[ 2 ] = {
. hwport = 2 ,
. flags = 0 ,
. ucon = UCON ,
. ulcon = ULCON ,
. ufcon = UFCON ,
}
} ;
/* definitions for the vr1000 extra 16550 serial ports */
# define VR1000_BAUDBASE (3692307)
# define VR1000_SERIAL_MAPBASE(x) (VR1000_PA_SERIAL + 0x80 + ((x) << 5))
static struct plat_serial8250_port serial_platform_data [ ] = {
[ 0 ] = {
. mapbase = VR1000_SERIAL_MAPBASE ( 0 ) ,
2013-01-02 22:47:40 +04:00
. irq = VR1000_IRQ_SERIAL + 0 ,
2005-04-17 02:20:36 +04:00
. flags = UPF_BOOT_AUTOCONF | UPF_IOREMAP ,
. iotype = UPIO_MEM ,
. regshift = 0 ,
. uartclk = VR1000_BAUDBASE ,
} ,
[ 1 ] = {
. mapbase = VR1000_SERIAL_MAPBASE ( 1 ) ,
2013-01-02 22:47:40 +04:00
. irq = VR1000_IRQ_SERIAL + 1 ,
2005-04-17 02:20:36 +04:00
. flags = UPF_BOOT_AUTOCONF | UPF_IOREMAP ,
. iotype = UPIO_MEM ,
. regshift = 0 ,
. uartclk = VR1000_BAUDBASE ,
} ,
[ 2 ] = {
. mapbase = VR1000_SERIAL_MAPBASE ( 2 ) ,
2013-01-02 22:47:40 +04:00
. irq = VR1000_IRQ_SERIAL + 2 ,
2005-04-17 02:20:36 +04:00
. flags = UPF_BOOT_AUTOCONF | UPF_IOREMAP ,
. iotype = UPIO_MEM ,
. regshift = 0 ,
. uartclk = VR1000_BAUDBASE ,
} ,
[ 3 ] = {
. mapbase = VR1000_SERIAL_MAPBASE ( 3 ) ,
2013-01-02 22:47:40 +04:00
. irq = VR1000_IRQ_SERIAL + 3 ,
2005-04-17 02:20:36 +04:00
. flags = UPF_BOOT_AUTOCONF | UPF_IOREMAP ,
. iotype = UPIO_MEM ,
. regshift = 0 ,
. uartclk = VR1000_BAUDBASE ,
} ,
{ } ,
} ;
static struct platform_device serial_device = {
. name = " serial8250 " ,
2005-09-08 19:04:41 +04:00
. id = PLAT8250_DEV_PLATFORM ,
2005-04-17 02:20:36 +04:00
. dev = {
. platform_data = serial_platform_data ,
} ,
} ;
2005-06-24 00:56:47 +04:00
/* DM9000 ethernet devices */
static struct resource vr1000_dm9k0_resource [ ] = {
2012-05-12 11:12:25 +04:00
[ 0 ] = DEFINE_RES_MEM ( S3C2410_CS5 + VR1000_PA_DM9000 , 4 ) ,
[ 1 ] = DEFINE_RES_MEM ( S3C2410_CS5 + VR1000_PA_DM9000 + 0x40 , 0x40 ) ,
2013-01-02 22:47:40 +04:00
[ 2 ] = DEFINE_RES_NAMED ( VR1000_IRQ_DM9000A , 1 , NULL , IORESOURCE_IRQ \
2012-05-12 11:12:25 +04:00
| IORESOURCE_IRQ_HIGHLEVEL ) ,
2005-06-24 00:56:47 +04:00
} ;
static struct resource vr1000_dm9k1_resource [ ] = {
2012-05-12 11:12:25 +04:00
[ 0 ] = DEFINE_RES_MEM ( S3C2410_CS5 + VR1000_PA_DM9000 + 0x80 , 4 ) ,
[ 1 ] = DEFINE_RES_MEM ( S3C2410_CS5 + VR1000_PA_DM9000 + 0xC0 , 0x40 ) ,
2013-01-02 22:47:40 +04:00
[ 2 ] = DEFINE_RES_NAMED ( VR1000_IRQ_DM9000N , 1 , NULL , IORESOURCE_IRQ \
2012-05-12 11:12:25 +04:00
| IORESOURCE_IRQ_HIGHLEVEL ) ,
2005-06-24 00:56:47 +04:00
} ;
/* for the moment we limit ourselves to 16bit IO until some
* better IO routines can be written and tested
*/
2005-10-12 22:58:07 +04:00
static struct dm9000_plat_data vr1000_dm9k_platdata = {
2005-06-24 00:56:47 +04:00
. flags = DM9000_PLATF_16BITONLY ,
} ;
static struct platform_device vr1000_dm9k0 = {
. name = " dm9000 " ,
. id = 0 ,
. num_resources = ARRAY_SIZE ( vr1000_dm9k0_resource ) ,
. resource = vr1000_dm9k0_resource ,
. dev = {
. platform_data = & vr1000_dm9k_platdata ,
}
} ;
static struct platform_device vr1000_dm9k1 = {
. name = " dm9000 " ,
. id = 1 ,
. num_resources = ARRAY_SIZE ( vr1000_dm9k1_resource ) ,
. resource = vr1000_dm9k1_resource ,
. dev = {
. platform_data = & vr1000_dm9k_platdata ,
}
} ;
2006-12-07 22:28:23 +03:00
/* LEDS */
static struct s3c24xx_led_platdata vr1000_led1_pdata = {
. name = " led1 " ,
2009-05-18 01:32:23 +04:00
. gpio = S3C2410_GPB ( 0 ) ,
2006-12-07 22:28:23 +03:00
. def_trigger = " " ,
} ;
static struct s3c24xx_led_platdata vr1000_led2_pdata = {
. name = " led2 " ,
2009-05-18 01:32:23 +04:00
. gpio = S3C2410_GPB ( 1 ) ,
2006-12-07 22:28:23 +03:00
. def_trigger = " " ,
} ;
static struct s3c24xx_led_platdata vr1000_led3_pdata = {
. name = " led3 " ,
2009-05-18 01:32:23 +04:00
. gpio = S3C2410_GPB ( 2 ) ,
2006-12-07 22:28:23 +03:00
. def_trigger = " " ,
} ;
static struct platform_device vr1000_led1 = {
. name = " s3c24xx_led " ,
. id = 1 ,
. dev = {
. platform_data = & vr1000_led1_pdata ,
} ,
} ;
static struct platform_device vr1000_led2 = {
. name = " s3c24xx_led " ,
. id = 2 ,
. dev = {
. platform_data = & vr1000_led2_pdata ,
} ,
} ;
static struct platform_device vr1000_led3 = {
. name = " s3c24xx_led " ,
2006-12-19 21:10:13 +03:00
. id = 3 ,
2006-12-07 22:28:23 +03:00
. dev = {
. platform_data = & vr1000_led3_pdata ,
} ,
} ;
2008-07-03 14:24:42 +04:00
/* I2C devices. */
static struct i2c_board_info vr1000_i2c_devs [ ] __initdata = {
{
I2C_BOARD_INFO ( " tlv320aic23 " , 0x1a ) ,
2008-07-03 14:24:44 +04:00
} , {
I2C_BOARD_INFO ( " tmp101 " , 0x48 ) ,
2008-07-03 14:24:42 +04:00
} , {
I2C_BOARD_INFO ( " m41st87 " , 0x68 ) ,
} ,
} ;
2005-06-24 00:56:47 +04:00
/* devices for this board */
2005-04-17 02:20:36 +04:00
static struct platform_device * vr1000_devices [ ] __initdata = {
2009-11-23 03:13:39 +03:00
& s3c_device_ohci ,
2005-04-17 02:20:36 +04:00
& s3c_device_lcd ,
& s3c_device_wdt ,
2008-10-31 19:14:40 +03:00
& s3c_device_i2c0 ,
2005-06-24 00:56:47 +04:00
& s3c_device_adc ,
2005-04-17 02:20:36 +04:00
& serial_device ,
2005-06-24 00:56:47 +04:00
& vr1000_dm9k0 ,
2006-12-07 22:28:23 +03:00
& vr1000_dm9k1 ,
& vr1000_led1 ,
& vr1000_led2 ,
& vr1000_led3 ,
2005-04-17 02:20:36 +04:00
} ;
2008-07-15 20:17:48 +04:00
static struct clk * vr1000_clocks [ ] __initdata = {
2005-04-17 02:20:36 +04:00
& s3c24xx_dclk0 ,
& s3c24xx_dclk1 ,
& s3c24xx_clkout0 ,
& s3c24xx_clkout1 ,
& s3c24xx_uclk ,
} ;
static void vr1000_power_off ( void )
{
2010-05-04 07:53:11 +04:00
gpio_direction_output ( S3C2410_GPB ( 9 ) , 1 ) ;
2005-04-17 02:20:36 +04:00
}
2005-09-20 20:24:33 +04:00
static void __init vr1000_map_io ( void )
2005-04-17 02:20:36 +04:00
{
/* initialise clock sources */
2008-04-16 03:12:39 +04:00
s3c24xx_dclk0 . parent = & clk_upll ;
2005-04-17 02:20:36 +04:00
s3c24xx_dclk0 . rate = 12 * 1000 * 1000 ;
s3c24xx_dclk1 . parent = NULL ;
s3c24xx_dclk1 . rate = 3692307 ;
s3c24xx_clkout0 . parent = & s3c24xx_dclk0 ;
s3c24xx_clkout1 . parent = & s3c24xx_dclk1 ;
s3c24xx_uclk . parent = & s3c24xx_clkout1 ;
2007-04-20 14:15:27 +04:00
s3c24xx_register_clocks ( vr1000_clocks , ARRAY_SIZE ( vr1000_clocks ) ) ;
2005-04-17 02:20:36 +04:00
pm_power_off = vr1000_power_off ;
s3c24xx_init_io ( vr1000_iodesc , ARRAY_SIZE ( vr1000_iodesc ) ) ;
s3c24xx_init_clocks ( 0 ) ;
s3c24xx_init_uarts ( vr1000_uartcfgs , ARRAY_SIZE ( vr1000_uartcfgs ) ) ;
2013-01-10 06:47:04 +04:00
samsung_set_timer_source ( SAMSUNG_PWM3 , SAMSUNG_PWM4 ) ;
2005-04-17 02:20:36 +04:00
}
2007-04-20 14:19:16 +04:00
static void __init vr1000_init ( void )
{
2008-10-31 19:14:40 +03:00
s3c_i2c0_set_platdata ( NULL ) ;
2007-04-20 14:19:16 +04:00
platform_add_devices ( vr1000_devices , ARRAY_SIZE ( vr1000_devices ) ) ;
2008-07-03 14:24:39 +04:00
2008-07-03 14:24:42 +04:00
i2c_register_board_info ( 0 , vr1000_i2c_devs ,
ARRAY_SIZE ( vr1000_i2c_devs ) ) ;
2008-07-03 14:24:39 +04:00
nor_simtec_init ( ) ;
2009-11-14 01:34:20 +03:00
simtec_audio_add ( NULL , true , NULL ) ;
2010-05-04 07:53:11 +04:00
WARN_ON ( gpio_request ( S3C2410_GPB ( 9 ) , " power off " ) ) ;
2007-04-20 14:19:16 +04:00
}
2005-04-17 02:20:36 +04:00
MACHINE_START ( VR1000 , " Thorcom-VR1000 " )
2005-07-03 20:38:58 +04:00
/* Maintainer: Ben Dooks <ben@simtec.co.uk> */
2011-07-06 06:38:17 +04:00
. atag_offset = 0x100 ,
2005-06-29 14:09:15 +04:00
. map_io = vr1000_map_io ,
2007-04-20 14:19:16 +04:00
. init_machine = vr1000_init ,
2013-03-07 07:38:19 +04:00
. init_irq = s3c2410_init_irq ,
2013-01-10 06:47:04 +04:00
. init_time = samsung_timer_init ,
2012-01-03 17:02:03 +04:00
. restart = s3c2410_restart ,
2005-04-17 02:20:36 +04:00
MACHINE_END