s3c6400_pcm.c 30 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284
  1. /*
  2. * Common audio handling for the SA11x0 processor
  3. *
  4. * Copyright (C) 2007, Ryu Euiyoul <ryu.real@gmail.com>
  5. *
  6. * This program is free software; you can redistribute it and/or
  7. * modify it under the terms of the GNU General Public License.
  8. *
  9. * This module handles the generic buffering/DMA/mmap audio interface for
  10. * codecs connected to the SA1100 chip. All features depending on specific
  11. * hardware implementations like supported audio formats or samplerates are
  12. * relegated to separate specific modules.
  13. *
  14. */
  15. #include <linux/module.h>
  16. #include <linux/init.h>
  17. #include <linux/types.h>
  18. #include <linux/fs.h>
  19. #include <linux/mm.h>
  20. #include <linux/slab.h>
  21. #include <linux/sched.h>
  22. #include <linux/poll.h>
  23. #include <linux/device.h>
  24. #include <linux/errno.h>
  25. #include <linux/sound.h>
  26. #include <linux/soundcard.h>
  27. #include <linux/sysrq.h>
  28. #include <linux/device.h>
  29. #include <linux/dma-mapping.h>
  30. #include <asm/uaccess.h>
  31. #include <asm/io.h>
  32. #include <asm/delay.h>
  33. #include <asm/hardware.h>
  34. #include <asm/semaphore.h>
  35. #include <asm/dma.h>
  36. #include <asm/arch/dma.h>
  37. #include <asm/arch/regs-iis.h>
  38. #include <asm/arch/regs-ac97.h>
  39. #include "s3c6400_pcm.h"
  40. #undef DEBUG
  41. //#define DEBUG
  42. #ifdef DEBUG
  43. #define DPRINTK printk
  44. #else
  45. #define DPRINTK( x... )
  46. #endif
  47. #define AUDIO_NAME "s3c-audio"
  48. #define AUDIO_NBFRAGS_DEFAULT 8
  49. #define AUDIO_FRAGSIZE_DEFAULT 8192
  50. #define AUDIO_ACTIVE(state) ((state)->rd_ref || (state)->wr_ref)
  51. #define SPIN_ADDR (dma_addr_t)FLUSH_BASE_PHYS
  52. #define SPIN_SIZE 2048
  53. static int write_count = 0;
  54. void audio_dma_callback(struct s3c2410_dma_chan *dma_ch, void *buf_id,
  55. int size, enum s3c2410_dma_buffresult result);
  56. #ifdef CONFIG_SOUND_S3C6400_AC97
  57. /* DMA operation
  58. * Control AC97 global control register to set DMA operation
  59. * If the DMA transfer is endded you should turn off AC97 DMA
  60. * otherwise the noise will be heard. -JaeCheol Lee (2007.03.05)
  61. */
  62. static int audio_dma_operation(struct s3c2410_dma_chan *subchan, enum s3c2410_chan_op op);
  63. #endif
  64. /*
  65. * DMA processing
  66. */
  67. static struct s3c2410_dma_client s3cplay_dma_client = {
  68. .name = "s3c-play",
  69. };
  70. #if defined (CONFIG_AC97_MIC_PATH) || defined (CONFIG_SOUND_S3C6400_I2S)
  71. static struct s3c2410_dma_client s3cmic_dma_client = {
  72. .name = "s3c-recmic",
  73. };
  74. #endif
  75. #ifdef CONFIG_SOUND_S3C6400_AC97
  76. static struct s3c2410_dma_client s3cline_dma_client = {
  77. .name = "s3c-recline",
  78. };
  79. #endif
  80. #ifdef CONFIG_SOUND_S3C6400_AC97
  81. static int s3c_ac97_dma_init(audio_stream_t * s, int mode)
  82. {
  83. if (mode == 0) { //play
  84. s3c2410_dma_devconfig(s->subchannel, S3C2410_DMASRC_MEM, 0, AC_PCMDATA_PHYS);
  85. s3c2410_dma_set_opfn(s->subchannel, audio_dma_operation);
  86. }
  87. /* attach capture channel */
  88. if (mode == 1) {
  89. s3c2410_dma_devconfig(s->subchannel, S3C2410_DMASRC_HW, 0, AC_PCMDATA_PHYS);
  90. }
  91. if (mode == 2) {
  92. s3c2410_dma_devconfig(s->subchannel, S3C2410_DMASRC_HW, 0, AC_MICDATA_PHYS);
  93. }
  94. s3c2410_dma_config(s->subchannel, 4, 4);
  95. s3c2410_dma_set_buffdone_fn(s->subchannel, audio_dma_callback);
  96. s3c2410_dma_setflags(s->subchannel, S3C2410_DMAF_AUTOSTART);
  97. return 0;
  98. }
  99. #endif
  100. #ifdef CONFIG_SOUND_S3C6400_I2S
  101. static int s3c_iis_dma_init(audio_stream_t *s,int mode)
  102. {
  103. if(mode == 0) //play
  104. {
  105. s3c2410_dma_devconfig(s->subchannel, S3C2410_DMASRC_MEM, 0, S3C_IIS0TXD_PHYS);
  106. }
  107. /* attach capture channel */
  108. if(mode ==1)
  109. {
  110. s3c2410_dma_devconfig(s->subchannel, S3C2410_DMASRC_HW, 0, S3C_IIS0RXD_PHYS);
  111. }
  112. s3c2410_dma_config(s->subchannel, 4, 0);
  113. s3c2410_dma_set_buffdone_fn(s->subchannel, audio_dma_callback);
  114. s3c2410_dma_setflags(s->subchannel, S3C2410_DMAF_AUTOSTART);
  115. return 0;
  116. }
  117. #endif
  118. static u_int audio_get_dma_pos(audio_stream_t *s)
  119. {
  120. int dma_srcpos,dma_dstpos;
  121. audio_buf_t *b = &s->buffers[s->dma_tail];
  122. u_int offset;
  123. if (b->dma_ref) {
  124. s3c2410_dma_getposition(s->subchannel, &dma_srcpos, &dma_dstpos);
  125. offset = dma_srcpos - b->dma_addr;
  126. if (offset >= s->fragsize)
  127. offset = s->fragsize - 4;
  128. } else if (s->pending_frags) {
  129. offset = b->offset;
  130. } else {
  131. offset = 0;
  132. }
  133. return offset;
  134. }
  135. static void audio_stop_dma(audio_stream_t *s)
  136. {
  137. u_int pos;
  138. unsigned long flags;
  139. audio_buf_t *b;
  140. if (!s->buffers)
  141. return;
  142. local_irq_save(flags);
  143. s->stopped = 1;
  144. pos = audio_get_dma_pos(s);
  145. s3c2410_dma_ctrl(s->subchannel, S3C2410_DMAOP_FLUSH);
  146. local_irq_restore(flags);
  147. /* back up pointers to be ready to restart from the same spot */
  148. while (s->dma_head != s->dma_tail) {
  149. b = &s->buffers[s->dma_head];
  150. if (b->dma_ref) {
  151. b->dma_ref = 0;
  152. b->offset = 0;
  153. }
  154. s->pending_frags++;
  155. if (s->dma_head == 0)
  156. s->dma_head = s->nbfrags;
  157. s->dma_head--;
  158. }
  159. b = &s->buffers[s->dma_head];
  160. if (b->dma_ref) {
  161. b->offset = pos;
  162. b->dma_ref = 0;
  163. }
  164. }
  165. static void audio_reset(audio_stream_t *s)
  166. {
  167. if (s->buffers) {
  168. audio_stop_dma(s);
  169. s->buffers[s->dma_head].offset = 0;
  170. s->buffers[s->usr_head].offset = 0;
  171. s->usr_head = s->dma_head;
  172. s->pending_frags = 0;
  173. sema_init(&s->sem, s->nbfrags);
  174. }
  175. s->active = 0;
  176. s->stopped = 0;
  177. }
  178. static void audio_process_dma(audio_stream_t *s)
  179. {
  180. while (s->pending_frags) {
  181. audio_buf_t *b = &s->buffers[s->dma_head];
  182. u_int dma_size = s->fragsize - b->offset;
  183. s3c2410_dma_enqueue(s->subchannel, (void *) s,
  184. b->dma_addr+b->offset,dma_size);
  185. b->dma_ref++;
  186. b->offset += dma_size;
  187. if (b->offset >= s->fragsize) {
  188. s->pending_frags--;
  189. if (++s->dma_head >= s->nbfrags)
  190. s->dma_head = 0;
  191. }
  192. }
  193. }
  194. void audio_dma_callback(struct s3c2410_dma_chan *dma_ch, void *buf_id,
  195. int size, enum s3c2410_dma_buffresult result)
  196. {
  197. audio_stream_t *s = (audio_stream_t *)buf_id;
  198. audio_buf_t *b = &s->buffers[s->dma_tail];
  199. if (!s->buffers) {
  200. printk(KERN_CRIT "elfin: received DMA IRQ for non existent buffers!\n");
  201. return;
  202. } else if (b->dma_ref && --b->dma_ref == 0 && b->offset >= s->fragsize) {
  203. /* This fragment is done */
  204. b->offset = 0;
  205. s->bytecount += s->fragsize;
  206. s->fragcount++;
  207. if (++s->dma_tail >= s->nbfrags)
  208. s->dma_tail = 0;
  209. if (!s->mapped)
  210. up(&s->sem);
  211. else
  212. s->pending_frags++;
  213. wake_up(&s->wq);
  214. }
  215. audio_process_dma(s);
  216. }
  217. #ifdef CONFIG_SOUND_S3C6400_AC97
  218. /* AC97 DMA operation
  219. * Control AC97 global control register to set DMA operation
  220. * If the DMA transfer is endded you should turn off AC97 DMA
  221. * otherwise the noise will be heard. -JaeCheol Lee (2007.03.05)
  222. */
  223. static int audio_dma_operation(struct s3c2410_dma_chan *subchan, enum s3c2410_chan_op op)
  224. {
  225. switch (op) {
  226. case S3C2410_DMAOP_START:
  227. __raw_writel(__raw_readl(AC_GLBCTRL) | (0x2 << 12), AC_GLBCTRL);
  228. break;
  229. case S3C2410_DMAOP_STOP:
  230. __raw_writel(__raw_readl(AC_GLBCTRL) & ~(0x3 << 12), AC_GLBCTRL);
  231. break;
  232. default:
  233. break;
  234. }
  235. return 0;
  236. }
  237. #endif
  238. static int copy_to_user_stereo_mono(char *to, char *from, int count)
  239. {
  240. int ind, fact;
  241. if(!count)
  242. return 0;
  243. if(from[6] && from[7] && !from[5] && !from[4]) //check for the nonzero channel
  244. fact = 0;
  245. else
  246. fact = 1;
  247. ind = 0;
  248. while(ind < count){
  249. if(ind%2){
  250. *(from + ind) = *(from + 2*ind +1);
  251. *(from + ind) = *(from + 2*ind -1);
  252. }else{
  253. *(from + ind) = *(from + 2*ind +2);
  254. *(from + ind) = *(from + 2*ind -0);
  255. }
  256. ind++;
  257. }
  258. return copy_to_user(to, from, count);
  259. }
  260. static int copy_from_user_mono_stereo(char *to, const char *from, int count)
  261. {
  262. int ind;
  263. if(copy_from_user(to, from, count))
  264. return -EFAULT;
  265. ind = count - 1;
  266. while(ind){
  267. if(ind%2){
  268. *(to + 2*ind + 1) = *(to + ind);
  269. *(to + 2*ind - 1) = *(to + ind); // R;
  270. }else{
  271. *(to + 2*ind + 2) = *(to + ind);
  272. *(to + 2*ind + 0) = *(to + ind); // R;
  273. }
  274. ind--;
  275. }
  276. return 0;
  277. }
  278. /*
  279. * Buffer creation/destruction
  280. */
  281. static void audio_discard_buf(audio_stream_t * s)
  282. {
  283. DPRINTK("audio_discard_buf\n");
  284. /* ensure DMA isn't using those buffers */
  285. audio_reset(s);
  286. if (s->buffers) {
  287. int frag;
  288. for (frag = 0; frag < s->nbfrags; frag++) {
  289. if (!s->buffers[frag].master)
  290. continue;
  291. dma_free_coherent(s->dev,
  292. s->buffers[frag].master,
  293. s->buffers[frag].data, s->buffers[frag].dma_addr);
  294. }
  295. kfree(s->buffers);
  296. s->buffers = NULL;
  297. }
  298. }
  299. static int audio_setup_buf(audio_stream_t * s)
  300. {
  301. int frag;
  302. int dmasize = 0;
  303. char *dmabuf = NULL;
  304. dma_addr_t dmaphys = 0;
  305. if (s->buffers)
  306. return -EBUSY;
  307. s->buffers = kmalloc(sizeof(audio_buf_t) * s->nbfrags, GFP_KERNEL);
  308. if (!s->buffers)
  309. goto err;
  310. memset(s->buffers, 0, sizeof(audio_buf_t) * s->nbfrags);
  311. for (frag = 0; frag < s->nbfrags; frag++) {
  312. audio_buf_t *b = &s->buffers[frag];
  313. /*
  314. * Let's allocate non-cached memory for DMA buffers.
  315. * We try to allocate all memory at once.
  316. * If this fails (a common reason is memory fragmentation),
  317. * then we allocate more smaller buffers.
  318. */
  319. if (!dmasize) {
  320. dmasize = (s->nbfrags - frag) * s->fragsize;
  321. do {
  322. dmabuf = dma_alloc_coherent(s->dev, dmasize, &dmaphys, GFP_KERNEL);
  323. if (!dmabuf)
  324. dmasize -= s->fragsize;
  325. } while (!dmabuf && dmasize);
  326. if (!dmabuf)
  327. goto err;
  328. b->master = dmasize;
  329. memzero(dmabuf, dmasize);
  330. }
  331. b->data = dmabuf;
  332. b->dma_addr = dmaphys;
  333. DPRINTK("buf %d: start %p dma %#08x\n", frag, b->data, b->dma_addr);
  334. dmabuf += s->fragsize;
  335. dmaphys += s->fragsize;
  336. dmasize -= s->fragsize;
  337. }
  338. s->usr_head = s->dma_head = s->dma_tail = 0;
  339. s->bytecount = 0;
  340. s->fragcount = 0;
  341. sema_init(&s->sem, s->nbfrags);
  342. return 0;
  343. err:
  344. printk(AUDIO_NAME ": unable to allocate audio memory\n ");
  345. audio_discard_buf(s);
  346. return -ENOMEM;
  347. }
  348. /*
  349. * Driver interface functions
  350. */
  351. static int audio_write(struct file *file, const char *buffer, size_t count, loff_t * ppos)
  352. {
  353. const char *buffer0 = buffer;
  354. audio_state_t *state = file->private_data;
  355. audio_stream_t *s = state->output_stream;
  356. int chunksize, ret = 0;
  357. unsigned long flags;
  358. DPRINTK("audio_write: count=%d\n", count);
  359. if (s->mapped)
  360. return -ENXIO;
  361. if (!s->buffers && audio_setup_buf(s))
  362. return -ENOMEM;
  363. while (count > 0) {
  364. audio_buf_t *b = &s->buffers[s->usr_head];
  365. /* Wait for a buffer to become free */
  366. if (file->f_flags & O_NONBLOCK) {
  367. ret = -EAGAIN;
  368. if (down_trylock(&s->sem))
  369. break;
  370. } else {
  371. ret = -ERESTARTSYS;
  372. if (down_interruptible(&s->sem))
  373. break;
  374. }
  375. /* Feed the current buffer */
  376. if(state->sound_mode == MONO) {
  377. /* mono mode play back */
  378. if(count > s->fragsize/2)
  379. chunksize = s->fragsize/2;
  380. else
  381. chunksize = count;
  382. if (copy_from_user_mono_stereo(b->data + b->offset, buffer, chunksize)) {
  383. up(&s->sem);
  384. return -EFAULT;
  385. }
  386. b->offset += chunksize*2;
  387. } else {
  388. /* stereo mode play back */
  389. chunksize = s->fragsize - b->offset;
  390. if (chunksize > count)
  391. chunksize = count;
  392. DPRINTK("write %d to %d\n", chunksize, s->usr_head);
  393. if (copy_from_user(b->data + b->offset, buffer, chunksize)) {
  394. up(&s->sem);
  395. return -EFAULT;
  396. }
  397. b->offset += chunksize;
  398. }
  399. count -= chunksize;
  400. buffer += chunksize;
  401. if (b->offset < s->fragsize) {
  402. up(&s->sem);
  403. break;
  404. }
  405. /* Update pointers and send current fragment to DMA */
  406. b->offset = 0;
  407. if (++s->usr_head >= s->nbfrags)
  408. s->usr_head = 0;
  409. local_irq_save(flags);
  410. s->pending_frags++;
  411. s->active = 1;
  412. write_count++;
  413. audio_process_dma(s);
  414. local_irq_restore(flags);
  415. }
  416. if ((buffer - buffer0))
  417. ret = buffer - buffer0;
  418. DPRINTK("audio_write: return=%d\n", ret);
  419. return ret;
  420. }
  421. static void audio_prime_rx(audio_state_t *state)
  422. {
  423. audio_stream_t *is = state->input_stream;
  424. unsigned long flags;
  425. local_irq_save(flags);
  426. is->pending_frags = is->nbfrags;
  427. sema_init(&is->sem, 0);
  428. is->active = 1;
  429. audio_process_dma(is);
  430. local_irq_restore(flags);
  431. }
  432. static int audio_read(struct file *file, char *buffer, size_t count, loff_t * ppos)
  433. {
  434. char *buffer0 = buffer;
  435. audio_state_t *state = file->private_data;
  436. audio_stream_t *s = state->input_stream;
  437. int chunksize, ret = 0;
  438. unsigned long flags;
  439. DPRINTK("audio_read: count=%d\n", count);
  440. if (s->mapped)
  441. return -ENXIO;
  442. if (!s->active) {
  443. if (!s->buffers && audio_setup_buf(s))
  444. return -ENOMEM;
  445. audio_prime_rx(state);
  446. }
  447. while (count > 0) {
  448. audio_buf_t *b = &s->buffers[s->usr_head];
  449. /* Wait for a buffer to become full */
  450. if (file->f_flags & O_NONBLOCK) {
  451. ret = -EAGAIN;
  452. if (down_trylock(&s->sem))
  453. break;
  454. } else {
  455. ret = -ERESTARTSYS;
  456. if (down_interruptible(&s->sem))
  457. break;
  458. }
  459. /* Grab data from the current buffer */
  460. if(state->sound_mode == MONO) {
  461. chunksize = (s->fragsize - b->offset)/2;
  462. if(chunksize > count)
  463. chunksize = count/2;
  464. if(copy_to_user_stereo_mono(buffer, b->data + b->offset, chunksize)) {
  465. up(&s->sem);
  466. return -EFAULT;
  467. }
  468. b->offset += chunksize * 2;
  469. } else {
  470. /* stereo mode play back */
  471. chunksize = s->fragsize - b->offset;
  472. if (chunksize > count)
  473. chunksize = count;
  474. DPRINTK("read %d from %d\n", chunksize, s->usr_head);
  475. if (copy_to_user(buffer, b->data + b->offset, chunksize)) {
  476. up(&s->sem);
  477. return -EFAULT;
  478. }
  479. b->offset += chunksize;
  480. }
  481. buffer += chunksize;
  482. count -= chunksize;
  483. if (b->offset < s->fragsize) {
  484. up(&s->sem);
  485. break;
  486. }
  487. /* Update pointers and return current fragment to DMA */
  488. b->offset = 0;
  489. if (++s->usr_head >= s->nbfrags)
  490. s->usr_head = 0;
  491. local_irq_save(flags);
  492. s->pending_frags++;
  493. audio_process_dma(s);
  494. local_irq_restore(flags);
  495. }
  496. if ((buffer - buffer0))
  497. ret = buffer - buffer0;
  498. DPRINTK("audio_read: return=%d\n", ret);
  499. return ret;
  500. }
  501. static int audio_sync(struct file *file)
  502. {
  503. audio_state_t *state = file->private_data;
  504. audio_stream_t *s = state->output_stream;
  505. audio_buf_t *b;
  506. u_int shiftval = 0;
  507. unsigned long flags;
  508. DECLARE_WAITQUEUE(wait, current);
  509. DPRINTK("audio_sync\n");
  510. if (!(file->f_mode & FMODE_WRITE) || !s->buffers || s->mapped)
  511. return 0;
  512. /*
  513. * Send current buffer if it contains data. Be sure to send
  514. * a full sample count.
  515. */
  516. b = &s->buffers[s->usr_head];
  517. if (b->offset &= ~3) {
  518. down(&s->sem);
  519. /*
  520. * HACK ALERT !
  521. * To avoid increased complexity in the rest of the code
  522. * where full fragment sizes are assumed, we cheat a little
  523. * with the start pointer here and don't forget to restore
  524. * it later.
  525. */
  526. shiftval = s->fragsize - b->offset;
  527. b->offset = shiftval;
  528. b->dma_addr -= shiftval;
  529. s->bytecount -= shiftval;
  530. if (++s->usr_head >= s->nbfrags)
  531. s->usr_head = 0;
  532. local_irq_save(flags);
  533. s->pending_frags++;
  534. audio_process_dma(s);
  535. local_irq_restore(flags);
  536. }
  537. /* Let's wait for all buffers to complete */
  538. set_current_state(TASK_INTERRUPTIBLE);
  539. add_wait_queue(&s->wq, &wait);
  540. while (s->pending_frags && s->dma_tail != s->usr_head && !signal_pending(current)) {
  541. schedule();
  542. set_current_state(TASK_INTERRUPTIBLE);
  543. }
  544. set_current_state(TASK_RUNNING);
  545. remove_wait_queue(&s->wq, &wait);
  546. /* undo the pointer hack above */
  547. if (shiftval) {
  548. local_irq_save(flags);
  549. b->dma_addr += shiftval;
  550. /* ensure sane DMA code behavior if not yet processed */
  551. if (b->offset != 0)
  552. b->offset = s->fragsize;
  553. local_irq_restore(flags);
  554. }
  555. return 0;
  556. }
  557. static int audio_mmap(struct file *file, struct vm_area_struct *vma)
  558. {
  559. audio_state_t *state = file->private_data;
  560. audio_stream_t *s;
  561. unsigned long size, vma_addr;
  562. int i, ret;
  563. if (vma->vm_pgoff != 0)
  564. return -EINVAL;
  565. if (vma->vm_flags & VM_WRITE) {
  566. if (!state->wr_ref)
  567. return -EINVAL;;
  568. s = state->output_stream;
  569. } else if (vma->vm_flags & VM_READ) {
  570. if (!state->rd_ref)
  571. return -EINVAL;
  572. s = state->input_stream;
  573. } else
  574. return -EINVAL;
  575. if (s->mapped)
  576. return -EINVAL;
  577. size = vma->vm_end - vma->vm_start;
  578. if (size != s->fragsize * s->nbfrags)
  579. return -EINVAL;
  580. if (!s->buffers && audio_setup_buf(s))
  581. return -ENOMEM;
  582. vma_addr = vma->vm_start;
  583. for (i = 0; i < s->nbfrags; i++) {
  584. audio_buf_t *buf = &s->buffers[i];
  585. if (!buf->master)
  586. continue;
  587. ret = remap_pfn_range(vma, vma_addr, buf->dma_addr, buf->master, vma->vm_page_prot);
  588. if (ret)
  589. return ret;
  590. vma_addr += buf->master;
  591. }
  592. s->mapped = 1;
  593. return 0;
  594. }
  595. static unsigned int audio_poll(struct file *file, struct poll_table_struct *wait)
  596. {
  597. audio_state_t *state = file->private_data;
  598. audio_stream_t *is = state->input_stream;
  599. audio_stream_t *os = state->output_stream;
  600. unsigned int mask = 0;
  601. DPRINTK("audio_poll(): mode=%s%s\n",
  602. (file->f_mode & FMODE_READ) ? "r" : "", (file->f_mode & FMODE_WRITE) ? "w" : "");
  603. if (file->f_mode & FMODE_READ) {
  604. /* Start audio input if not already active */
  605. if (!is->active) {
  606. if (!is->buffers && audio_setup_buf(is))
  607. return -ENOMEM;
  608. audio_prime_rx(state);
  609. }
  610. poll_wait(file, &is->wq, wait);
  611. }
  612. if (file->f_mode & FMODE_WRITE) {
  613. if (!os->buffers && audio_setup_buf(os))
  614. return -ENOMEM;
  615. poll_wait(file, &os->wq, wait);
  616. }
  617. if (file->f_mode & FMODE_READ)
  618. if (( is->mapped && is->bytecount > 0))
  619. mask |= POLLIN | POLLRDNORM;
  620. if (file->f_mode & FMODE_WRITE)
  621. if (( os->mapped && os->bytecount > 0))
  622. mask |= POLLOUT | POLLWRNORM;
  623. DPRINTK("audio_poll() returned mask of %s%s\n",
  624. (mask & POLLIN) ? "r" : "", (mask & POLLOUT) ? "w" : "");
  625. return mask;
  626. }
  627. static loff_t audio_llseek(struct file *file, loff_t offset, int origin)
  628. {
  629. return -ESPIPE;
  630. }
  631. static int audio_set_fragments(audio_stream_t *s, int val)
  632. {
  633. if (s->active)
  634. return -EBUSY;
  635. if (s->buffers)
  636. audio_discard_buf(s);
  637. s->nbfrags = (val >> 16) & 0x7FFF;
  638. val &= 0xffff;
  639. if (val < 4)
  640. val = 4;
  641. if (val > 13)
  642. val = 13;
  643. s->fragsize = 1 << val;
  644. if (s->nbfrags < 2)
  645. s->nbfrags = 2;
  646. if (s->nbfrags * s->fragsize > 128 * 1024)
  647. s->nbfrags = 128 * 1024 / s->fragsize;
  648. if (audio_setup_buf(s))
  649. return -ENOMEM;
  650. return val|(s->nbfrags << 16);
  651. }
  652. static int audio_ioctl(struct inode *inode, struct file *file, uint cmd, ulong arg)
  653. {
  654. audio_state_t *state = file->private_data;
  655. audio_stream_t *os = state->output_stream;
  656. audio_stream_t *is = state->input_stream;
  657. audio_buf_info inf = { 0, };
  658. long val;
  659. /* dispatch based on command */
  660. switch (cmd) {
  661. case OSS_GETVERSION:
  662. return put_user(SOUND_VERSION, (int *)arg);
  663. case SNDCTL_DSP_GETBLKSIZE:
  664. if (file->f_mode & FMODE_WRITE)
  665. return put_user(os->fragsize, (int *)arg);
  666. else
  667. return put_user(is->fragsize, (int *)arg);
  668. case SNDCTL_DSP_GETCAPS:
  669. val = DSP_CAP_REALTIME|DSP_CAP_TRIGGER|DSP_CAP_MMAP;
  670. if (is && os)
  671. val |= DSP_CAP_DUPLEX;
  672. return put_user(val, (int *)arg);
  673. case SNDCTL_DSP_SETFRAGMENT:
  674. if (get_user(val, (long *) arg))
  675. return -EFAULT;
  676. if (file->f_mode & FMODE_READ) {
  677. int ret = audio_set_fragments(is, val);
  678. if (ret < 0)
  679. return ret;
  680. ret = put_user(ret, (int *)arg);
  681. if (ret)
  682. return ret;
  683. }
  684. if (file->f_mode & FMODE_WRITE) {
  685. int ret = audio_set_fragments(os, val);
  686. if (ret < 0)
  687. return ret;
  688. ret = put_user(ret, (int *)arg);
  689. if (ret)
  690. return ret;
  691. }
  692. return 0;
  693. case SNDCTL_DSP_SYNC:
  694. return audio_sync(file);
  695. case SNDCTL_DSP_SETDUPLEX:
  696. return 0;
  697. case SNDCTL_DSP_POST:
  698. return 0;
  699. case SNDCTL_DSP_GETTRIGGER:
  700. val = 0;
  701. if (file->f_mode & FMODE_READ && is->active && !is->stopped)
  702. val |= PCM_ENABLE_INPUT;
  703. if (file->f_mode & FMODE_WRITE && os->active && !os->stopped)
  704. val |= PCM_ENABLE_OUTPUT;
  705. return put_user(val, (int *)arg);
  706. case SNDCTL_DSP_SETTRIGGER:
  707. if (get_user(val, (int *)arg))
  708. return -EFAULT;
  709. if (file->f_mode & FMODE_READ) {
  710. if (val & PCM_ENABLE_INPUT) {
  711. unsigned long flags;
  712. if (!is->active) {
  713. if (!is->buffers && audio_setup_buf(is))
  714. return -ENOMEM;
  715. audio_prime_rx(state);
  716. }
  717. local_irq_save(flags);
  718. is->stopped = 0;
  719. audio_process_dma(is);
  720. local_irq_restore(flags);
  721. } else {
  722. audio_stop_dma(is);
  723. }
  724. }
  725. if (file->f_mode & FMODE_WRITE) {
  726. if (val & PCM_ENABLE_OUTPUT) {
  727. unsigned long flags;
  728. if (!os->buffers && audio_setup_buf(os))
  729. return -ENOMEM;
  730. local_irq_save(flags);
  731. if (os->mapped && !os->pending_frags) {
  732. os->pending_frags = os->nbfrags;
  733. sema_init(&os->sem, 0);
  734. os->active = 1;
  735. }
  736. os->stopped = 0;
  737. audio_process_dma(os);
  738. local_irq_restore(flags);
  739. } else {
  740. audio_stop_dma(os);
  741. }
  742. }
  743. return 0;
  744. case SNDCTL_DSP_GETOPTR:
  745. case SNDCTL_DSP_GETIPTR:
  746. {
  747. count_info inf = { 0, };
  748. audio_stream_t *s = (cmd == SNDCTL_DSP_GETOPTR) ? os : is;
  749. int bytecount, offset;
  750. unsigned long flags;
  751. if ((s == is && !(file->f_mode & FMODE_READ)) ||
  752. (s == os && !(file->f_mode & FMODE_WRITE)))
  753. return -EINVAL;
  754. if (s->active) {
  755. local_irq_save(flags);
  756. offset = audio_get_dma_pos(s);
  757. inf.ptr = s->dma_tail * s->fragsize + offset;
  758. bytecount = s->bytecount + offset;
  759. s->bytecount = -offset;
  760. inf.blocks = s->fragcount;
  761. s->fragcount = 0;
  762. local_irq_restore(flags);
  763. if (bytecount < 0)
  764. bytecount = 0;
  765. inf.bytes = bytecount;
  766. }
  767. return copy_to_user((void *)arg, &inf, sizeof(inf));
  768. }
  769. case SNDCTL_DSP_GETOSPACE:
  770. {
  771. audio_stream_t *s = os;
  772. if (!(file->f_mode & FMODE_WRITE))
  773. return -EINVAL;
  774. if (!s->buffers && audio_setup_buf(s))
  775. return -ENOMEM;
  776. inf.bytes = s->fragsize * s->free_bufnum;
  777. inf.fragments = s->free_bufnum;
  778. inf.fragsize = s->fragsize;
  779. inf.fragstotal = s->nbfrags;
  780. return copy_to_user((void *) arg, &inf, sizeof(inf));
  781. }
  782. case SNDCTL_DSP_GETISPACE:
  783. {
  784. audio_stream_t *s = is;
  785. if (!(file->f_mode & FMODE_READ))
  786. return -EINVAL;
  787. if (!s->buffers && audio_setup_buf(s))
  788. return -ENOMEM;
  789. inf.bytes = s->fragsize * s->free_bufnum;
  790. inf.fragments = s->free_bufnum;
  791. inf.fragsize = s->fragsize;
  792. inf.fragstotal = s->nbfrags;
  793. return copy_to_user((void *) arg, &inf, sizeof(inf));
  794. }
  795. case SNDCTL_DSP_NONBLOCK:
  796. file->f_flags |= O_NONBLOCK;
  797. return 0;
  798. case SNDCTL_DSP_RESET:
  799. if (file->f_mode & FMODE_READ) {
  800. audio_reset(is);
  801. }
  802. if (file->f_mode & FMODE_WRITE) {
  803. audio_reset(os);
  804. }
  805. return 0;
  806. default:
  807. /*
  808. * Let the client of this module handle the
  809. * non generic ioctls
  810. */
  811. return state->client_ioctl(inode, file, cmd, arg);
  812. }
  813. return 0;
  814. }
  815. static int audio_release(struct inode *inode, struct file *file)
  816. {
  817. #ifdef CONFIG_SOUND_S3C6400_AC97
  818. int i;
  819. #endif
  820. audio_state_t *state = file->private_data;
  821. audio_stream_t *os = state->output_stream;
  822. audio_stream_t *is = state->input_stream;
  823. DPRINTK("audio_release\n");
  824. down(&state->sem);
  825. if (file->f_mode & FMODE_READ) {
  826. audio_discard_buf(is);
  827. #if defined (CONFIG_AC97_MIC_PATH) || defined (CONFIG_SOUND_S3C6400_I2S)
  828. s3c2410_dma_free(is->subchannel, &s3cmic_dma_client);
  829. #else
  830. s3c2410_dma_free(is->subchannel, &s3cline_dma_client);
  831. #endif
  832. state->rd_ref = 0;
  833. }
  834. if (file->f_mode & FMODE_WRITE) {
  835. audio_sync(file);
  836. audio_discard_buf(os);
  837. s3c2410_dma_free( os->subchannel, &s3cplay_dma_client);
  838. state->wr_ref = 0;
  839. }
  840. if (!AUDIO_ACTIVE(state)) {
  841. if (state->hw_shutdown)
  842. state->hw_shutdown(state->data);
  843. }
  844. #ifdef CONFIG_SOUND_S3C6400_AC97
  845. for (i = 0; i < 64; i++)
  846. writel(0, AC_PCMDATA);
  847. #endif
  848. up(&state->sem);
  849. return 0;
  850. }
  851. #ifdef CONFIG_PM
  852. int s3c64xx_audio_suspend(audio_state_t * s, u32 state, u32 level)
  853. {
  854. #ifdef CONFIG_SOUND_S3C6400_I2S
  855. if (level == SUSPEND_DISABLE || level == SUSPEND_POWER_DOWN) {
  856. audio_stream_t *is = s->input_stream;
  857. audio_stream_t *os = s->output_stream;
  858. int stopstate;
  859. if (is) {
  860. stopstate = is->stopped;
  861. audio_stop_dma(is);
  862. s3c_dma_ctrl(is->dma, is->subchannel, S3C_DMAOP_FLUSH);
  863. is->stopped = stopstate;
  864. }
  865. if (os) {
  866. stopstate = os->stopped;
  867. audio_stop_dma(os);
  868. s3c_dma_ctrl(os->dma, os->subchannel, S3C_DMAOP_FLUSH);
  869. os->stopped = stopstate;
  870. }
  871. if (AUDIO_ACTIVE(s) && s->hw_shutdown)
  872. s->hw_shutdown(s->data);
  873. }
  874. #endif
  875. #ifdef CONFIG_SOUND_S3C6400_AC97
  876. s3c64xx_ac97_suspend();
  877. #endif
  878. return 0;
  879. }
  880. int s3c64xx_audio_resume(audio_state_t * s, u32 level)
  881. {
  882. printk("%s\n", __FUNCTION__);
  883. #if 0
  884. if (level == RESUME_ENABLE) {
  885. audio_stream_t *is = s->input_stream;
  886. audio_stream_t *os = s->output_stream;
  887. if (AUDIO_ACTIVE(s) && s->hw_init)
  888. s->hw_init(s->data);
  889. if (os && os->dma_regs) {
  890. //DMA_RESET(os);
  891. audio_process_dma(os);
  892. }
  893. if (is && is->dma_regs) {
  894. //DMA_RESET(is);
  895. audio_process_dma(is);
  896. }
  897. }
  898. #endif
  899. #ifdef CONFIG_SOUND_S3C6400_AC97
  900. s3c64xx_ac97_resume();
  901. #endif
  902. return 0;
  903. }
  904. EXPORT_SYMBOL(s3c64xx_audio_suspend);
  905. EXPORT_SYMBOL(s3c64xx_audio_resume);
  906. #else
  907. #define s3c64xx_audio_suspend() NULL
  908. #define s3c64xx_audio_resume() NULL
  909. #endif
  910. /* structure file_operations changed to const.
  911. */
  912. static const struct file_operations s3c_f_ops =
  913. {
  914. .release = audio_release,
  915. .write = audio_write,
  916. .read = audio_read,
  917. .mmap = audio_mmap,
  918. .poll = audio_poll,
  919. .ioctl = audio_ioctl,
  920. .llseek = audio_llseek
  921. };
  922. #ifdef CONFIG_SOUND_S3C6400_AC97
  923. extern void codec_reset_settings(int mode);
  924. int s3c_audio_attach(struct inode *inode, struct file *file, audio_state_t * state)
  925. {
  926. audio_stream_t *os = state->output_stream;
  927. audio_stream_t *is_line = state->input_stream_line;
  928. audio_stream_t *is_mic = state->input_stream_mic;
  929. int err, need_tx_dma = 0;
  930. /*make mic default rec source*/
  931. state->input_stream = state->input_stream_line;
  932. DPRINTK("audio_open\n");
  933. down(&state->sem);
  934. /* access control */
  935. err = -ENODEV;
  936. if ((file->f_mode & FMODE_WRITE) && !os)
  937. goto out;
  938. if ((file->f_mode & FMODE_READ) && !is_mic)
  939. goto out;
  940. err = -EBUSY;
  941. if ((file->f_mode & FMODE_WRITE) && state->wr_ref)
  942. goto out;
  943. if ((file->f_mode & FMODE_READ) && state->rd_ref)
  944. goto out;
  945. err = -EINVAL;
  946. if ((file->f_mode & FMODE_READ) && state->need_tx_for_rx && !os)
  947. goto out;
  948. if(file->f_mode & FMODE_READ)
  949. file->f_mode = FMODE_READ;
  950. /* request DMA channels */
  951. if (file->f_mode & FMODE_WRITE) {
  952. if (s3c2410_dma_request(os->subchannel, &s3cplay_dma_client, NULL)) {
  953. printk(KERN_WARNING "unable to get DMA channel.\n");
  954. err = -EBUSY;
  955. goto out;
  956. }
  957. need_tx_dma = 1; //we claimed the play channel
  958. err = s3c_ac97_dma_init(os, 0);
  959. }
  960. if (file->f_mode & FMODE_READ) {
  961. #ifdef CONFIG_AC97_MIC_PATH
  962. if (s3c2410_dma_request(is_mic->subchannel, &s3cmic_dma_client, NULL)) {
  963. printk(KERN_WARNING "unable to get %d DMA %d channel.\n", is_mic->dma,
  964. is_mic->subchannel);
  965. err = -EBUSY;
  966. if (need_tx_dma)
  967. s3c2410_dma_free(os->subchannel, &s3cplay_dma_client);
  968. s3c2410_dma_free(is_mic->subchannel, &s3cmic_dma_client);
  969. goto out;
  970. }
  971. if (s3c_ac97_dma_init(is_mic, 2))
  972. goto out;
  973. #else
  974. if (s3c2410_dma_request(is_line->subchannel, &s3cline_dma_client, NULL)) {
  975. printk(KERN_WARNING "unable to get %d DMA %d channel.\n", is_line->dma,
  976. is_line->subchannel);
  977. err = -EBUSY;
  978. if (need_tx_dma)
  979. s3c2410_dma_free(os->subchannel, &s3cplay_dma_client);
  980. s3c2410_dma_free(is_line->subchannel, &s3cline_dma_client);
  981. goto out;
  982. }
  983. if (s3c_ac97_dma_init(is_line, 1))
  984. goto out;
  985. #endif
  986. }
  987. /* now complete initialisation */
  988. if (!AUDIO_ACTIVE(state)) {
  989. if (state->hw_init)
  990. state->hw_init(state->data);
  991. }
  992. if ((file->f_mode & FMODE_WRITE)) {
  993. state->wr_ref = 1;
  994. audio_reset(os);
  995. os->fragsize = AUDIO_FRAGSIZE_DEFAULT;
  996. os->nbfrags = AUDIO_NBFRAGS_DEFAULT;
  997. os->free_bufnum = AUDIO_NBFRAGS_DEFAULT;
  998. os->mapped = 0;
  999. init_waitqueue_head(&os->wq);
  1000. codec_reset_settings(MODE_PLAY);
  1001. }
  1002. /*only mic or line in will be used at a time ..this can be modified*/
  1003. if (file->f_mode & FMODE_READ) {
  1004. state->rd_ref = 1;
  1005. #ifdef CONFIG_AC97_MIC_PATH
  1006. audio_reset(is_mic);
  1007. #else
  1008. audio_reset(is_line);
  1009. #endif
  1010. is_line->fragsize = is_mic->fragsize = AUDIO_FRAGSIZE_DEFAULT;
  1011. is_line->nbfrags = is_mic->nbfrags = AUDIO_NBFRAGS_DEFAULT;
  1012. is_line->free_bufnum = is_mic->free_bufnum = AUDIO_NBFRAGS_DEFAULT;
  1013. is_line->mapped = is_mic->mapped = 0;
  1014. #ifdef CONFIG_AC97_MIC_PATH
  1015. init_waitqueue_head(&is_mic->wq);
  1016. #else
  1017. init_waitqueue_head(&is_line->wq);
  1018. #endif
  1019. codec_reset_settings(MODE_REC);
  1020. }
  1021. file->private_data = state;
  1022. file->f_op = &s3c_f_ops;
  1023. err = 0;
  1024. out:
  1025. up(&state->sem);
  1026. return err;
  1027. }
  1028. #endif
  1029. #ifdef CONFIG_SOUND_S3C6400_I2S
  1030. int s3c_audio_attach(struct inode *inode, struct file *file,
  1031. audio_state_t *state)
  1032. {
  1033. audio_stream_t *os = state->output_stream;
  1034. audio_stream_t *is = state->input_stream;
  1035. int err, need_tx_dma=0;
  1036. DPRINTK("audio_open\n");
  1037. down(&state->sem);
  1038. /* access control */
  1039. err = -ENODEV;
  1040. if ((file->f_mode & FMODE_WRITE) && !os)
  1041. goto out;
  1042. if ((file->f_mode & FMODE_READ) && !is)
  1043. goto out;
  1044. err = -EBUSY;
  1045. if ((file->f_mode & FMODE_WRITE) && state->wr_ref)
  1046. goto out;
  1047. if ((file->f_mode & FMODE_READ) && state->rd_ref)
  1048. goto out;
  1049. err = -EINVAL;
  1050. if ((file->f_mode & FMODE_READ) && state->need_tx_for_rx && !os)
  1051. goto out;
  1052. if(file->f_mode & FMODE_READ)
  1053. file->f_mode = FMODE_READ;
  1054. DPRINTK("%s, f_mode = 0x%x\n", __FUNCTION__, file->f_mode);
  1055. /* request DMA channels */
  1056. if (file->f_mode & FMODE_WRITE) {
  1057. if(s3c2410_dma_request(os->subchannel, &s3cplay_dma_client, NULL)) {
  1058. printk(KERN_WARNING "unable to get DMA channel.\n" );
  1059. err = -EBUSY;
  1060. goto out;
  1061. }
  1062. need_tx_dma = 1;
  1063. err = s3c_iis_dma_init(os,0);
  1064. if(err)
  1065. goto out;
  1066. err = wm8753_set_hpout_path();
  1067. if(err)
  1068. goto out;
  1069. }
  1070. if (file->f_mode & FMODE_READ) {
  1071. if(s3c2410_dma_request(is->subchannel, &s3cmic_dma_client, NULL)) {
  1072. printk(KERN_WARNING "unable to get DMA channel.\n" );
  1073. err = -EBUSY;
  1074. if (need_tx_dma)
  1075. s3c2410_dma_free(os->subchannel, &s3cplay_dma_client);
  1076. goto out;
  1077. }
  1078. err = s3c_iis_dma_init(is,1);
  1079. if(err)
  1080. goto out;
  1081. #ifdef CONFIG_MIC_PATH
  1082. err = wm8753_set_mic1_path();
  1083. #else
  1084. err = wm8753_set_linein_path();
  1085. #endif
  1086. if(err)
  1087. goto out;
  1088. }
  1089. if ((file->f_mode & FMODE_WRITE)) {
  1090. state->wr_ref = 1;
  1091. audio_reset(os);
  1092. os->fragsize = AUDIO_FRAGSIZE_DEFAULT;
  1093. os->nbfrags = AUDIO_NBFRAGS_DEFAULT;
  1094. os->free_bufnum = AUDIO_NBFRAGS_DEFAULT;
  1095. os->mapped = 0;
  1096. init_waitqueue_head(&os->wq);
  1097. }
  1098. if (file->f_mode & FMODE_READ) {
  1099. state->rd_ref = 1;
  1100. audio_reset(is);
  1101. is->fragsize = AUDIO_FRAGSIZE_DEFAULT;
  1102. is->nbfrags = AUDIO_NBFRAGS_DEFAULT;
  1103. is->free_bufnum = AUDIO_NBFRAGS_DEFAULT;
  1104. is->mapped = 0;
  1105. init_waitqueue_head(&is->wq);
  1106. }
  1107. file->private_data = state;
  1108. file->f_op = &s3c_f_ops;
  1109. err = 0;
  1110. out:
  1111. up(&state->sem);
  1112. return err;
  1113. }
  1114. #endif
  1115. EXPORT_SYMBOL(s3c_audio_attach);
  1116. MODULE_AUTHOR("Ryu Euiyoul");
  1117. MODULE_DESCRIPTION("Common audio handling for the Samsung AP");
  1118. MODULE_LICENSE("GPL");