串口的硬件平台实现smdk2440_map_io()初始化入口:
- static void __init smdk2440_map_io(void)
- {
- s3c24xx_init_io(smdk2440_iodesc,ARRAY_SIZE(smdk2440_iodesc));
- s3c24xx_init_clocks(12000000);
- s3c24xx_init_uarts(smdk2440_uartcfgs,ARRAY_SIZE(smdk2440_uartcfgs)); //串口初始化
- }
s3c24xx_init_uarts()初始化串口, 主要完成platform device结构相关参数的赋值,如IO,中断,以及platform device私有数据赋值等。
串口platform_device结构:
- static struct platform_device s3c24xx_uart_device0= {
- .id = 0, // ID号
- };
- static struct platform_devices3c24xx_uart_device1 = {
- .id = 1,
- };
- static struct platform_devices3c24xx_uart_device2 = {
- .id = 2,
- };
要完成platform_device参数初始化,主要涉及到一下数据结构:
串口配置数据结构:
- static struct s3c2410_uartcfgtq2440_uartcfgs[] __initdata = {
- [0]= {
- .hwport =0,
- .flags = 0,
- .ucon = 0x3c5, // rx,tx采用中断方式
- .ulcon = 0x03, //数据长度设置为8-bits
- .ufcon = 0x51, //开启FIFO,并设置rx,tx触发字节数
- },
- [1]= {
- .hwport =1,
- .flags = 0,
- .ucon = 0x3c5,
- .ulcon = 0x03,
- .ufcon = 0x51,
- },
- [2]= {
- .hwport =2,
- .flags = 0,
- .ucon = 0x3c5,
- .ulcon = 0x03,
- .ufcon = 0x51,
- }
- };
串口资源:
- static struct resources3c2410_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,
- }
- };
- struct s3c24xx_uart_resourcess3c2410_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),
- },
- [3]= {
- .resources = s3c2410_uart3_resource,
- .nr_resources = ARRAY_SIZE(s3c2410_uart3_resource),
- },
- };
最后通过函数s3c24xx_init_uartdevs()完成 串口platform_device的初始化:
- void __init s3c24xx_init_uartdevs(char*name,
- struct s3c24xx_uart_resources *res,
- struct s3c2410_uartcfg *cfg, int no)
- {//name = s3c2440-uart, res =s3c2410_uart_resources[], cfg = tq2440_uartcfgs, no = 3
- structplatform_device *platdev;
- structs3c2410_uartcfg *cfgptr = uart_cfgs;
- structs3c24xx_uart_resources *resp;
- intuart;
- memcpy(cfgptr,cfg, sizeof(struct s3c2410_uartcfg) * no);
- for(uart = 0; uart < no; uart++, cfg++, cfgptr++) {
- platdev= s3c24xx_uart_src[cfgptr->hwport]; //platdev = s3c24xx_uart_device0
- resp= res + cfgptr->hwport; //resp =s3c2410_uart_resources[] + tq2440_uartcfgs.hwport
- s3c24xx_uart_devs[uart]= platdev; //
- platdev->name= name;
- platdev->resource= resp->resources;
- platdev->num_resources= resp->nr_resources;
- platdev->dev.platform_data= cfgptr;//plat_form_data = cfgptr = tq2440_uartcfgs
- }
- nr_uarts= no;
- }
最终在platform_add_device()中完成注册
- platform_add_devices(s3c24xx_uart_devs,nr_uarts);
- int platform_add_devices(structplatform_device **devs, int num)
- {
- inti, ret = 0;
- for(i = 0; i < num; i++) {
- ret= platform_device_register(devs[i]);
- if(ret) {
- while(--i >= 0)
- platform_device_unregister(devs[i]);
- break;
- }
- }
- return ret;
- }
上一篇:ARM-Linux s3c2440 之I2C分析
下一篇:ARM-Linux s3c2440 之UART分析(四)
推荐阅读最新更新时间:2024-03-16 14:56