blob: 464f66e93e91da822f190d36a6e4e8baae3d86c5 [file] [log] [blame]
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001/* Copyright (c) 2009-2011, Code Aurora Forum. All rights reserved.
2 *
3 * Based on the mp3 native driver in arch/arm/mach-msm/qdsp5v2/audio_mp3.c
4 *
5 * Copyright (C) 2008 Google, Inc.
6 * Copyright (C) 2008 HTC Corporation
7 *
8 * All source code in this file is licensed under the following license except
9 * where indicated.
10 *
11 * This program is free software; you can redistribute it and/or modify it
12 * under the terms of the GNU General Public License version 2 as published
13 * by the Free Software Foundation.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
18 *
19 * See the GNU General Public License for more details.
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, you can find it at http://www.fsf.org
22 */
23
Santosh Mardifdc227a2011-07-11 17:20:34 +053024#include <asm/atomic.h>
25#include <asm/ioctls.h>
26
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070027#include <linux/module.h>
28#include <linux/fs.h>
29#include <linux/miscdevice.h>
30#include <linux/uaccess.h>
31#include <linux/kthread.h>
32#include <linux/wait.h>
33#include <linux/dma-mapping.h>
34#include <linux/debugfs.h>
35#include <linux/delay.h>
36#include <linux/list.h>
37#include <linux/earlysuspend.h>
38#include <linux/android_pmem.h>
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070039#include <linux/slab.h>
40#include <linux/msm_audio.h>
Santosh Mardifdc227a2011-07-11 17:20:34 +053041#include <linux/msm_audio_wma.h>
42#include <linux/memory_alloc.h>
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070043#include <mach/qdsp5v2/audio_dev_ctl.h>
44
Santosh Mardifdc227a2011-07-11 17:20:34 +053045#include <mach/msm_adsp.h>
46#include <mach/iommu.h>
47#include <mach/iommu_domains.h>
48#include <mach/msm_subsystem_map.h>
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070049#include <mach/qdsp5v2/qdsp5audppmsg.h>
50#include <mach/qdsp5v2/qdsp5audplaycmdi.h>
51#include <mach/qdsp5v2/qdsp5audplaymsg.h>
52#include <mach/qdsp5v2/audio_dev_ctl.h>
53#include <mach/qdsp5v2/audpp.h>
54#include <mach/debug_mm.h>
Santosh Mardifdc227a2011-07-11 17:20:34 +053055#include <mach/msm_memtypes.h>
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070056
57/* Size must be power of 2 */
58#define BUFSZ_MAX 4110 /* Includes meta in size */
59#define BUFSZ_MIN 1038 /* Includes meta in size */
60#define DMASZ_MAX (BUFSZ_MAX * 2)
61#define DMASZ_MIN (BUFSZ_MIN * 2)
62
63#define AUDPLAY_INVALID_READ_PTR_OFFSET 0xFFFF
64#define AUDDEC_DEC_WMA 4
65
66#define PCM_BUFSZ_MIN 8216 /* Hold one stereo WMA frame and meta out*/
67#define PCM_BUF_MAX_COUNT 5 /* DSP only accepts 5 buffers at most
68 but support 2 buffers currently */
69#define ROUTING_MODE_FTRT 1
70#define ROUTING_MODE_RT 2
71/* Decoder status received from AUDPPTASK */
72#define AUDPP_DEC_STATUS_SLEEP 0
73#define AUDPP_DEC_STATUS_INIT 1
74#define AUDPP_DEC_STATUS_CFG 2
75#define AUDPP_DEC_STATUS_PLAY 3
76
77#define AUDWMA_METAFIELD_MASK 0xFFFF0000
78#define AUDWMA_EOS_FLG_OFFSET 0x0A /* Offset from beginning of buffer */
79#define AUDWMA_EOS_FLG_MASK 0x01
80#define AUDWMA_EOS_NONE 0x0 /* No EOS detected */
81#define AUDWMA_EOS_SET 0x1 /* EOS set in meta field */
82
83#define AUDWMA_EVENT_NUM 10 /* Default number of pre-allocated event packets */
84
85struct buffer {
86 void *data;
87 unsigned size;
88 unsigned used; /* Input usage actual DSP produced PCM size */
89 unsigned addr;
90 unsigned short mfield_sz; /*only useful for data has meta field */
91};
92
93#ifdef CONFIG_HAS_EARLYSUSPEND
94struct audwma_suspend_ctl {
95 struct early_suspend node;
96 struct audio *audio;
97};
98#endif
99
100struct audwma_event{
101 struct list_head list;
102 int event_type;
103 union msm_audio_event_payload payload;
104};
105
106struct audio {
107 struct buffer out[2];
108
109 spinlock_t dsp_lock;
110
111 uint8_t out_head;
112 uint8_t out_tail;
113 uint8_t out_needed; /* number of buffers the dsp is waiting for */
114 unsigned out_dma_sz;
115
116 atomic_t out_bytes;
117
118 struct mutex lock;
119 struct mutex write_lock;
120 wait_queue_head_t write_wait;
121
122 /* Host PCM section */
123 struct buffer in[PCM_BUF_MAX_COUNT];
124 struct mutex read_lock;
125 wait_queue_head_t read_wait; /* Wait queue for read */
126 char *read_data; /* pointer to reader buffer */
127 int32_t read_phys; /* physical address of reader buffer */
128 uint8_t read_next; /* index to input buffers to be read next */
129 uint8_t fill_next; /* index to buffer that DSP should be filling */
130 uint8_t pcm_buf_count; /* number of pcm buffer allocated */
131 /* ---- End of Host PCM section */
132
133 struct msm_adsp_module *audplay;
134
135 /* configuration to use on next enable */
136 uint32_t out_sample_rate;
137 uint32_t out_channel_mode;
138
139 struct msm_audio_wma_config wma_config;
140
141 /* data allocated for various buffers */
142 char *data;
143 int32_t phys; /* physical address of write buffer */
Santosh Mardifdc227a2011-07-11 17:20:34 +0530144 struct msm_mapped_buffer *map_v_read;
145 struct msm_mapped_buffer *map_v_write;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700146
147 int mfield; /* meta field embedded in data */
148 int rflush; /* Read flush */
149 int wflush; /* Write flush */
150 int opened;
151 int enabled;
152 int running;
153 int stopped; /* set when stopped, cleared on flush */
154 int pcm_feedback;
155 int buf_refresh;
156 int teos; /* valid only if tunnel mode & no data left for decoder */
157 enum msm_aud_decoder_state dec_state; /* Represents decoder state */
158 int reserved; /* A byte is being reserved */
159 char rsv_byte; /* Handle odd length user data */
160
161 const char *module_name;
162 unsigned queue_id;
163 uint16_t dec_id;
164 uint32_t read_ptr_offset;
165 int16_t source;
166
167#ifdef CONFIG_HAS_EARLYSUSPEND
168 struct audwma_suspend_ctl suspend_ctl;
169#endif
170
171#ifdef CONFIG_DEBUG_FS
172 struct dentry *dentry;
173#endif
174
175 wait_queue_head_t wait;
176 struct list_head free_event_queue;
177 struct list_head event_queue;
178 wait_queue_head_t event_wait;
179 spinlock_t event_queue_lock;
180 struct mutex get_event_lock;
181 int event_abort;
182 /* AV sync Info */
183 int avsync_flag; /* Flag to indicate feedback from DSP */
184 wait_queue_head_t avsync_wait;/* Wait queue for AV Sync Message */
185 /* flags, 48 bits sample/bytes counter per channel */
186 uint16_t avsync[AUDPP_AVSYNC_CH_COUNT * AUDPP_AVSYNC_NUM_WORDS + 1];
187
188 uint32_t device_events;
189
190 int eq_enable;
191 int eq_needs_commit;
192 struct audpp_cmd_cfg_object_params_eqalizer eq;
193 struct audpp_cmd_cfg_object_params_volume vol_pan;
194};
195
196static int auddec_dsp_config(struct audio *audio, int enable);
197static void audpp_cmd_cfg_adec_params(struct audio *audio);
198static void audpp_cmd_cfg_routing_mode(struct audio *audio);
199static void audplay_send_data(struct audio *audio, unsigned needed);
200static void audplay_config_hostpcm(struct audio *audio);
201static void audplay_buffer_refresh(struct audio *audio);
202static void audio_dsp_event(void *private, unsigned id, uint16_t *msg);
203static void audwma_post_event(struct audio *audio, int type,
204 union msm_audio_event_payload payload);
205
206/* must be called with audio->lock held */
207static int audio_enable(struct audio *audio)
208{
209 MM_DBG("\n"); /* Macro prints the file name and function */
210 if (audio->enabled)
211 return 0;
212
213 audio->dec_state = MSM_AUD_DECODER_STATE_NONE;
214 audio->out_tail = 0;
215 audio->out_needed = 0;
216
217 if (msm_adsp_enable(audio->audplay)) {
218 MM_ERR("msm_adsp_enable(audplay) failed\n");
219 return -ENODEV;
220 }
221
222 if (audpp_enable(audio->dec_id, audio_dsp_event, audio)) {
223 MM_ERR("audpp_enable() failed\n");
224 msm_adsp_disable(audio->audplay);
225 return -ENODEV;
226 }
227
228 audio->enabled = 1;
229 return 0;
230}
231
232static void wma_listner(u32 evt_id, union auddev_evt_data *evt_payload,
233 void *private_data)
234{
235 struct audio *audio = (struct audio *) private_data;
236 switch (evt_id) {
237 case AUDDEV_EVT_DEV_RDY:
238 MM_DBG(":AUDDEV_EVT_DEV_RDY\n");
239 audio->source |= (0x1 << evt_payload->routing_id);
240 if (audio->running == 1 && audio->enabled == 1)
241 audpp_route_stream(audio->dec_id, audio->source);
242 break;
243 case AUDDEV_EVT_DEV_RLS:
244 MM_DBG(":AUDDEV_EVT_DEV_RLS\n");
245 audio->source &= ~(0x1 << evt_payload->routing_id);
246 if (audio->running == 1 && audio->enabled == 1)
247 audpp_route_stream(audio->dec_id, audio->source);
248 break;
249 case AUDDEV_EVT_STREAM_VOL_CHG:
250 audio->vol_pan.volume = evt_payload->session_vol;
251 MM_DBG(":AUDDEV_EVT_STREAM_VOL_CHG, stream vol %d\n",
252 audio->vol_pan.volume);
253 if (audio->running)
254 audpp_dsp_set_vol_pan(audio->dec_id, &audio->vol_pan,
255 POPP);
256 break;
257 default:
258 MM_ERR(":ERROR:wrong event\n");
259 break;
260 }
261}
262/* must be called with audio->lock held */
263static int audio_disable(struct audio *audio)
264{
265 int rc = 0;
266 MM_DBG("\n"); /* Macro prints the file name and function */
267 if (audio->enabled) {
268 audio->enabled = 0;
269 audio->dec_state = MSM_AUD_DECODER_STATE_NONE;
270 auddec_dsp_config(audio, 0);
271 rc = wait_event_interruptible_timeout(audio->wait,
272 audio->dec_state != MSM_AUD_DECODER_STATE_NONE,
273 msecs_to_jiffies(MSM_AUD_DECODER_WAIT_MS));
274 if (rc == 0)
275 rc = -ETIMEDOUT;
276 else if (audio->dec_state != MSM_AUD_DECODER_STATE_CLOSE)
277 rc = -EFAULT;
278 else
279 rc = 0;
280 wake_up(&audio->write_wait);
281 wake_up(&audio->read_wait);
282 msm_adsp_disable(audio->audplay);
283 audpp_disable(audio->dec_id, audio);
284 audio->out_needed = 0;
285 }
286 return rc;
287}
288
289/* ------------------- dsp --------------------- */
290static void audio_update_pcm_buf_entry(struct audio *audio,
291 uint32_t *payload)
292{
293 uint8_t index;
294 unsigned long flags;
295
296 if (audio->rflush)
297 return;
298
299 spin_lock_irqsave(&audio->dsp_lock, flags);
300 for (index = 0; index < payload[1]; index++) {
301 if (audio->in[audio->fill_next].addr ==
302 payload[2 + index * 2]) {
303 MM_DBG("audio_update_pcm_buf_entry: \
304 in[%d] ready\n", audio->fill_next);
305 audio->in[audio->fill_next].used =
306 payload[3 + index * 2];
307 if ((++audio->fill_next) == audio->pcm_buf_count)
308 audio->fill_next = 0;
309 } else {
310 MM_ERR("audio_update_pcm_buf_entry: \
311 expected=%x ret=%x\n",
312 audio->in[audio->fill_next].addr,
313 payload[1 + index * 2]);
314 break;
315 }
316 }
317 if (audio->in[audio->fill_next].used == 0) {
318 audplay_buffer_refresh(audio);
319 } else {
320 MM_DBG("read cannot keep up\n");
321 audio->buf_refresh = 1;
322 }
323 wake_up(&audio->read_wait);
324 spin_unlock_irqrestore(&audio->dsp_lock, flags);
325}
326
327static void audplay_dsp_event(void *data, unsigned id, size_t len,
328 void (*getevent) (void *ptr, size_t len))
329{
330 struct audio *audio = data;
331 uint32_t msg[28];
332
333 getevent(msg, sizeof(msg));
334
335 MM_DBG("msg_id=%x\n", id);
336
337 switch (id) {
338 case AUDPLAY_MSG_DEC_NEEDS_DATA:
339 audplay_send_data(audio, 1);
340 break;
341
342 case AUDPLAY_MSG_BUFFER_UPDATE:
343 audio_update_pcm_buf_entry(audio, msg);
344 break;
345
346 case ADSP_MESSAGE_ID:
347 MM_DBG("Received ADSP event: module enable(audplaytask)\n");
348 break;
349
350 default:
351 MM_ERR("unexpected message from decoder \n");
352 break;
353 }
354}
355
356static void audio_dsp_event(void *private, unsigned id, uint16_t *msg)
357{
358 struct audio *audio = private;
359
360 switch (id) {
361 case AUDPP_MSG_STATUS_MSG:{
362 unsigned status = msg[1];
363
364 switch (status) {
365 case AUDPP_DEC_STATUS_SLEEP: {
366 uint16_t reason = msg[2];
367 MM_DBG("decoder status:sleep reason = \
368 0x%04x\n", reason);
369 if ((reason == AUDPP_MSG_REASON_MEM)
370 || (reason ==
371 AUDPP_MSG_REASON_NODECODER)) {
372 audio->dec_state =
373 MSM_AUD_DECODER_STATE_FAILURE;
374 wake_up(&audio->wait);
375 } else if (reason == AUDPP_MSG_REASON_NONE) {
376 /* decoder is in disable state */
377 audio->dec_state =
378 MSM_AUD_DECODER_STATE_CLOSE;
379 wake_up(&audio->wait);
380 }
381 break;
382 }
383 case AUDPP_DEC_STATUS_INIT:
384 MM_DBG("decoder status: init\n");
385 if (audio->pcm_feedback)
386 audpp_cmd_cfg_routing_mode(audio);
387 else
388 audpp_cmd_cfg_adec_params(audio);
389 break;
390
391 case AUDPP_DEC_STATUS_CFG:
392 MM_DBG("decoder status: cfg\n");
393 break;
394 case AUDPP_DEC_STATUS_PLAY:
395 MM_DBG("decoder status: play \n");
396 /* send mixer command */
397 audpp_route_stream(audio->dec_id,
398 audio->source);
399 if (audio->pcm_feedback) {
400 audplay_config_hostpcm(audio);
401 audplay_buffer_refresh(audio);
402 }
403 audio->dec_state =
404 MSM_AUD_DECODER_STATE_SUCCESS;
405 wake_up(&audio->wait);
406 break;
407 default:
408 MM_ERR("unknown decoder status\n");
409 }
410 break;
411 }
412 case AUDPP_MSG_CFG_MSG:
413 if (msg[0] == AUDPP_MSG_ENA_ENA) {
414 MM_DBG("CFG_MSG ENABLE\n");
415 auddec_dsp_config(audio, 1);
416 audio->out_needed = 0;
417 audio->running = 1;
418 audpp_dsp_set_vol_pan(audio->dec_id, &audio->vol_pan,
419 POPP);
420 audpp_dsp_set_eq(audio->dec_id, audio->eq_enable,
421 &audio->eq, POPP);
422 } else if (msg[0] == AUDPP_MSG_ENA_DIS) {
423 MM_DBG("CFG_MSG DISABLE\n");
424 audio->running = 0;
425 } else {
426 MM_DBG("CFG_MSG %d?\n", msg[0]);
427 }
428 break;
429 case AUDPP_MSG_ROUTING_ACK:
430 MM_DBG("ROUTING_ACK mode=%d\n", msg[1]);
431 audpp_cmd_cfg_adec_params(audio);
432 break;
433
434 case AUDPP_MSG_FLUSH_ACK:
435 MM_DBG("FLUSH_ACK\n");
436 audio->wflush = 0;
437 audio->rflush = 0;
438 wake_up(&audio->write_wait);
439 if (audio->pcm_feedback)
440 audplay_buffer_refresh(audio);
441 break;
442
443 case AUDPP_MSG_PCMDMAMISSED:
444 MM_DBG("PCMDMAMISSED\n");
445 audio->teos = 1;
446 wake_up(&audio->write_wait);
447 break;
448
449 case AUDPP_MSG_AVSYNC_MSG:
450 MM_DBG("AUDPP_MSG_AVSYNC_MSG\n");
451 memcpy(&audio->avsync[0], msg, sizeof(audio->avsync));
452 audio->avsync_flag = 1;
453 wake_up(&audio->avsync_wait);
454 break;
455
456 default:
457 MM_ERR("UNKNOWN (%d)\n", id);
458 }
459
460}
461
462static struct msm_adsp_ops audplay_adsp_ops_wma = {
463 .event = audplay_dsp_event,
464};
465
466#define audplay_send_queue0(audio, cmd, len) \
467 msm_adsp_write(audio->audplay, audio->queue_id, \
468 cmd, len)
469
470static int auddec_dsp_config(struct audio *audio, int enable)
471{
472 struct audpp_cmd_cfg_dec_type cfg_dec_cmd;
473
474 memset(&cfg_dec_cmd, 0, sizeof(cfg_dec_cmd));
475
476 cfg_dec_cmd.cmd_id = AUDPP_CMD_CFG_DEC_TYPE;
477 if (enable)
478 cfg_dec_cmd.dec_cfg = AUDPP_CMD_UPDATDE_CFG_DEC |
479 AUDPP_CMD_ENA_DEC_V | AUDDEC_DEC_WMA;
480 else
481 cfg_dec_cmd.dec_cfg = AUDPP_CMD_UPDATDE_CFG_DEC |
482 AUDPP_CMD_DIS_DEC_V;
483 cfg_dec_cmd.dm_mode = 0x0;
484 cfg_dec_cmd.stream_id = audio->dec_id;
485 return audpp_send_queue1(&cfg_dec_cmd, sizeof(cfg_dec_cmd));
486}
487
488static void audpp_cmd_cfg_adec_params(struct audio *audio)
489{
490 struct audpp_cmd_cfg_adec_params_wma cmd;
491
492 memset(&cmd, 0, sizeof(cmd));
493 cmd.common.cmd_id = AUDPP_CMD_CFG_ADEC_PARAMS;
494 cmd.common.length = AUDPP_CMD_CFG_ADEC_PARAMS_WMA_LEN;
495 cmd.common.dec_id = audio->dec_id;
496 cmd.common.input_sampling_frequency = audio->out_sample_rate;
497
498 /*
499 * Test done for sample with the following configuration
500 * armdatareqthr = 1262
501 * channelsdecoded = 1(MONO)/2(STEREO)
502 * wmabytespersec = Tested with 6003 Bytes per sec
503 * wmasamplingfreq = 44100
504 * wmaencoderopts = 31
505 */
506
507 cmd.armdatareqthr = audio->wma_config.armdatareqthr;
508 cmd.channelsdecoded = audio->wma_config.channelsdecoded;
509 cmd.wmabytespersec = audio->wma_config.wmabytespersec;
510 cmd.wmasamplingfreq = audio->wma_config.wmasamplingfreq;
511 cmd.wmaencoderopts = audio->wma_config.wmaencoderopts;
512
513 audpp_send_queue2(&cmd, sizeof(cmd));
514}
515
516static void audpp_cmd_cfg_routing_mode(struct audio *audio)
517{
518 struct audpp_cmd_routing_mode cmd;
519
520 MM_DBG("\n"); /* Macro prints the file name and function */
521 memset(&cmd, 0, sizeof(cmd));
522 cmd.cmd_id = AUDPP_CMD_ROUTING_MODE;
523 cmd.object_number = audio->dec_id;
524 if (audio->pcm_feedback)
525 cmd.routing_mode = ROUTING_MODE_FTRT;
526 else
527 cmd.routing_mode = ROUTING_MODE_RT;
528
529 audpp_send_queue1(&cmd, sizeof(cmd));
530}
531
532static void audplay_buffer_refresh(struct audio *audio)
533{
534 struct audplay_cmd_buffer_refresh refresh_cmd;
535
536 refresh_cmd.cmd_id = AUDPLAY_CMD_BUFFER_REFRESH;
537 refresh_cmd.num_buffers = 1;
538 refresh_cmd.buf0_address = audio->in[audio->fill_next].addr;
539 refresh_cmd.buf0_length = audio->in[audio->fill_next].size;
540 refresh_cmd.buf_read_count = 0;
541
542 MM_DBG("buf0_addr=%x buf0_len=%d\n",
543 refresh_cmd.buf0_address,
544 refresh_cmd.buf0_length);
545
546 (void)audplay_send_queue0(audio, &refresh_cmd, sizeof(refresh_cmd));
547}
548
549static void audplay_config_hostpcm(struct audio *audio)
550{
551 struct audplay_cmd_hpcm_buf_cfg cfg_cmd;
552
553 MM_DBG("\n"); /* Macro prints the file name and function */
554 cfg_cmd.cmd_id = AUDPLAY_CMD_HPCM_BUF_CFG;
555 cfg_cmd.max_buffers = audio->pcm_buf_count;
556 cfg_cmd.byte_swap = 0;
557 cfg_cmd.hostpcm_config = (0x8000) | (0x4000);
558 cfg_cmd.feedback_frequency = 1;
559 cfg_cmd.partition_number = 0;
560
561 (void)audplay_send_queue0(audio, &cfg_cmd, sizeof(cfg_cmd));
562}
563
564
565static int audplay_dsp_send_data_avail(struct audio *audio,
566 unsigned idx, unsigned len)
567{
568 struct audplay_cmd_bitstream_data_avail_nt2 cmd;
569
570 cmd.cmd_id = AUDPLAY_CMD_BITSTREAM_DATA_AVAIL_NT2;
571 if (!audio->pcm_feedback)
572 cmd.decoder_id = 0;
573 else {
574 if (audio->mfield)
575 cmd.decoder_id = AUDWMA_METAFIELD_MASK |
576 (audio->out[idx].mfield_sz >> 1);
577 else
578 cmd.decoder_id = audio->dec_id;
579 }
580 cmd.buf_ptr = audio->out[idx].addr;
581 cmd.buf_size = len/2;
582 cmd.partition_number = 0;
583 return audplay_send_queue0(audio, &cmd, sizeof(cmd));
584}
585
586static void audplay_send_data(struct audio *audio, unsigned needed)
587{
588 struct buffer *frame;
589 unsigned long flags;
590
591 spin_lock_irqsave(&audio->dsp_lock, flags);
592 if (!audio->running)
593 goto done;
594
595 if (audio->wflush) {
596 audio->out_needed = 1;
597 goto done;
598 }
599
600 if (needed && !audio->wflush) {
601 /* We were called from the callback because the DSP
602 * requested more data. Note that the DSP does want
603 * more data, and if a buffer was in-flight, mark it
604 * as available (since the DSP must now be done with
605 * it).
606 */
607 audio->out_needed = 1;
608 frame = audio->out + audio->out_tail;
609 if (frame->used == 0xffffffff) {
610 MM_DBG("frame %d free\n", audio->out_tail);
611 frame->used = 0;
612 audio->out_tail ^= 1;
613 wake_up(&audio->write_wait);
614 }
615 }
616
617 if (audio->out_needed) {
618 /* If the DSP currently wants data and we have a
619 * buffer available, we will send it and reset
620 * the needed flag. We'll mark the buffer as in-flight
621 * so that it won't be recycled until the next buffer
622 * is requested
623 */
624
625 MM_DBG("\n"); /* Macro prints the file name and function */
626 frame = audio->out + audio->out_tail;
627 if (frame->used) {
628 BUG_ON(frame->used == 0xffffffff);
629 MM_DBG("frame %d busy\n", audio->out_tail);
630 audplay_dsp_send_data_avail(audio, audio->out_tail,
631 frame->used);
632 frame->used = 0xffffffff;
633 audio->out_needed = 0;
634 }
635 }
636done:
637 spin_unlock_irqrestore(&audio->dsp_lock, flags);
638}
639
640/* ------------------- device --------------------- */
641
642static void audio_flush(struct audio *audio)
643{
644 audio->out[0].used = 0;
645 audio->out[1].used = 0;
646 audio->out_head = 0;
647 audio->out_tail = 0;
648 audio->reserved = 0;
649 atomic_set(&audio->out_bytes, 0);
650}
651
652static void audio_flush_pcm_buf(struct audio *audio)
653{
654 uint8_t index;
655
656 for (index = 0; index < PCM_BUF_MAX_COUNT; index++)
657 audio->in[index].used = 0;
658 audio->buf_refresh = 0;
659 audio->read_next = 0;
660 audio->fill_next = 0;
661}
662
663static void audio_ioport_reset(struct audio *audio)
664{
665 /* Make sure read/write thread are free from
666 * sleep and knowing that system is not able
667 * to process io request at the moment
668 */
669 wake_up(&audio->write_wait);
670 mutex_lock(&audio->write_lock);
671 audio_flush(audio);
672 mutex_unlock(&audio->write_lock);
673 wake_up(&audio->read_wait);
674 mutex_lock(&audio->read_lock);
675 audio_flush_pcm_buf(audio);
676 mutex_unlock(&audio->read_lock);
677 audio->avsync_flag = 1;
678 wake_up(&audio->avsync_wait);
679}
680
681static int audwma_events_pending(struct audio *audio)
682{
683 unsigned long flags;
684 int empty;
685
686 spin_lock_irqsave(&audio->event_queue_lock, flags);
687 empty = !list_empty(&audio->event_queue);
688 spin_unlock_irqrestore(&audio->event_queue_lock, flags);
689 return empty || audio->event_abort;
690}
691
692static void audwma_reset_event_queue(struct audio *audio)
693{
694 unsigned long flags;
695 struct audwma_event *drv_evt;
696 struct list_head *ptr, *next;
697
698 spin_lock_irqsave(&audio->event_queue_lock, flags);
699 list_for_each_safe(ptr, next, &audio->event_queue) {
700 drv_evt = list_first_entry(&audio->event_queue,
701 struct audwma_event, list);
702 list_del(&drv_evt->list);
703 kfree(drv_evt);
704 }
705 list_for_each_safe(ptr, next, &audio->free_event_queue) {
706 drv_evt = list_first_entry(&audio->free_event_queue,
707 struct audwma_event, list);
708 list_del(&drv_evt->list);
709 kfree(drv_evt);
710 }
711 spin_unlock_irqrestore(&audio->event_queue_lock, flags);
712
713 return;
714}
715
716static long audwma_process_event_req(struct audio *audio, void __user *arg)
717{
718 long rc;
719 struct msm_audio_event usr_evt;
720 struct audwma_event *drv_evt = NULL;
721 int timeout;
722 unsigned long flags;
723
724 if (copy_from_user(&usr_evt, arg, sizeof(struct msm_audio_event)))
725 return -EFAULT;
726
727 timeout = (int) usr_evt.timeout_ms;
728
729 if (timeout > 0) {
730 rc = wait_event_interruptible_timeout(
731 audio->event_wait, audwma_events_pending(audio),
732 msecs_to_jiffies(timeout));
733 if (rc == 0)
734 return -ETIMEDOUT;
735 } else {
736 rc = wait_event_interruptible(
737 audio->event_wait, audwma_events_pending(audio));
738 }
739
740 if (rc < 0)
741 return rc;
742
743 if (audio->event_abort) {
744 audio->event_abort = 0;
745 return -ENODEV;
746 }
747
748 rc = 0;
749
750 spin_lock_irqsave(&audio->event_queue_lock, flags);
751 if (!list_empty(&audio->event_queue)) {
752 drv_evt = list_first_entry(&audio->event_queue,
753 struct audwma_event, list);
754 list_del(&drv_evt->list);
755 }
756
757 if (drv_evt) {
758 usr_evt.event_type = drv_evt->event_type;
759 usr_evt.event_payload = drv_evt->payload;
760 list_add_tail(&drv_evt->list, &audio->free_event_queue);
761 } else
762 rc = -1;
763 spin_unlock_irqrestore(&audio->event_queue_lock, flags);
764
765 if (!rc && copy_to_user(arg, &usr_evt, sizeof(usr_evt)))
766 rc = -EFAULT;
767
768 return rc;
769}
770
771static int audio_enable_eq(struct audio *audio, int enable)
772{
773 if (audio->eq_enable == enable && !audio->eq_needs_commit)
774 return 0;
775
776 audio->eq_enable = enable;
777
778 if (audio->running) {
779 audpp_dsp_set_eq(audio->dec_id, enable, &audio->eq, POPP);
780 audio->eq_needs_commit = 0;
781 }
782 return 0;
783}
784
785static int audio_get_avsync_data(struct audio *audio,
786 struct msm_audio_stats *stats)
787{
788 int rc = -EINVAL;
789 unsigned long flags;
790
791 local_irq_save(flags);
792 if (audio->dec_id == audio->avsync[0] && audio->avsync_flag) {
793 /* av_sync sample count */
794 stats->sample_count = (audio->avsync[2] << 16) |
795 (audio->avsync[3]);
796
797 /* av_sync byte_count */
798 stats->byte_count = (audio->avsync[5] << 16) |
799 (audio->avsync[6]);
800
801 audio->avsync_flag = 0;
802 rc = 0;
803 }
804 local_irq_restore(flags);
805 return rc;
806
807}
808
809static long audio_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
810{
811 struct audio *audio = file->private_data;
812 int rc = -EINVAL;
813 unsigned long flags = 0;
814 uint16_t enable_mask;
815 int enable;
816 int prev_state;
817
818 MM_DBG("cmd = %d\n", cmd);
819
820 if (cmd == AUDIO_GET_STATS) {
821 struct msm_audio_stats stats;
822
823 audio->avsync_flag = 0;
824 memset(&stats, 0, sizeof(stats));
825 if (audpp_query_avsync(audio->dec_id) < 0)
826 return rc;
827
828 rc = wait_event_interruptible_timeout(audio->avsync_wait,
829 (audio->avsync_flag == 1),
830 msecs_to_jiffies(AUDPP_AVSYNC_EVENT_TIMEOUT));
831
832 if (rc < 0)
833 return rc;
834 else if ((rc > 0) || ((rc == 0) && (audio->avsync_flag == 1))) {
835 if (audio_get_avsync_data(audio, &stats) < 0)
836 return rc;
837
838 if (copy_to_user((void *)arg, &stats, sizeof(stats)))
839 return -EFAULT;
840 return 0;
841 } else
842 return -EAGAIN;
843 }
844
845 switch (cmd) {
846 case AUDIO_ENABLE_AUDPP:
847 if (copy_from_user(&enable_mask, (void *) arg,
848 sizeof(enable_mask))) {
849 rc = -EFAULT;
850 break;
851 }
852
853 spin_lock_irqsave(&audio->dsp_lock, flags);
854 enable = (enable_mask & EQ_ENABLE) ? 1 : 0;
855 audio_enable_eq(audio, enable);
856 spin_unlock_irqrestore(&audio->dsp_lock, flags);
857 rc = 0;
858 break;
859 case AUDIO_SET_VOLUME:
860 spin_lock_irqsave(&audio->dsp_lock, flags);
861 audio->vol_pan.volume = arg;
862 if (audio->running)
863 audpp_dsp_set_vol_pan(audio->dec_id, &audio->vol_pan,
864 POPP);
865 spin_unlock_irqrestore(&audio->dsp_lock, flags);
866 rc = 0;
867 break;
868
869 case AUDIO_SET_PAN:
870 spin_lock_irqsave(&audio->dsp_lock, flags);
871 audio->vol_pan.pan = arg;
872 if (audio->running)
873 audpp_dsp_set_vol_pan(audio->dec_id, &audio->vol_pan,
874 POPP);
875 spin_unlock_irqrestore(&audio->dsp_lock, flags);
876 rc = 0;
877 break;
878
879 case AUDIO_SET_EQ:
880 prev_state = audio->eq_enable;
881 audio->eq_enable = 0;
882 if (copy_from_user(&audio->eq.num_bands, (void *) arg,
883 sizeof(audio->eq) -
884 (AUDPP_CMD_CFG_OBJECT_PARAMS_COMMON_LEN + 2))) {
885 rc = -EFAULT;
886 break;
887 }
888 audio->eq_enable = prev_state;
889 audio->eq_needs_commit = 1;
890 rc = 0;
891 break;
892 }
893
894 if (-EINVAL != rc)
895 return rc;
896
897 if (cmd == AUDIO_GET_EVENT) {
898 MM_DBG("AUDIO_GET_EVENT\n");
899 if (mutex_trylock(&audio->get_event_lock)) {
900 rc = audwma_process_event_req(audio,
901 (void __user *) arg);
902 mutex_unlock(&audio->get_event_lock);
903 } else
904 rc = -EBUSY;
905 return rc;
906 }
907
908 if (cmd == AUDIO_ABORT_GET_EVENT) {
909 audio->event_abort = 1;
910 wake_up(&audio->event_wait);
911 return 0;
912 }
913
914 mutex_lock(&audio->lock);
915 switch (cmd) {
916 case AUDIO_START:
917 MM_DBG("AUDIO_START\n");
918 rc = audio_enable(audio);
919 if (!rc) {
920 rc = wait_event_interruptible_timeout(audio->wait,
921 audio->dec_state != MSM_AUD_DECODER_STATE_NONE,
922 msecs_to_jiffies(MSM_AUD_DECODER_WAIT_MS));
923 MM_INFO("dec_state %d rc = %d\n", audio->dec_state, rc);
924
925 if (audio->dec_state != MSM_AUD_DECODER_STATE_SUCCESS)
926 rc = -ENODEV;
927 else
928 rc = 0;
929 }
930 break;
931 case AUDIO_STOP:
932 MM_DBG("AUDIO_STOP\n");
933 rc = audio_disable(audio);
934 audio->stopped = 1;
935 audio_ioport_reset(audio);
936 audio->stopped = 0;
937 break;
938 case AUDIO_FLUSH:
939 MM_DBG("AUDIO_FLUSH\n");
940 audio->rflush = 1;
941 audio->wflush = 1;
942 audio_ioport_reset(audio);
943 if (audio->running) {
944 audpp_flush(audio->dec_id);
945 rc = wait_event_interruptible(audio->write_wait,
946 !audio->wflush);
947 if (rc < 0) {
948 MM_ERR("AUDIO_FLUSH interrupted\n");
949 rc = -EINTR;
950 }
951 } else {
952 audio->rflush = 0;
953 audio->wflush = 0;
954 }
955 break;
956 case AUDIO_SET_CONFIG: {
957 struct msm_audio_config config;
958 if (copy_from_user(&config, (void *) arg, sizeof(config))) {
959 rc = -EFAULT;
960 break;
961 }
962 if (config.channel_count == 1) {
963 config.channel_count = AUDPP_CMD_PCM_INTF_MONO_V;
964 } else if (config.channel_count == 2) {
965 config.channel_count = AUDPP_CMD_PCM_INTF_STEREO_V;
966 } else {
967 rc = -EINVAL;
968 break;
969 }
970 audio->mfield = config.meta_field;
971 audio->out_sample_rate = config.sample_rate;
972 audio->out_channel_mode = config.channel_count;
973 rc = 0;
974 break;
975 }
976 case AUDIO_GET_CONFIG: {
977 struct msm_audio_config config;
978 config.buffer_size = (audio->out_dma_sz >> 1);
979 config.buffer_count = 2;
980 config.sample_rate = audio->out_sample_rate;
981 if (audio->out_channel_mode == AUDPP_CMD_PCM_INTF_MONO_V)
982 config.channel_count = 1;
983 else
984 config.channel_count = 2;
985 config.meta_field = 0;
986 config.unused[0] = 0;
987 config.unused[1] = 0;
988 config.unused[2] = 0;
989 if (copy_to_user((void *) arg, &config, sizeof(config)))
990 rc = -EFAULT;
991 else
992 rc = 0;
993
994 break;
995 }
996 case AUDIO_GET_WMA_CONFIG:{
997 if (copy_to_user((void *)arg, &audio->wma_config,
998 sizeof(audio->wma_config)))
999 rc = -EFAULT;
1000 else
1001 rc = 0;
1002 break;
1003 }
1004 case AUDIO_SET_WMA_CONFIG:{
1005 struct msm_audio_wma_config usr_config;
1006
1007 if (copy_from_user
1008 (&usr_config, (void *)arg,
1009 sizeof(usr_config))) {
1010 rc = -EFAULT;
1011 break;
1012 }
1013
1014 audio->wma_config = usr_config;
1015 rc = 0;
1016 break;
1017 }
1018 case AUDIO_GET_PCM_CONFIG:{
1019 struct msm_audio_pcm_config config;
1020 config.pcm_feedback = audio->pcm_feedback;
1021 config.buffer_count = PCM_BUF_MAX_COUNT;
1022 config.buffer_size = PCM_BUFSZ_MIN;
1023 if (copy_to_user((void *)arg, &config,
1024 sizeof(config)))
1025 rc = -EFAULT;
1026 else
1027 rc = 0;
1028 break;
1029 }
1030 case AUDIO_SET_PCM_CONFIG:{
1031 struct msm_audio_pcm_config config;
1032 if (copy_from_user
1033 (&config, (void *)arg, sizeof(config))) {
1034 rc = -EFAULT;
1035 break;
1036 }
1037 if (config.pcm_feedback != audio->pcm_feedback) {
1038 MM_ERR("Not sufficient permission to"
1039 "change the playback mode\n");
1040 rc = -EACCES;
1041 break;
1042 }
1043 if ((config.buffer_count > PCM_BUF_MAX_COUNT) ||
1044 (config.buffer_count == 1))
1045 config.buffer_count = PCM_BUF_MAX_COUNT;
1046
1047 if (config.buffer_size < PCM_BUFSZ_MIN)
1048 config.buffer_size = PCM_BUFSZ_MIN;
1049
1050 /* Check if pcm feedback is required */
1051 if ((config.pcm_feedback) && (!audio->read_data)) {
1052 MM_DBG("allocate PCM buffer %d\n",
1053 config.buffer_count *
1054 config.buffer_size);
Santosh Mardifdc227a2011-07-11 17:20:34 +05301055 audio->read_phys =
1056 allocate_contiguous_ebi_nomap(
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001057 config.buffer_size *
1058 config.buffer_count,
Santosh Mardifdc227a2011-07-11 17:20:34 +05301059 SZ_4K);
1060 if (!audio->read_phys) {
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001061 rc = -ENOMEM;
1062 break;
1063 }
Santosh Mardifdc227a2011-07-11 17:20:34 +05301064 audio->map_v_read = msm_subsystem_map_buffer(
1065 audio->read_phys,
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001066 config.buffer_size *
Santosh Mardifdc227a2011-07-11 17:20:34 +05301067 config.buffer_count,
1068 MSM_SUBSYSTEM_MAP_KADDR
1069 , NULL, 0);
1070 if (IS_ERR(audio->map_v_read)) {
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001071 MM_ERR("read buf alloc fail\n");
1072 rc = -ENOMEM;
Santosh Mardifdc227a2011-07-11 17:20:34 +05301073 free_contiguous_memory_by_paddr(
1074 audio->read_phys);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001075 } else {
1076 uint8_t index;
1077 uint32_t offset = 0;
Santosh Mardifdc227a2011-07-11 17:20:34 +05301078 audio->read_data =
1079 audio->map_v_read->vaddr;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001080 audio->buf_refresh = 0;
1081 audio->pcm_buf_count =
1082 config.buffer_count;
1083 audio->read_next = 0;
1084 audio->fill_next = 0;
1085
1086 for (index = 0;
1087 index < config.buffer_count;
1088 index++) {
1089 audio->in[index].data =
1090 audio->read_data + offset;
1091 audio->in[index].addr =
1092 audio->read_phys + offset;
1093 audio->in[index].size =
1094 config.buffer_size;
1095 audio->in[index].used = 0;
1096 offset += config.buffer_size;
1097 }
1098 MM_DBG("read buf: phy addr \
1099 0x%08x kernel addr 0x%08x\n",
1100 audio->read_phys,
1101 (int)audio->read_data);
1102 rc = 0;
1103 }
1104 } else {
1105 rc = 0;
1106 }
1107 break;
1108 }
1109 case AUDIO_PAUSE:
1110 MM_DBG("AUDIO_PAUSE %ld\n", arg);
1111 rc = audpp_pause(audio->dec_id, (int) arg);
1112 break;
1113 case AUDIO_GET_SESSION_ID:
1114 if (copy_to_user((void *) arg, &audio->dec_id,
1115 sizeof(unsigned short)))
1116 rc = -EFAULT;
1117 else
1118 rc = 0;
1119 break;
1120 default:
1121 rc = -EINVAL;
1122 }
1123 mutex_unlock(&audio->lock);
1124 return rc;
1125}
1126
1127/* Only useful in tunnel-mode */
1128static int audio_fsync(struct file *file, int datasync)
1129{
1130 struct audio *audio = file->private_data;
1131 struct buffer *frame;
1132 int rc = 0;
1133
1134 MM_DBG("\n"); /* Macro prints the file name and function */
1135
1136 if (!audio->running || audio->pcm_feedback) {
1137 rc = -EINVAL;
1138 goto done_nolock;
1139 }
1140
1141 mutex_lock(&audio->write_lock);
1142
1143 rc = wait_event_interruptible(audio->write_wait,
1144 (!audio->out[0].used &&
1145 !audio->out[1].used &&
1146 audio->out_needed) || audio->wflush);
1147
1148 if (rc < 0)
1149 goto done;
1150 else if (audio->wflush) {
1151 rc = -EBUSY;
1152 goto done;
1153 }
1154
1155 if (audio->reserved) {
1156 MM_DBG("send reserved byte\n");
1157 frame = audio->out + audio->out_tail;
1158 ((char *) frame->data)[0] = audio->rsv_byte;
1159 ((char *) frame->data)[1] = 0;
1160 frame->used = 2;
1161 audplay_send_data(audio, 0);
1162
1163 rc = wait_event_interruptible(audio->write_wait,
1164 (!audio->out[0].used &&
1165 !audio->out[1].used &&
1166 audio->out_needed) || audio->wflush);
1167
1168 if (rc < 0)
1169 goto done;
1170 else if (audio->wflush) {
1171 rc = -EBUSY;
1172 goto done;
1173 }
1174 }
1175
1176 /* pcm dmamiss message is sent continously
1177 * when decoder is starved so no race
1178 * condition concern
1179 */
1180 audio->teos = 0;
1181
1182 rc = wait_event_interruptible(audio->write_wait,
1183 audio->teos || audio->wflush);
1184
1185 if (audio->wflush)
1186 rc = -EBUSY;
1187
1188done:
1189 mutex_unlock(&audio->write_lock);
1190done_nolock:
1191 return rc;
1192}
1193
1194static ssize_t audio_read(struct file *file, char __user *buf, size_t count,
1195 loff_t *pos)
1196{
1197 struct audio *audio = file->private_data;
1198 const char __user *start = buf;
1199 int rc = 0;
1200
1201 if (!audio->pcm_feedback)
1202 return 0; /* PCM feedback is not enabled. Nothing to read */
1203
1204 mutex_lock(&audio->read_lock);
1205 MM_DBG("%d \n", count);
1206 while (count > 0) {
1207 rc = wait_event_interruptible(audio->read_wait,
1208 (audio->in[audio->read_next].used > 0) ||
1209 (audio->stopped) || (audio->rflush));
1210
1211 if (rc < 0)
1212 break;
1213
1214 if (audio->stopped || audio->rflush) {
1215 rc = -EBUSY;
1216 break;
1217 }
1218
1219 if (count < audio->in[audio->read_next].used) {
1220 /* Read must happen in frame boundary. Since driver
1221 does not know frame size, read count must be greater
1222 or equal to size of PCM samples */
1223 MM_DBG("audio_read: no partial frame done reading\n");
1224 break;
1225 } else {
1226 MM_DBG("audio_read: read from in[%d]\n",
1227 audio->read_next);
1228 if (copy_to_user
1229 (buf, audio->in[audio->read_next].data,
1230 audio->in[audio->read_next].used)) {
1231 MM_ERR("invalid addr %x \n", (unsigned int)buf);
1232 rc = -EFAULT;
1233 break;
1234 }
1235 count -= audio->in[audio->read_next].used;
1236 buf += audio->in[audio->read_next].used;
1237 audio->in[audio->read_next].used = 0;
1238 if ((++audio->read_next) == audio->pcm_buf_count)
1239 audio->read_next = 0;
1240 break; /* Force to exit while loop
1241 * to prevent output thread
1242 * sleep too long if data is
1243 * not ready at this moment.
1244 */
1245 }
1246 }
1247
1248 /* don't feed output buffer to HW decoder during flushing
1249 * buffer refresh command will be sent once flush completes
1250 * send buf refresh command here can confuse HW decoder
1251 */
1252 if (audio->buf_refresh && !audio->rflush) {
1253 audio->buf_refresh = 0;
1254 MM_DBG("kick start pcm feedback again\n");
1255 audplay_buffer_refresh(audio);
1256 }
1257
1258 mutex_unlock(&audio->read_lock);
1259
1260 if (buf > start)
1261 rc = buf - start;
1262
1263 MM_DBG("read %d bytes\n", rc);
1264 return rc;
1265}
1266
1267static int audwma_process_eos(struct audio *audio,
1268 const char __user *buf_start, unsigned short mfield_size)
1269{
1270 int rc = 0;
1271 struct buffer *frame;
1272 char *buf_ptr;
1273
1274 if (audio->reserved) {
1275 MM_DBG("flush reserve byte\n");
1276 frame = audio->out + audio->out_head;
1277 buf_ptr = frame->data;
1278 rc = wait_event_interruptible(audio->write_wait,
1279 (frame->used == 0)
1280 || (audio->stopped)
1281 || (audio->wflush));
1282 if (rc < 0)
1283 goto done;
1284 if (audio->stopped || audio->wflush) {
1285 rc = -EBUSY;
1286 goto done;
1287 }
1288
1289 buf_ptr[0] = audio->rsv_byte;
1290 buf_ptr[1] = 0;
1291 audio->out_head ^= 1;
1292 frame->mfield_sz = 0;
1293 frame->used = 2;
1294 audio->reserved = 0;
1295 audplay_send_data(audio, 0);
1296 }
1297
1298 frame = audio->out + audio->out_head;
1299
1300 rc = wait_event_interruptible(audio->write_wait,
1301 (audio->out_needed &&
1302 audio->out[0].used == 0 &&
1303 audio->out[1].used == 0)
1304 || (audio->stopped)
1305 || (audio->wflush));
1306
1307 if (rc < 0)
1308 goto done;
1309 if (audio->stopped || audio->wflush) {
1310 rc = -EBUSY;
1311 goto done;
1312 }
1313
1314 if (copy_from_user(frame->data, buf_start, mfield_size)) {
1315 rc = -EFAULT;
1316 goto done;
1317 }
1318
1319 frame->mfield_sz = mfield_size;
1320 audio->out_head ^= 1;
1321 frame->used = mfield_size;
1322 audplay_send_data(audio, 0);
1323done:
1324 return rc;
1325}
1326
1327static ssize_t audio_write(struct file *file, const char __user *buf,
1328 size_t count, loff_t *pos)
1329{
1330 struct audio *audio = file->private_data;
1331 const char __user *start = buf;
1332 struct buffer *frame;
1333 size_t xfer;
1334 char *cpy_ptr;
1335 int rc = 0, eos_condition = AUDWMA_EOS_NONE;
1336 unsigned dsize;
1337 unsigned short mfield_size = 0;
1338
1339 MM_DBG("cnt=%d\n", count);
1340
1341 mutex_lock(&audio->write_lock);
1342 while (count > 0) {
1343 frame = audio->out + audio->out_head;
1344 cpy_ptr = frame->data;
1345 dsize = 0;
1346 rc = wait_event_interruptible(audio->write_wait,
1347 (frame->used == 0)
1348 || (audio->stopped)
1349 || (audio->wflush));
1350 if (rc < 0)
1351 break;
1352 if (audio->stopped || audio->wflush) {
1353 rc = -EBUSY;
1354 break;
1355 }
1356 if (audio->mfield) {
1357 if (buf == start) {
1358 /* Processing beginning of user buffer */
1359 if (__get_user(mfield_size,
1360 (unsigned short __user *) buf)) {
1361 rc = -EFAULT;
1362 break;
1363 } else if (mfield_size > count) {
1364 rc = -EINVAL;
1365 break;
1366 }
1367 MM_DBG("audio_write: mf offset_val %x\n",
1368 mfield_size);
1369 if (copy_from_user(cpy_ptr, buf, mfield_size)) {
1370 rc = -EFAULT;
1371 break;
1372 }
1373 /* Check if EOS flag is set and buffer has
1374 * contains just meta field
1375 */
1376 if (cpy_ptr[AUDWMA_EOS_FLG_OFFSET] &
1377 AUDWMA_EOS_FLG_MASK) {
1378 MM_DBG("audio_write: EOS SET\n");
1379 eos_condition = AUDWMA_EOS_SET;
1380 if (mfield_size == count) {
1381 buf += mfield_size;
1382 break;
1383 } else
1384 cpy_ptr[AUDWMA_EOS_FLG_OFFSET]
1385 &= ~AUDWMA_EOS_FLG_MASK;
1386 }
1387 cpy_ptr += mfield_size;
1388 count -= mfield_size;
1389 dsize += mfield_size;
1390 buf += mfield_size;
1391 } else {
1392 mfield_size = 0;
1393 MM_DBG("audio_write: continuous buffer\n");
1394 }
1395 frame->mfield_sz = mfield_size;
1396 }
1397
1398 if (audio->reserved) {
1399 MM_DBG("append reserved byte %x\n", audio->rsv_byte);
1400 *cpy_ptr = audio->rsv_byte;
1401 xfer = (count > ((frame->size - mfield_size) - 1)) ?
1402 (frame->size - mfield_size) - 1 : count;
1403 cpy_ptr++;
1404 dsize += 1;
1405 audio->reserved = 0;
1406 } else
1407 xfer = (count > (frame->size - mfield_size)) ?
1408 (frame->size - mfield_size) : count;
1409
1410 if (copy_from_user(cpy_ptr, buf, xfer)) {
1411 rc = -EFAULT;
1412 break;
1413 }
1414
1415 dsize += xfer;
1416 if (dsize & 1) {
1417 audio->rsv_byte = ((char *) frame->data)[dsize - 1];
1418 MM_DBG("odd length buf reserve last byte %x\n",
1419 audio->rsv_byte);
1420 audio->reserved = 1;
1421 dsize--;
1422 }
1423 count -= xfer;
1424 buf += xfer;
1425
1426 if (dsize > 0) {
1427 audio->out_head ^= 1;
1428 frame->used = dsize;
1429 audplay_send_data(audio, 0);
1430 }
1431 }
1432 if (eos_condition == AUDWMA_EOS_SET)
1433 rc = audwma_process_eos(audio, start, mfield_size);
1434 mutex_unlock(&audio->write_lock);
1435 if (!rc) {
1436 if (buf > start)
1437 return buf - start;
1438 }
1439 return rc;
1440}
1441
1442static int audio_release(struct inode *inode, struct file *file)
1443{
1444 struct audio *audio = file->private_data;
1445
1446 MM_INFO("audio instance 0x%08x freeing\n", (int)audio);
1447 mutex_lock(&audio->lock);
1448 auddev_unregister_evt_listner(AUDDEV_CLNT_DEC, audio->dec_id);
1449 audio_disable(audio);
1450 audio_flush(audio);
1451 audio_flush_pcm_buf(audio);
1452 msm_adsp_put(audio->audplay);
1453 audpp_adec_free(audio->dec_id);
1454#ifdef CONFIG_HAS_EARLYSUSPEND
1455 unregister_early_suspend(&audio->suspend_ctl.node);
1456#endif
1457 audio->event_abort = 1;
1458 wake_up(&audio->event_wait);
1459 audwma_reset_event_queue(audio);
Santosh Mardifdc227a2011-07-11 17:20:34 +05301460 msm_subsystem_unmap_buffer(audio->map_v_write);
1461 free_contiguous_memory_by_paddr(audio->phys);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001462 if (audio->read_data) {
Santosh Mardifdc227a2011-07-11 17:20:34 +05301463 msm_subsystem_unmap_buffer(audio->map_v_read);
1464 free_contiguous_memory_by_paddr(audio->read_phys);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001465 }
1466 mutex_unlock(&audio->lock);
1467#ifdef CONFIG_DEBUG_FS
1468 if (audio->dentry)
1469 debugfs_remove(audio->dentry);
1470#endif
1471 kfree(audio);
1472 return 0;
1473}
1474
1475static void audwma_post_event(struct audio *audio, int type,
1476 union msm_audio_event_payload payload)
1477{
1478 struct audwma_event *e_node = NULL;
1479 unsigned long flags;
1480
1481 spin_lock_irqsave(&audio->event_queue_lock, flags);
1482
1483 if (!list_empty(&audio->free_event_queue)) {
1484 e_node = list_first_entry(&audio->free_event_queue,
1485 struct audwma_event, list);
1486 list_del(&e_node->list);
1487 } else {
1488 e_node = kmalloc(sizeof(struct audwma_event), GFP_ATOMIC);
1489 if (!e_node) {
1490 MM_ERR("No mem to post event %d\n", type);
1491 return;
1492 }
1493 }
1494
1495 e_node->event_type = type;
1496 e_node->payload = payload;
1497
1498 list_add_tail(&e_node->list, &audio->event_queue);
1499 spin_unlock_irqrestore(&audio->event_queue_lock, flags);
1500 wake_up(&audio->event_wait);
1501}
1502
1503#ifdef CONFIG_HAS_EARLYSUSPEND
1504static void audwma_suspend(struct early_suspend *h)
1505{
1506 struct audwma_suspend_ctl *ctl =
1507 container_of(h, struct audwma_suspend_ctl, node);
1508 union msm_audio_event_payload payload;
1509
1510 MM_DBG("\n"); /* Macro prints the file name and function */
1511 audwma_post_event(ctl->audio, AUDIO_EVENT_SUSPEND, payload);
1512}
1513
1514static void audwma_resume(struct early_suspend *h)
1515{
1516 struct audwma_suspend_ctl *ctl =
1517 container_of(h, struct audwma_suspend_ctl, node);
1518 union msm_audio_event_payload payload;
1519
1520 MM_DBG("\n"); /* Macro prints the file name and function */
1521 audwma_post_event(ctl->audio, AUDIO_EVENT_RESUME, payload);
1522}
1523#endif
1524
1525#ifdef CONFIG_DEBUG_FS
1526static ssize_t audwma_debug_open(struct inode *inode, struct file *file)
1527{
1528 file->private_data = inode->i_private;
1529 return 0;
1530}
1531
1532static ssize_t audwma_debug_read(struct file *file, char __user *buf,
1533 size_t count, loff_t *ppos)
1534{
1535 const int debug_bufmax = 4096;
1536 static char buffer[4096];
1537 int n = 0, i;
1538 struct audio *audio = file->private_data;
1539
1540 mutex_lock(&audio->lock);
1541 n = scnprintf(buffer, debug_bufmax, "opened %d\n", audio->opened);
1542 n += scnprintf(buffer + n, debug_bufmax - n,
1543 "enabled %d\n", audio->enabled);
1544 n += scnprintf(buffer + n, debug_bufmax - n,
1545 "stopped %d\n", audio->stopped);
1546 n += scnprintf(buffer + n, debug_bufmax - n,
1547 "pcm_feedback %d\n", audio->pcm_feedback);
1548 n += scnprintf(buffer + n, debug_bufmax - n,
1549 "out_buf_sz %d\n", audio->out[0].size);
1550 n += scnprintf(buffer + n, debug_bufmax - n,
1551 "pcm_buf_count %d \n", audio->pcm_buf_count);
1552 n += scnprintf(buffer + n, debug_bufmax - n,
1553 "pcm_buf_sz %d \n", audio->in[0].size);
1554 n += scnprintf(buffer + n, debug_bufmax - n,
1555 "volume %x \n", audio->vol_pan.volume);
1556 n += scnprintf(buffer + n, debug_bufmax - n,
1557 "sample rate %d \n", audio->out_sample_rate);
1558 n += scnprintf(buffer + n, debug_bufmax - n,
1559 "channel mode %d \n", audio->out_channel_mode);
1560 mutex_unlock(&audio->lock);
1561 /* Following variables are only useful for debugging when
1562 * when playback halts unexpectedly. Thus, no mutual exclusion
1563 * enforced
1564 */
1565 n += scnprintf(buffer + n, debug_bufmax - n,
1566 "wflush %d\n", audio->wflush);
1567 n += scnprintf(buffer + n, debug_bufmax - n,
1568 "rflush %d\n", audio->rflush);
1569 n += scnprintf(buffer + n, debug_bufmax - n,
1570 "running %d \n", audio->running);
1571 n += scnprintf(buffer + n, debug_bufmax - n,
1572 "dec state %d \n", audio->dec_state);
1573 n += scnprintf(buffer + n, debug_bufmax - n,
1574 "out_needed %d \n", audio->out_needed);
1575 n += scnprintf(buffer + n, debug_bufmax - n,
1576 "out_head %d \n", audio->out_head);
1577 n += scnprintf(buffer + n, debug_bufmax - n,
1578 "out_tail %d \n", audio->out_tail);
1579 n += scnprintf(buffer + n, debug_bufmax - n,
1580 "out[0].used %d \n", audio->out[0].used);
1581 n += scnprintf(buffer + n, debug_bufmax - n,
1582 "out[1].used %d \n", audio->out[1].used);
1583 n += scnprintf(buffer + n, debug_bufmax - n,
1584 "buffer_refresh %d \n", audio->buf_refresh);
1585 n += scnprintf(buffer + n, debug_bufmax - n,
1586 "read_next %d \n", audio->read_next);
1587 n += scnprintf(buffer + n, debug_bufmax - n,
1588 "fill_next %d \n", audio->fill_next);
1589 for (i = 0; i < audio->pcm_buf_count; i++)
1590 n += scnprintf(buffer + n, debug_bufmax - n,
1591 "in[%d].size %d \n", i, audio->in[i].used);
1592 buffer[n] = 0;
1593 return simple_read_from_buffer(buf, count, ppos, buffer, n);
1594}
1595
1596static const struct file_operations audwma_debug_fops = {
1597 .read = audwma_debug_read,
1598 .open = audwma_debug_open,
1599};
1600#endif
1601
1602static int audio_open(struct inode *inode, struct file *file)
1603{
1604 struct audio *audio = NULL;
1605 int rc, dec_attrb, decid, i;
1606 unsigned pmem_sz = DMASZ_MAX;
1607 struct audwma_event *e_node = NULL;
1608#ifdef CONFIG_DEBUG_FS
1609 /* 4 bytes represents decoder number, 1 byte for terminate string */
1610 char name[sizeof "msm_wma_" + 5];
1611#endif
1612
1613 /* Allocate Mem for audio instance */
1614 audio = kzalloc(sizeof(struct audio), GFP_KERNEL);
1615 if (!audio) {
1616 MM_ERR("no memory to allocate audio instance \n");
1617 rc = -ENOMEM;
1618 goto done;
1619 }
1620 MM_INFO("audio instance 0x%08x created\n", (int)audio);
1621
1622 /* Allocate the decoder */
1623 dec_attrb = AUDDEC_DEC_WMA;
1624 if ((file->f_mode & FMODE_WRITE) &&
1625 (file->f_mode & FMODE_READ)) {
1626 dec_attrb |= MSM_AUD_MODE_NONTUNNEL;
1627 audio->pcm_feedback = NON_TUNNEL_MODE_PLAYBACK;
1628 } else if ((file->f_mode & FMODE_WRITE) &&
1629 !(file->f_mode & FMODE_READ)) {
1630 dec_attrb |= MSM_AUD_MODE_TUNNEL;
1631 audio->pcm_feedback = TUNNEL_MODE_PLAYBACK;
1632 } else {
1633 kfree(audio);
1634 rc = -EACCES;
1635 goto done;
1636 }
1637
1638 decid = audpp_adec_alloc(dec_attrb, &audio->module_name,
1639 &audio->queue_id);
1640
1641 if (decid < 0) {
1642 MM_ERR("No free decoder available, freeing instance 0x%08x\n",
1643 (int)audio);
1644 rc = -ENODEV;
1645 kfree(audio);
1646 goto done;
1647 }
1648 audio->dec_id = decid & MSM_AUD_DECODER_MASK;
1649
1650 while (pmem_sz >= DMASZ_MIN) {
1651 MM_DBG("pmemsz = %d\n", pmem_sz);
Santosh Mardifdc227a2011-07-11 17:20:34 +05301652 audio->phys = allocate_contiguous_ebi_nomap(pmem_sz, SZ_4K);
1653 if (audio->phys) {
1654 audio->map_v_write = msm_subsystem_map_buffer(
1655 audio->phys, pmem_sz,
1656 MSM_SUBSYSTEM_MAP_KADDR,
1657 NULL, 0);
1658 if (IS_ERR(audio->map_v_write)) {
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001659 MM_ERR("could not allocate write buffers, \
1660 freeing instance 0x%08x\n",
1661 (int)audio);
1662 rc = -ENOMEM;
Santosh Mardifdc227a2011-07-11 17:20:34 +05301663 free_contiguous_memory_by_paddr(audio->phys);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001664 audpp_adec_free(audio->dec_id);
1665 kfree(audio);
1666 goto done;
1667 }
Santosh Mardifdc227a2011-07-11 17:20:34 +05301668 audio->data = audio->map_v_write->vaddr;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001669 MM_DBG("write buf: phy addr 0x%08x kernel addr \
1670 0x%08x\n", audio->phys, (int)audio->data);
1671 break;
1672 } else if (pmem_sz == DMASZ_MIN) {
1673 MM_ERR("could not allocate write buffers, freeing \
1674 instance 0x%08x\n", (int)audio);
1675 rc = -ENOMEM;
1676 audpp_adec_free(audio->dec_id);
1677 kfree(audio);
1678 goto done;
1679 } else
1680 pmem_sz >>= 1;
1681 }
1682 audio->out_dma_sz = pmem_sz;
1683
1684 rc = msm_adsp_get(audio->module_name, &audio->audplay,
1685 &audplay_adsp_ops_wma, audio);
1686 if (rc) {
1687 MM_ERR("failed to get %s module, freeing instance 0x%08x\n",
1688 audio->module_name, (int)audio);
1689 goto err;
1690 }
1691
1692 mutex_init(&audio->lock);
1693 mutex_init(&audio->write_lock);
1694 mutex_init(&audio->read_lock);
1695 mutex_init(&audio->get_event_lock);
1696 spin_lock_init(&audio->dsp_lock);
1697 init_waitqueue_head(&audio->write_wait);
1698 init_waitqueue_head(&audio->read_wait);
1699 INIT_LIST_HEAD(&audio->free_event_queue);
1700 INIT_LIST_HEAD(&audio->event_queue);
1701 init_waitqueue_head(&audio->wait);
1702 init_waitqueue_head(&audio->event_wait);
1703 spin_lock_init(&audio->event_queue_lock);
1704 init_waitqueue_head(&audio->avsync_wait);
1705
1706 audio->out[0].data = audio->data + 0;
1707 audio->out[0].addr = audio->phys + 0;
1708 audio->out[0].size = audio->out_dma_sz >> 1;
1709
1710 audio->out[1].data = audio->data + audio->out[0].size;
1711 audio->out[1].addr = audio->phys + audio->out[0].size;
1712 audio->out[1].size = audio->out[0].size;
1713
1714 audio->wma_config.armdatareqthr = 1262;
1715 audio->wma_config.channelsdecoded = 2;
1716 audio->wma_config.wmabytespersec = 6003;
1717 audio->wma_config.wmasamplingfreq = 44100;
1718 audio->wma_config.wmaencoderopts = 31;
1719
1720 audio->out_sample_rate = 44100;
1721 audio->out_channel_mode = AUDPP_CMD_PCM_INTF_STEREO_V;
1722
1723 audio->vol_pan.volume = 0x2000;
1724
1725 audio_flush(audio);
1726
1727 file->private_data = audio;
1728 audio->opened = 1;
1729
1730 audio->device_events = AUDDEV_EVT_DEV_RDY
1731 |AUDDEV_EVT_DEV_RLS|
1732 AUDDEV_EVT_STREAM_VOL_CHG;
1733
1734 rc = auddev_register_evt_listner(audio->device_events,
1735 AUDDEV_CLNT_DEC,
1736 audio->dec_id,
1737 wma_listner,
1738 (void *)audio);
1739 if (rc) {
1740 MM_ERR("%s: failed to register listner\n", __func__);
1741 goto event_err;
1742 }
1743
1744#ifdef CONFIG_DEBUG_FS
1745 snprintf(name, sizeof name, "msm_wma_%04x", audio->dec_id);
1746 audio->dentry = debugfs_create_file(name, S_IFREG | S_IRUGO,
1747 NULL, (void *) audio,
1748 &audwma_debug_fops);
1749
1750 if (IS_ERR(audio->dentry))
1751 MM_DBG("debugfs_create_file failed\n");
1752#endif
1753#ifdef CONFIG_HAS_EARLYSUSPEND
1754 audio->suspend_ctl.node.level = EARLY_SUSPEND_LEVEL_DISABLE_FB;
1755 audio->suspend_ctl.node.resume = audwma_resume;
1756 audio->suspend_ctl.node.suspend = audwma_suspend;
1757 audio->suspend_ctl.audio = audio;
1758 register_early_suspend(&audio->suspend_ctl.node);
1759#endif
1760 for (i = 0; i < AUDWMA_EVENT_NUM; i++) {
1761 e_node = kmalloc(sizeof(struct audwma_event), GFP_KERNEL);
1762 if (e_node)
1763 list_add_tail(&e_node->list, &audio->free_event_queue);
1764 else {
1765 MM_ERR("event pkt alloc failed\n");
1766 break;
1767 }
1768 }
1769done:
1770 return rc;
1771event_err:
1772 msm_adsp_put(audio->audplay);
1773err:
Santosh Mardifdc227a2011-07-11 17:20:34 +05301774 msm_subsystem_unmap_buffer(audio->map_v_write);
1775 free_contiguous_memory_by_paddr(audio->phys);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001776 audpp_adec_free(audio->dec_id);
1777 kfree(audio);
1778 return rc;
1779}
1780
1781static const struct file_operations audio_wma_fops = {
1782 .owner = THIS_MODULE,
1783 .open = audio_open,
1784 .release = audio_release,
1785 .read = audio_read,
1786 .write = audio_write,
1787 .unlocked_ioctl = audio_ioctl,
1788 .fsync = audio_fsync,
1789};
1790
1791struct miscdevice audio_wma_misc = {
1792 .minor = MISC_DYNAMIC_MINOR,
1793 .name = "msm_wma",
1794 .fops = &audio_wma_fops,
1795};
1796
1797static int __init audio_init(void)
1798{
1799 return misc_register(&audio_wma_misc);
1800}
1801
1802device_initcall(audio_init);