1/* linux/arch/arm/mach-s5pc100/dev-audio.c 2 * 3 * Copyright (c) 2010 Samsung Electronics Co. Ltd 4 * Jaswinder Singh <jassi.brar@samsung.com> 5 * 6 * This program is free software; you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License version 2 as 8 * published by the Free Software Foundation. 9 */ 10 11#include <linux/platform_device.h> 12#include <linux/dma-mapping.h> 13#include <linux/gpio.h> 14 15#include <plat/gpio-cfg.h> 16#include <plat/audio.h> 17 18#include <mach/map.h> 19#include <mach/dma.h> 20#include <mach/irqs.h> 21 22static int s5pc100_cfg_i2s(struct platform_device *pdev) 23{ 24 /* configure GPIO for i2s port */ 25 switch (pdev->id) { 26 case 1: 27 s3c_gpio_cfgpin(S5PC100_GPC(0), S3C_GPIO_SFN(2)); 28 s3c_gpio_cfgpin(S5PC100_GPC(1), S3C_GPIO_SFN(2)); 29 s3c_gpio_cfgpin(S5PC100_GPC(2), S3C_GPIO_SFN(2)); 30 s3c_gpio_cfgpin(S5PC100_GPC(3), S3C_GPIO_SFN(2)); 31 s3c_gpio_cfgpin(S5PC100_GPC(4), S3C_GPIO_SFN(2)); 32 break; 33 34 case 2: 35 s3c_gpio_cfgpin(S5PC100_GPG3(0), S3C_GPIO_SFN(4)); 36 s3c_gpio_cfgpin(S5PC100_GPG3(1), S3C_GPIO_SFN(4)); 37 s3c_gpio_cfgpin(S5PC100_GPG3(2), S3C_GPIO_SFN(4)); 38 s3c_gpio_cfgpin(S5PC100_GPG3(3), S3C_GPIO_SFN(4)); 39 s3c_gpio_cfgpin(S5PC100_GPG3(4), S3C_GPIO_SFN(4)); 40 break; 41 42 case -1: /* Dedicated pins */ 43 break; 44 45 default: 46 printk(KERN_ERR "Invalid Device %d\n", pdev->id); 47 return -EINVAL; 48 } 49 50 return 0; 51} 52 53static struct s3c_audio_pdata s3c_i2s_pdata = { 54 .cfg_gpio = s5pc100_cfg_i2s, 55}; 56 57static struct resource s5pc100_iis0_resource[] = { 58 [0] = { 59 .start = S5PC100_PA_I2S0, 60 .end = S5PC100_PA_I2S0 + 0x100 - 1, 61 .flags = IORESOURCE_MEM, 62 }, 63 [1] = { 64 .start = DMACH_I2S0_TX, 65 .end = DMACH_I2S0_TX, 66 .flags = IORESOURCE_DMA, 67 }, 68 [2] = { 69 .start = DMACH_I2S0_RX, 70 .end = DMACH_I2S0_RX, 71 .flags = IORESOURCE_DMA, 72 }, 73}; 74 75struct platform_device s5pc100_device_iis0 = { 76 .name = "s3c64xx-iis-v4", 77 .id = -1, 78 .num_resources = ARRAY_SIZE(s5pc100_iis0_resource), 79 .resource = s5pc100_iis0_resource, 80 .dev = { 81 .platform_data = &s3c_i2s_pdata, 82 }, 83}; 84 85static struct resource s5pc100_iis1_resource[] = { 86 [0] = { 87 .start = S5PC100_PA_I2S1, 88 .end = S5PC100_PA_I2S1 + 0x100 - 1, 89 .flags = IORESOURCE_MEM, 90 }, 91 [1] = { 92 .start = DMACH_I2S1_TX, 93 .end = DMACH_I2S1_TX, 94 .flags = IORESOURCE_DMA, 95 }, 96 [2] = { 97 .start = DMACH_I2S1_RX, 98 .end = DMACH_I2S1_RX, 99 .flags = IORESOURCE_DMA, 100 }, 101}; 102 103struct platform_device s5pc100_device_iis1 = { 104 .name = "s3c64xx-iis", 105 .id = 1, 106 .num_resources = ARRAY_SIZE(s5pc100_iis1_resource), 107 .resource = s5pc100_iis1_resource, 108 .dev = { 109 .platform_data = &s3c_i2s_pdata, 110 }, 111}; 112 113static struct resource s5pc100_iis2_resource[] = { 114 [0] = { 115 .start = S5PC100_PA_I2S2, 116 .end = S5PC100_PA_I2S2 + 0x100 - 1, 117 .flags = IORESOURCE_MEM, 118 }, 119 [1] = { 120 .start = DMACH_I2S2_TX, 121 .end = DMACH_I2S2_TX, 122 .flags = IORESOURCE_DMA, 123 }, 124 [2] = { 125 .start = DMACH_I2S2_RX, 126 .end = DMACH_I2S2_RX, 127 .flags = IORESOURCE_DMA, 128 }, 129}; 130 131struct platform_device s5pc100_device_iis2 = { 132 .name = "s3c64xx-iis", 133 .id = 2, 134 .num_resources = ARRAY_SIZE(s5pc100_iis2_resource), 135 .resource = s5pc100_iis2_resource, 136 .dev = { 137 .platform_data = &s3c_i2s_pdata, 138 }, 139}; 140 141/* PCM Controller platform_devices */ 142 143static int s5pc100_pcm_cfg_gpio(struct platform_device *pdev) 144{ 145 switch (pdev->id) { 146 case 0: 147 s3c_gpio_cfgpin(S5PC100_GPG3(0), S3C_GPIO_SFN(5)); 148 s3c_gpio_cfgpin(S5PC100_GPG3(1), S3C_GPIO_SFN(5)); 149 s3c_gpio_cfgpin(S5PC100_GPG3(2), S3C_GPIO_SFN(5)); 150 s3c_gpio_cfgpin(S5PC100_GPG3(3), S3C_GPIO_SFN(5)); 151 s3c_gpio_cfgpin(S5PC100_GPG3(4), S3C_GPIO_SFN(5)); 152 break; 153 154 case 1: 155 s3c_gpio_cfgpin(S5PC100_GPC(0), S3C_GPIO_SFN(3)); 156 s3c_gpio_cfgpin(S5PC100_GPC(1), S3C_GPIO_SFN(3)); 157 s3c_gpio_cfgpin(S5PC100_GPC(2), S3C_GPIO_SFN(3)); 158 s3c_gpio_cfgpin(S5PC100_GPC(3), S3C_GPIO_SFN(3)); 159 s3c_gpio_cfgpin(S5PC100_GPC(4), S3C_GPIO_SFN(3)); 160 break; 161 162 default: 163 printk(KERN_DEBUG "Invalid PCM Controller number!"); 164 return -EINVAL; 165 } 166 167 return 0; 168} 169 170static struct s3c_audio_pdata s3c_pcm_pdata = { 171 .cfg_gpio = s5pc100_pcm_cfg_gpio, 172}; 173 174static struct resource s5pc100_pcm0_resource[] = { 175 [0] = { 176 .start = S5PC100_PA_PCM0, 177 .end = S5PC100_PA_PCM0 + 0x100 - 1, 178 .flags = IORESOURCE_MEM, 179 }, 180 [1] = { 181 .start = DMACH_PCM0_TX, 182 .end = DMACH_PCM0_TX, 183 .flags = IORESOURCE_DMA, 184 }, 185 [2] = { 186 .start = DMACH_PCM0_RX, 187 .end = DMACH_PCM0_RX, 188 .flags = IORESOURCE_DMA, 189 }, 190}; 191 192struct platform_device s5pc100_device_pcm0 = { 193 .name = "samsung-pcm", 194 .id = 0, 195 .num_resources = ARRAY_SIZE(s5pc100_pcm0_resource), 196 .resource = s5pc100_pcm0_resource, 197 .dev = { 198 .platform_data = &s3c_pcm_pdata, 199 }, 200}; 201 202static struct resource s5pc100_pcm1_resource[] = { 203 [0] = { 204 .start = S5PC100_PA_PCM1, 205 .end = S5PC100_PA_PCM1 + 0x100 - 1, 206 .flags = IORESOURCE_MEM, 207 }, 208 [1] = { 209 .start = DMACH_PCM1_TX, 210 .end = DMACH_PCM1_TX, 211 .flags = IORESOURCE_DMA, 212 }, 213 [2] = { 214 .start = DMACH_PCM1_RX, 215 .end = DMACH_PCM1_RX, 216 .flags = IORESOURCE_DMA, 217 }, 218}; 219 220struct platform_device s5pc100_device_pcm1 = { 221 .name = "samsung-pcm", 222 .id = 1, 223 .num_resources = ARRAY_SIZE(s5pc100_pcm1_resource), 224 .resource = s5pc100_pcm1_resource, 225 .dev = { 226 .platform_data = &s3c_pcm_pdata, 227 }, 228}; 229 230/* AC97 Controller platform devices */ 231 232static int s5pc100_ac97_cfg_gpio(struct platform_device *pdev) 233{ 234 s3c_gpio_cfgpin(S5PC100_GPC(0), S3C_GPIO_SFN(4)); 235 s3c_gpio_cfgpin(S5PC100_GPC(1), S3C_GPIO_SFN(4)); 236 s3c_gpio_cfgpin(S5PC100_GPC(2), S3C_GPIO_SFN(4)); 237 s3c_gpio_cfgpin(S5PC100_GPC(3), S3C_GPIO_SFN(4)); 238 s3c_gpio_cfgpin(S5PC100_GPC(4), S3C_GPIO_SFN(4)); 239 240 return 0; 241} 242 243static struct resource s5pc100_ac97_resource[] = { 244 [0] = { 245 .start = S5PC100_PA_AC97, 246 .end = S5PC100_PA_AC97 + 0x100 - 1, 247 .flags = IORESOURCE_MEM, 248 }, 249 [1] = { 250 .start = DMACH_AC97_PCMOUT, 251 .end = DMACH_AC97_PCMOUT, 252 .flags = IORESOURCE_DMA, 253 }, 254 [2] = { 255 .start = DMACH_AC97_PCMIN, 256 .end = DMACH_AC97_PCMIN, 257 .flags = IORESOURCE_DMA, 258 }, 259 [3] = { 260 .start = DMACH_AC97_MICIN, 261 .end = DMACH_AC97_MICIN, 262 .flags = IORESOURCE_DMA, 263 }, 264 [4] = { 265 .start = IRQ_AC97, 266 .end = IRQ_AC97, 267 .flags = IORESOURCE_IRQ, 268 }, 269}; 270 271static struct s3c_audio_pdata s3c_ac97_pdata = { 272 .cfg_gpio = s5pc100_ac97_cfg_gpio, 273}; 274 275static u64 s5pc100_ac97_dmamask = DMA_BIT_MASK(32); 276 277struct platform_device s5pc100_device_ac97 = { 278 .name = "s3c-ac97", 279 .id = -1, 280 .num_resources = ARRAY_SIZE(s5pc100_ac97_resource), 281 .resource = s5pc100_ac97_resource, 282 .dev = { 283 .platform_data = &s3c_ac97_pdata, 284 .dma_mask = &s5pc100_ac97_dmamask, 285 .coherent_dma_mask = DMA_BIT_MASK(32), 286 }, 287}; 288