[ARM] 3557/1: S3C24XX: centralise and cleanup uart registration

Patch from Ben Dooks

All the S3C24XX based devices currently have similar
uart blocks, in the same location. Make the process
of adding new uart blocks easier by commonising the
device definitions and adding a new init function
for the cpu code.

Signed-off-by: Ben Dooks <ben-linux@fluff.org>
Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
This commit is contained in:
Ben Dooks 2006-06-18 23:04:05 +01:00 committed by Russell King
parent 810c894f2b
commit 66a9b49a37
15 changed files with 154 additions and 185 deletions

View File

@ -37,8 +37,10 @@
#include <asm/mach/map.h>
#include <asm/arch/regs-gpio.h>
#include <asm/arch/regs-serial.h>
#include "cpu.h"
#include "devs.h"
#include "clock.h"
#include "s3c2400.h"
#include "s3c2410.h"
@ -208,6 +210,49 @@ void __init s3c24xx_init_clocks(int xtal)
(cpu->init_clocks)(xtal);
}
/* uart management */
static int nr_uarts __initdata = 0;
static struct s3c2410_uartcfg uart_cfgs[3];
/* s3c24xx_init_uartdevs
*
* copy the specified platform data and configuration into our central
* set of devices, before the data is thrown away after the init process.
*
* This also fills in the array passed to the serial driver for the
* early initialisation of the console.
*/
void __init s3c24xx_init_uartdevs(char *name,
struct s3c24xx_uart_resources *res,
struct s3c2410_uartcfg *cfg, int no)
{
struct platform_device *platdev;
struct s3c2410_uartcfg *cfgptr = uart_cfgs;
struct s3c24xx_uart_resources *resp;
int uart;
memcpy(cfgptr, cfg, sizeof(struct s3c2410_uartcfg) * no);
for (uart = 0; uart < no; uart++, cfg++, cfgptr++) {
platdev = s3c24xx_uart_src[cfgptr->hwport];
resp = res + cfgptr->hwport;
s3c24xx_uart_devs[uart] = platdev;
platdev->name = name;
platdev->resource = resp->resources;
platdev->num_resources = resp->nr_resources;
platdev->dev.platform_data = cfgptr;
}
nr_uarts = no;
}
void __init s3c24xx_init_uarts(struct s3c2410_uartcfg *cfg, int no)
{
if (cpu == NULL)
@ -232,6 +277,10 @@ static int __init s3c_arch_init(void)
if (ret != 0)
return ret;
ret = platform_add_devices(s3c24xx_uart_devs, nr_uarts);
if (ret != 0)
return ret;
if (board != NULL) {
struct platform_device **ptr = board->devices;
int i;

View File

@ -31,6 +31,8 @@
#define print_mhz(m) ((m) / MHZ), ((m / 1000) % 1000)
/* forward declaration */
struct s3c24xx_uart_resources;
struct platform_device;
struct s3c2410_uartcfg;
struct map_desc;
@ -44,6 +46,10 @@ extern void s3c24xx_init_uarts(struct s3c2410_uartcfg *cfg, int no);
extern void s3c24xx_init_clocks(int xtal);
extern void s3c24xx_init_uartdevs(char *name,
struct s3c24xx_uart_resources *res,
struct s3c2410_uartcfg *cfg, int no);
/* the board structure is used at first initialsation time
* to get info such as the devices to register for this
* board. This is done because platfrom_add_devices() cannot

View File

@ -38,10 +38,86 @@
#include <asm/arch/regs-serial.h>
#include "devs.h"
#include "cpu.h"
/* Serial port registrations */
struct platform_device *s3c24xx_uart_devs[3];
static struct resource s3c2410_uart0_resource[] = {
[0] = {
.start = S3C2410_PA_UART0,
.end = S3C2410_PA_UART0 + 0x3fff,
.flags = IORESOURCE_MEM,
},
[1] = {
.start = IRQ_S3CUART_RX0,
.end = IRQ_S3CUART_ERR0,
.flags = IORESOURCE_IRQ,
}
};
static struct resource s3c2410_uart1_resource[] = {
[0] = {
.start = S3C2410_PA_UART1,
.end = S3C2410_PA_UART1 + 0x3fff,
.flags = IORESOURCE_MEM,
},
[1] = {
.start = IRQ_S3CUART_RX1,
.end = IRQ_S3CUART_ERR1,
.flags = IORESOURCE_IRQ,
}
};
static struct resource s3c2410_uart2_resource[] = {
[0] = {
.start = S3C2410_PA_UART2,
.end = S3C2410_PA_UART2 + 0x3fff,
.flags = IORESOURCE_MEM,
},
[1] = {
.start = IRQ_S3CUART_RX2,
.end = IRQ_S3CUART_ERR2,
.flags = IORESOURCE_IRQ,
}
};
struct s3c24xx_uart_resources s3c2410_uart_resources[] __initdata = {
[0] = {
.resources = s3c2410_uart0_resource,
.nr_resources = ARRAY_SIZE(s3c2410_uart0_resource),
},
[1] = {
.resources = s3c2410_uart1_resource,
.nr_resources = ARRAY_SIZE(s3c2410_uart1_resource),
},
[2] = {
.resources = s3c2410_uart2_resource,
.nr_resources = ARRAY_SIZE(s3c2410_uart2_resource),
},
};
/* yart devices */
static struct platform_device s3c24xx_uart_device0 = {
.id = 0,
};
static struct platform_device s3c24xx_uart_device1 = {
.id = 1,
};
static struct platform_device s3c24xx_uart_device2 = {
.id = 2,
};
struct platform_device *s3c24xx_uart_src[3] = {
&s3c24xx_uart_device0,
&s3c24xx_uart_device1,
&s3c24xx_uart_device2,
};
struct platform_device *s3c24xx_uart_devs[3] = {
};
/* USB Host Controller */

View File

@ -17,7 +17,15 @@
#include <linux/config.h>
#include <linux/platform_device.h>
struct s3c24xx_uart_resources {
struct resource *resources;
unsigned long nr_resources;
};
extern struct s3c24xx_uart_resources s3c2410_uart_resources[];
extern struct platform_device *s3c24xx_uart_devs[];
extern struct platform_device *s3c24xx_uart_src[];
extern struct platform_device s3c_device_usb;
extern struct platform_device s3c_device_lcd;

View File

@ -131,7 +131,7 @@ static struct s3c24xx_uart_clksrc anubis_serial_clocks[] = {
};
static struct s3c2410_uartcfg anubis_uartcfgs[] = {
static struct s3c2410_uartcfg anubis_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,

View File

@ -208,7 +208,7 @@ static struct s3c24xx_uart_clksrc bast_serial_clocks[] = {
};
static struct s3c2410_uartcfg bast_uartcfgs[] = {
static struct s3c2410_uartcfg bast_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,

View File

@ -72,7 +72,7 @@ static struct map_desc h1940_iodesc[] __initdata = {
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
static struct s3c2410_uartcfg h1940_uartcfgs[] = {
static struct s3c2410_uartcfg h1940_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,

View File

@ -51,7 +51,7 @@ static struct map_desc nexcoder_iodesc[] __initdata = {
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
#define UFCON S3C2410_UFCON_RXTRIG12 | S3C2410_UFCON_FIFOMODE
static struct s3c2410_uartcfg nexcoder_uartcfgs[] = {
static struct s3c2410_uartcfg nexcoder_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,

View File

@ -95,8 +95,7 @@ static struct s3c24xx_uart_clksrc osiris_serial_clocks[] = {
}
};
static struct s3c2410_uartcfg osiris_uartcfgs[] = {
static struct s3c2410_uartcfg osiris_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,

View File

@ -45,7 +45,7 @@ static struct map_desc otom11_iodesc[] __initdata = {
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
#define UFCON S3C2410_UFCON_RXTRIG12 | S3C2410_UFCON_FIFOMODE
static struct s3c2410_uartcfg otom11_uartcfgs[] = {
static struct s3c2410_uartcfg otom11_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,

View File

@ -65,7 +65,7 @@ static struct map_desc smdk2410_iodesc[] __initdata = {
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
static struct s3c2410_uartcfg smdk2410_uartcfgs[] = {
static struct s3c2410_uartcfg smdk2410_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,

View File

@ -86,7 +86,7 @@ static struct map_desc smdk2440_iodesc[] __initdata = {
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
static struct s3c2410_uartcfg smdk2440_uartcfgs[] = {
static struct s3c2410_uartcfg smdk2440_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,

View File

@ -166,7 +166,7 @@ static struct s3c24xx_uart_clksrc vr1000_serial_clocks[] = {
}
};
static struct s3c2410_uartcfg vr1000_uartcfgs[] = {
static struct s3c2410_uartcfg vr1000_uartcfgs[] __initdata = {
[0] = {
.hwport = 0,
.flags = 0,

View File

@ -42,6 +42,7 @@
#include "s3c2410.h"
#include "cpu.h"
#include "devs.h"
#include "clock.h"
/* Initial IO mappings */
@ -55,93 +56,13 @@ static struct map_desc s3c2410_iodesc[] __initdata = {
IODESC_ENT(WATCHDOG),
};
static struct resource s3c_uart0_resource[] = {
[0] = {
.start = S3C2410_PA_UART0,
.end = S3C2410_PA_UART0 + 0x3fff,
.flags = IORESOURCE_MEM,
},
[1] = {
.start = IRQ_S3CUART_RX0,
.end = IRQ_S3CUART_ERR0,
.flags = IORESOURCE_IRQ,
}
};
static struct resource s3c_uart1_resource[] = {
[0] = {
.start = S3C2410_PA_UART1,
.end = S3C2410_PA_UART1 + 0x3fff,
.flags = IORESOURCE_MEM,
},
[1] = {
.start = IRQ_S3CUART_RX1,
.end = IRQ_S3CUART_ERR1,
.flags = IORESOURCE_IRQ,
}
};
static struct resource s3c_uart2_resource[] = {
[0] = {
.start = S3C2410_PA_UART2,
.end = S3C2410_PA_UART2 + 0x3fff,
.flags = IORESOURCE_MEM,
},
[1] = {
.start = IRQ_S3CUART_RX2,
.end = IRQ_S3CUART_ERR2,
.flags = IORESOURCE_IRQ,
}
};
/* our uart devices */
static struct platform_device s3c_uart0 = {
.name = "s3c2410-uart",
.id = 0,
.num_resources = ARRAY_SIZE(s3c_uart0_resource),
.resource = s3c_uart0_resource,
};
static struct platform_device s3c_uart1 = {
.name = "s3c2410-uart",
.id = 1,
.num_resources = ARRAY_SIZE(s3c_uart1_resource),
.resource = s3c_uart1_resource,
};
static struct platform_device s3c_uart2 = {
.name = "s3c2410-uart",
.id = 2,
.num_resources = ARRAY_SIZE(s3c_uart2_resource),
.resource = s3c_uart2_resource,
};
static struct platform_device *uart_devices[] __initdata = {
&s3c_uart0,
&s3c_uart1,
&s3c_uart2
};
static int s3c2410_uart_count = 0;
/* uart registration process */
void __init s3c2410_init_uarts(struct s3c2410_uartcfg *cfg, int no)
{
struct platform_device *platdev;
int uart;
for (uart = 0; uart < no; uart++, cfg++) {
platdev = uart_devices[cfg->hwport];
s3c24xx_uart_devs[uart] = platdev;
platdev->dev.platform_data = cfg;
}
s3c2410_uart_count = uart;
s3c24xx_init_uartdevs("s3c2410-uart", s3c2410_uart_resources, cfg, no);
}
/* s3c2410_map_io
@ -193,5 +114,5 @@ int __init s3c2410_init(void)
{
printk("S3C2410: Initialising architecture\n");
return platform_add_devices(s3c24xx_uart_devs, s3c2410_uart_count);
return 0;
}

View File

@ -60,95 +60,13 @@ static struct map_desc s3c2440_iodesc[] __initdata = {
IODESC_ENT(WATCHDOG),
};
static struct resource s3c_uart0_resource[] = {
[0] = {
.start = S3C2410_PA_UART0,
.end = S3C2410_PA_UART0 + 0x3fff,
.flags = IORESOURCE_MEM,
},
[1] = {
.start = IRQ_S3CUART_RX0,
.end = IRQ_S3CUART_ERR0,
.flags = IORESOURCE_IRQ,
}
};
static struct resource s3c_uart1_resource[] = {
[0] = {
.start = S3C2410_PA_UART1,
.end = S3C2410_PA_UART1 + 0x3fff,
.flags = IORESOURCE_MEM,
},
[1] = {
.start = IRQ_S3CUART_RX1,
.end = IRQ_S3CUART_ERR1,
.flags = IORESOURCE_IRQ,
}
};
static struct resource s3c_uart2_resource[] = {
[0] = {
.start = S3C2410_PA_UART2,
.end = S3C2410_PA_UART2 + 0x3fff,
.flags = IORESOURCE_MEM,
},
[1] = {
.start = IRQ_S3CUART_RX2,
.end = IRQ_S3CUART_ERR2,
.flags = IORESOURCE_IRQ,
}
};
/* our uart devices */
static struct platform_device s3c_uart0 = {
.name = "s3c2440-uart",
.id = 0,
.num_resources = ARRAY_SIZE(s3c_uart0_resource),
.resource = s3c_uart0_resource,
};
static struct platform_device s3c_uart1 = {
.name = "s3c2440-uart",
.id = 1,
.num_resources = ARRAY_SIZE(s3c_uart1_resource),
.resource = s3c_uart1_resource,
};
static struct platform_device s3c_uart2 = {
.name = "s3c2440-uart",
.id = 2,
.num_resources = ARRAY_SIZE(s3c_uart2_resource),
.resource = s3c_uart2_resource,
};
static struct platform_device *uart_devices[] __initdata = {
&s3c_uart0,
&s3c_uart1,
&s3c_uart2
};
/* uart initialisation */
static int __initdata s3c2440_uart_count;
void __init s3c2440_init_uarts(struct s3c2410_uartcfg *cfg, int no)
{
struct platform_device *platdev;
int uart;
for (uart = 0; uart < no; uart++, cfg++) {
platdev = uart_devices[cfg->hwport];
s3c24xx_uart_devs[uart] = platdev;
platdev->dev.platform_data = cfg;
}
s3c2440_uart_count = uart;
s3c24xx_init_uartdevs("s3c2440-uart", s3c2410_uart_resources, cfg, no);
}
#ifdef CONFIG_PM
static struct sleep_save s3c2440_sleep[] = {
@ -269,15 +187,7 @@ core_initcall(s3c2440_core_init);
int __init s3c2440_init(void)
{
int ret;
printk("S3C2440: Initialising architecture\n");
ret = sysdev_register(&s3c2440_sysdev);
if (ret != 0)
printk(KERN_ERR "failed to register sysdev for s3c2440\n");
else
ret = platform_add_devices(s3c24xx_uart_devs, s3c2440_uart_count);
return ret;
return sysdev_register(&s3c2440_sysdev);
}