dma-s3c2410.c revision 85fd6d63bf2927b9da7ab1b0d46723bfdb13808c
1/* linux/arch/arm/mach-s3c2410/dma.c 2 * 3 * Copyright (c) 2006 Simtec Electronics 4 * Ben Dooks <ben@simtec.co.uk> 5 * 6 * S3C2410 DMA selection 7 * 8 * http://armlinux.simtec.co.uk/ 9 * 10 * This program is free software; you can redistribute it and/or modify 11 * it under the terms of the GNU General Public License version 2 as 12 * published by the Free Software Foundation. 13*/ 14 15#include <linux/kernel.h> 16#include <linux/init.h> 17#include <linux/device.h> 18#include <linux/serial_core.h> 19 20#include <mach/map.h> 21#include <mach/dma.h> 22 23#include <plat/cpu.h> 24#include <plat/dma-s3c24xx.h> 25 26#include <plat/regs-serial.h> 27#include <mach/regs-gpio.h> 28#include <plat/regs-ac97.h> 29#include <plat/regs-dma.h> 30#include <mach/regs-mem.h> 31#include <mach/regs-lcd.h> 32#include <mach/regs-sdi.h> 33#include <plat/regs-iis.h> 34#include <plat/regs-spi.h> 35 36static struct s3c24xx_dma_map __initdata s3c2410_dma_mappings[] = { 37 [DMACH_XD0] = { 38 .name = "xdreq0", 39 .channels[0] = S3C2410_DCON_CH0_XDREQ0 | DMA_CH_VALID, 40 }, 41 [DMACH_XD1] = { 42 .name = "xdreq1", 43 .channels[1] = S3C2410_DCON_CH1_XDREQ1 | DMA_CH_VALID, 44 }, 45 [DMACH_SDI] = { 46 .name = "sdi", 47 .channels[0] = S3C2410_DCON_CH0_SDI | DMA_CH_VALID, 48 .channels[2] = S3C2410_DCON_CH2_SDI | DMA_CH_VALID, 49 .channels[3] = S3C2410_DCON_CH3_SDI | DMA_CH_VALID, 50 }, 51 [DMACH_SPI0] = { 52 .name = "spi0", 53 .channels[1] = S3C2410_DCON_CH1_SPI | DMA_CH_VALID, 54 }, 55 [DMACH_SPI1] = { 56 .name = "spi1", 57 .channels[3] = S3C2410_DCON_CH3_SPI | DMA_CH_VALID, 58 }, 59 [DMACH_UART0] = { 60 .name = "uart0", 61 .channels[0] = S3C2410_DCON_CH0_UART0 | DMA_CH_VALID, 62 }, 63 [DMACH_UART1] = { 64 .name = "uart1", 65 .channels[1] = S3C2410_DCON_CH1_UART1 | DMA_CH_VALID, 66 }, 67 [DMACH_UART2] = { 68 .name = "uart2", 69 .channels[3] = S3C2410_DCON_CH3_UART2 | DMA_CH_VALID, 70 }, 71 [DMACH_TIMER] = { 72 .name = "timer", 73 .channels[0] = S3C2410_DCON_CH0_TIMER | DMA_CH_VALID, 74 .channels[2] = S3C2410_DCON_CH2_TIMER | DMA_CH_VALID, 75 .channels[3] = S3C2410_DCON_CH3_TIMER | DMA_CH_VALID, 76 }, 77 [DMACH_I2S_IN] = { 78 .name = "i2s-sdi", 79 .channels[1] = S3C2410_DCON_CH1_I2SSDI | DMA_CH_VALID, 80 .channels[2] = S3C2410_DCON_CH2_I2SSDI | DMA_CH_VALID, 81 }, 82 [DMACH_I2S_OUT] = { 83 .name = "i2s-sdo", 84 .channels[2] = S3C2410_DCON_CH2_I2SSDO | DMA_CH_VALID, 85 }, 86 [DMACH_USB_EP1] = { 87 .name = "usb-ep1", 88 .channels[0] = S3C2410_DCON_CH0_USBEP1 | DMA_CH_VALID, 89 }, 90 [DMACH_USB_EP2] = { 91 .name = "usb-ep2", 92 .channels[1] = S3C2410_DCON_CH1_USBEP2 | DMA_CH_VALID, 93 }, 94 [DMACH_USB_EP3] = { 95 .name = "usb-ep3", 96 .channels[2] = S3C2410_DCON_CH2_USBEP3 | DMA_CH_VALID, 97 }, 98 [DMACH_USB_EP4] = { 99 .name = "usb-ep4", 100 .channels[3] =S3C2410_DCON_CH3_USBEP4 | DMA_CH_VALID, 101 }, 102}; 103 104static void s3c2410_dma_select(struct s3c2410_dma_chan *chan, 105 struct s3c24xx_dma_map *map) 106{ 107 chan->dcon = map->channels[chan->number] & ~DMA_CH_VALID; 108} 109 110static struct s3c24xx_dma_selection __initdata s3c2410_dma_sel = { 111 .select = s3c2410_dma_select, 112 .dcon_mask = 7 << 24, 113 .map = s3c2410_dma_mappings, 114 .map_size = ARRAY_SIZE(s3c2410_dma_mappings), 115}; 116 117static struct s3c24xx_dma_order __initdata s3c2410_dma_order = { 118 .channels = { 119 [DMACH_SDI] = { 120 .list = { 121 [0] = 3 | DMA_CH_VALID, 122 [1] = 2 | DMA_CH_VALID, 123 [2] = 0 | DMA_CH_VALID, 124 }, 125 }, 126 [DMACH_I2S_IN] = { 127 .list = { 128 [0] = 1 | DMA_CH_VALID, 129 [1] = 2 | DMA_CH_VALID, 130 }, 131 }, 132 }, 133}; 134 135static int __init s3c2410_dma_add(struct device *dev) 136{ 137 s3c2410_dma_init(); 138 s3c24xx_dma_order_set(&s3c2410_dma_order); 139 return s3c24xx_dma_init_map(&s3c2410_dma_sel); 140} 141 142#if defined(CONFIG_CPU_S3C2410) 143static struct subsys_interface s3c2410_dma_interface = { 144 .name = "s3c2410_dma", 145 .subsys = &s3c2410_subsys, 146 .add_dev = s3c2410_dma_add, 147}; 148 149static int __init s3c2410_dma_drvinit(void) 150{ 151 return subsys_interface_register(&s3c2410_interface); 152} 153 154arch_initcall(s3c2410_dma_drvinit); 155 156static struct subsys_interface s3c2410a_dma_interface = { 157 .name = "s3c2410a_dma", 158 .subsys = &s3c2410a_subsys, 159 .add_dev = s3c2410_dma_add, 160}; 161 162static int __init s3c2410a_dma_drvinit(void) 163{ 164 return subsys_interface_register(&s3c2410a_dma_interface); 165} 166 167arch_initcall(s3c2410a_dma_drvinit); 168#endif 169 170#if defined(CONFIG_CPU_S3C2442) 171/* S3C2442 DMA contains the same selection table as the S3C2410 */ 172static struct subsys_interface s3c2442_dma_interface = { 173 .name = "s3c2442_dma", 174 .subsys = &s3c2442_subsys, 175 .add_dev = s3c2410_dma_add, 176}; 177 178static int __init s3c2442_dma_drvinit(void) 179{ 180 return subsys_interface_register(&s3c2442_dma_interface); 181} 182 183arch_initcall(s3c2442_dma_drvinit); 184#endif 185 186