blob: 1997bcda17b6aeb929f7b9eed5f10d5a4eb4ab8c [file] [log] [blame]
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001/* Copyright (c) 2011, Code Aurora Forum. All rights reserved.
2 *
3 * This program is free software; you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License version 2 and
5 * only version 2 as published by the Free Software Foundation.
6 *
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 * GNU General Public License for more details.
11 */
12#include <linux/slab.h>
13#include <linux/kthread.h>
14#include <linux/kernel.h>
15#include <linux/module.h>
16#include <linux/uaccess.h>
17#include <linux/wait.h>
18#include <linux/mutex.h>
Ben Romberger13b74ab2011-07-18 17:36:32 -070019
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070020#include <mach/qdsp6v2/audio_acdb.h>
Ben Romberger13b74ab2011-07-18 17:36:32 -070021#include <mach/qdsp6v2/rtac.h>
22
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070023#include "sound/apr_audio.h"
24#include "sound/q6afe.h"
Ben Romberger13b74ab2011-07-18 17:36:32 -070025
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070026#include "q6voice.h"
27
28#define TIMEOUT_MS 3000
29
30#define CMD_STATUS_SUCCESS 0
31#define CMD_STATUS_FAIL 1
32
33#define VOC_PATH_PASSIVE 0
34#define VOC_PATH_FULL 1
35
36static struct voice_data voice;
37
38static int voice_send_enable_vocproc_cmd(struct voice_data *v);
39static int voice_send_netid_timing_cmd(struct voice_data *v);
40static int voice_send_attach_vocproc_cmd(struct voice_data *v);
41static int voice_send_set_device_cmd(struct voice_data *v);
42static int voice_send_disable_vocproc_cmd(struct voice_data *v);
43static int voice_send_vol_index_cmd(struct voice_data *v);
Helen Zeng29eb7442011-06-20 11:06:29 -070044static int voice_send_cvp_map_memory_cmd(struct voice_data *v);
45static int voice_send_cvp_unmap_memory_cmd(struct voice_data *v);
46static int voice_send_cvs_map_memory_cmd(struct voice_data *v);
47static int voice_send_cvs_unmap_memory_cmd(struct voice_data *v);
48static int voice_send_cvs_register_cal_cmd(struct voice_data *v);
49static int voice_send_cvs_deregister_cal_cmd(struct voice_data *v);
50static int voice_send_cvp_register_cal_cmd(struct voice_data *v);
51static int voice_send_cvp_deregister_cal_cmd(struct voice_data *v);
52static int voice_send_cvp_register_vol_cal_table_cmd(struct voice_data *v);
53static int voice_send_cvp_deregister_vol_cal_table_cmd(struct voice_data *v);
Helen Zeng44d4d272011-08-10 14:49:20 -070054static int voice_send_set_widevoice_enable_cmd(struct voice_data *v);
Helen Zeng29eb7442011-06-20 11:06:29 -070055
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -070056
57static int32_t qdsp_mvm_callback(struct apr_client_data *data, void *priv);
58static int32_t qdsp_cvs_callback(struct apr_client_data *data, void *priv);
59static int32_t qdsp_cvp_callback(struct apr_client_data *data, void *priv);
60
61static u16 voice_get_mvm_handle(struct voice_data *v)
62{
63 u16 mvm_handle = 0;
64
65 if (v == NULL) {
66 pr_err("%s: v is NULL\n", __func__);
67 return -EINVAL;
68 }
69 if (v->voc_path == VOC_PATH_PASSIVE)
70 mvm_handle = v->mvm_passive_handle;
71 else
72 mvm_handle = v->mvm_full_handle;
73
74 pr_debug("%s: mvm_handle %d\n", __func__, mvm_handle);
75
76 return mvm_handle;
77}
78
79static void voice_set_mvm_handle(struct voice_data *v, u16 mvm_handle)
80{
81 pr_debug("%s: mvm_handle %d\n", __func__, mvm_handle);
82 if (v == NULL) {
83 pr_err("%s: v is NULL\n", __func__);
84 return;
85 }
86
87 if (v->voc_path == VOC_PATH_PASSIVE)
88 v->mvm_passive_handle = mvm_handle;
89 else
90 v->mvm_full_handle = mvm_handle;
91}
92
93static u16 voice_get_cvs_handle(struct voice_data *v)
94{
95 u16 cvs_handle = 0;
96
97 if (v == NULL) {
98 pr_err("%s: v is NULL\n", __func__);
99 return -EINVAL;
100 }
101 if (v->voc_path == VOC_PATH_PASSIVE)
102 cvs_handle = v->cvs_passive_handle;
103 else
104 cvs_handle = v->cvs_full_handle;
105
106 pr_debug("%s: cvs_handle %d\n", __func__, cvs_handle);
107
108 return cvs_handle;
109}
110
111static void voice_set_cvs_handle(struct voice_data *v, u16 cvs_handle)
112{
113 pr_debug("%s: cvs_handle %d\n", __func__, cvs_handle);
114 if (v == NULL) {
115 pr_err("%s: v is NULL\n", __func__);
116 return;
117 }
118 if (v->voc_path == VOC_PATH_PASSIVE)
119 v->cvs_passive_handle = cvs_handle;
120 else
121 v->cvs_full_handle = cvs_handle;
122}
123
124static u16 voice_get_cvp_handle(struct voice_data *v)
125{
126 u16 cvp_handle = 0;
127
128 if (v->voc_path == VOC_PATH_PASSIVE)
129 cvp_handle = v->cvp_passive_handle;
130 else
131 cvp_handle = v->cvp_full_handle;
132
133 pr_debug("%s: cvp_handle %d\n", __func__, cvp_handle);
134
135 return cvp_handle;
136}
137
138static void voice_set_cvp_handle(struct voice_data *v, u16 cvp_handle)
139{
140 pr_debug("%s: cvp_handle %d\n", __func__, cvp_handle);
141 if (v == NULL) {
142 pr_err("%s: v is NULL\n", __func__);
143 return;
144 }
145 if (v->voc_path == VOC_PATH_PASSIVE)
146 v->cvp_passive_handle = cvp_handle;
147 else
148 v->cvp_full_handle = cvp_handle;
149}
150
151static int voice_apr_register(struct voice_data *v)
152{
153 void *apr_mvm, *apr_cvs, *apr_cvp;
154
155 if (v == NULL) {
156 pr_err("%s: v is NULL\n", __func__);
157 return -EINVAL;
158 }
159 apr_mvm = v->apr_q6_mvm;
160 apr_cvs = v->apr_q6_cvs;
161 apr_cvp = v->apr_q6_cvp;
162
163 pr_debug("into voice_apr_register_callback\n");
164 /* register callback to APR */
165 if (apr_mvm == NULL) {
166 pr_debug("start to register MVM callback\n");
167
168 apr_mvm = apr_register("ADSP", "MVM",
169 qdsp_mvm_callback,
170 0xFFFFFFFF, v);
171
172 if (apr_mvm == NULL) {
173 pr_err("Unable to register MVM\n");
174 goto err;
175 }
176 v->apr_q6_mvm = apr_mvm;
177 }
178
179 if (apr_cvs == NULL) {
180 pr_debug("start to register CVS callback\n");
181
182 apr_cvs = apr_register("ADSP", "CVS",
183 qdsp_cvs_callback,
184 0xFFFFFFFF, v);
185
186 if (apr_cvs == NULL) {
187 pr_err("Unable to register CVS\n");
188 goto err;
189 }
190 v->apr_q6_cvs = apr_cvs;
Ben Romberger13b74ab2011-07-18 17:36:32 -0700191
192 rtac_set_voice_handle(RTAC_CVS, apr_cvs);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700193 }
194
195 if (apr_cvp == NULL) {
196 pr_debug("start to register CVP callback\n");
197
198 apr_cvp = apr_register("ADSP", "CVP",
199 qdsp_cvp_callback,
200 0xFFFFFFFF, v);
201
202 if (apr_cvp == NULL) {
203 pr_err("Unable to register CVP\n");
204 goto err;
205 }
206 v->apr_q6_cvp = apr_cvp;
Ben Romberger13b74ab2011-07-18 17:36:32 -0700207
208 rtac_set_voice_handle(RTAC_CVP, apr_cvp);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700209 }
210 return 0;
211
212err:
213 if (v->apr_q6_cvs != NULL) {
214 apr_deregister(apr_cvs);
215 v->apr_q6_cvs = NULL;
Ben Romberger13b74ab2011-07-18 17:36:32 -0700216 rtac_set_voice_handle(RTAC_CVS, NULL);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700217 }
218 if (v->apr_q6_mvm != NULL) {
219 apr_deregister(apr_mvm);
220 v->apr_q6_mvm = NULL;
221 }
222
223 return -ENODEV;
224}
225
226static int voice_create_mvm_cvs_session(struct voice_data *v)
227{
228 int ret = 0;
Helen Zeng69b00962011-07-08 11:38:36 -0700229 struct mvm_create_ctl_session_cmd mvm_session_cmd;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700230 struct cvs_create_passive_ctl_session_cmd cvs_session_cmd;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700231 struct cvs_create_full_ctl_session_cmd cvs_full_ctl_cmd;
232 struct mvm_attach_stream_cmd attach_stream_cmd;
233 void *apr_mvm, *apr_cvs, *apr_cvp;
234 u16 mvm_handle, cvs_handle, cvp_handle;
235
236 if (v == NULL) {
237 pr_err("%s: v is NULL\n", __func__);
238 return -EINVAL;
239 }
240 apr_mvm = v->apr_q6_mvm;
241 apr_cvs = v->apr_q6_cvs;
242 apr_cvp = v->apr_q6_cvp;
243
244 if (!apr_mvm || !apr_cvs || !apr_cvp) {
245 pr_err("%s: apr_mvm or apr_cvs or apr_cvp is NULL\n", __func__);
246 return -EINVAL;
247 }
248 mvm_handle = voice_get_mvm_handle(v);
249 cvs_handle = voice_get_cvs_handle(v);
250 cvp_handle = voice_get_cvp_handle(v);
251
252 pr_debug("%s: mvm_hdl=%d, cvs_hdl=%d\n", __func__,
253 mvm_handle, cvs_handle);
254 /* send cmd to create mvm session and wait for response */
255
256 if (!mvm_handle) {
257 if (v->voc_path == VOC_PATH_PASSIVE) {
258 mvm_session_cmd.hdr.hdr_field = APR_HDR_FIELD(
259 APR_MSG_TYPE_SEQ_CMD,
260 APR_HDR_LEN(APR_HDR_SIZE),
261 APR_PKT_VER);
262 mvm_session_cmd.hdr.pkt_size = APR_PKT_SIZE(
263 APR_HDR_SIZE,
264 sizeof(mvm_session_cmd) -
265 APR_HDR_SIZE);
266 pr_debug("send mvm create session pkt size = %d\n",
267 mvm_session_cmd.hdr.pkt_size);
268 mvm_session_cmd.hdr.src_port = 0;
269 mvm_session_cmd.hdr.dest_port = 0;
270 mvm_session_cmd.hdr.token = 0;
271 mvm_session_cmd.hdr.opcode =
272 VSS_IMVM_CMD_CREATE_PASSIVE_CONTROL_SESSION;
Helen Zeng69b00962011-07-08 11:38:36 -0700273 strncpy(mvm_session_cmd.mvm_session.name,
274 "default modem voice", SESSION_NAME_LEN);
275
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700276 v->mvm_state = CMD_STATUS_FAIL;
277
278 ret = apr_send_pkt(apr_mvm,
279 (uint32_t *) &mvm_session_cmd);
280 if (ret < 0) {
281 pr_err("Error sending MVM_CONTROL_SESSION\n");
282 goto fail;
283 }
284 ret = wait_event_timeout(v->mvm_wait,
285 (v->mvm_state == CMD_STATUS_SUCCESS),
286 msecs_to_jiffies(TIMEOUT_MS));
287 if (!ret) {
288 pr_err("%s: wait_event timeout\n", __func__);
289 goto fail;
290 }
291 } else {
292 pr_debug("%s: creating MVM full ctrl\n", __func__);
Helen Zeng69b00962011-07-08 11:38:36 -0700293 mvm_session_cmd.hdr.hdr_field =
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700294 APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
295 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
Helen Zeng69b00962011-07-08 11:38:36 -0700296 mvm_session_cmd.hdr.pkt_size =
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700297 APR_PKT_SIZE(APR_HDR_SIZE,
Helen Zeng69b00962011-07-08 11:38:36 -0700298 sizeof(mvm_session_cmd) -
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700299 APR_HDR_SIZE);
Helen Zeng69b00962011-07-08 11:38:36 -0700300 mvm_session_cmd.hdr.src_port = 0;
301 mvm_session_cmd.hdr.dest_port = 0;
302 mvm_session_cmd.hdr.token = 0;
303 mvm_session_cmd.hdr.opcode =
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700304 VSS_IMVM_CMD_CREATE_FULL_CONTROL_SESSION;
Helen Zeng69b00962011-07-08 11:38:36 -0700305 strncpy(mvm_session_cmd.mvm_session.name,
306 "default voip", SESSION_NAME_LEN);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700307
308 v->mvm_state = CMD_STATUS_FAIL;
309
310 ret = apr_send_pkt(apr_mvm,
Helen Zeng69b00962011-07-08 11:38:36 -0700311 (uint32_t *) &mvm_session_cmd);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700312 if (ret < 0) {
313 pr_err("Fail in sending MVM_CONTROL_SESSION\n");
314 goto fail;
315 }
316 ret = wait_event_timeout(v->mvm_wait,
317 (v->mvm_state == CMD_STATUS_SUCCESS),
318 msecs_to_jiffies(TIMEOUT_MS));
319 if (!ret) {
320 pr_err("%s: wait_event timeout\n", __func__);
321 goto fail;
322 }
323 }
324 /* Get the created MVM handle. */
325 mvm_handle = voice_get_mvm_handle(v);
326 }
327 /* send cmd to create cvs session */
328 if (!cvs_handle) {
329 if (v->voc_path == VOC_PATH_PASSIVE) {
330 pr_debug("creating CVS passive session\n");
331
332 cvs_session_cmd.hdr.hdr_field = APR_HDR_FIELD(
333 APR_MSG_TYPE_SEQ_CMD,
334 APR_HDR_LEN(APR_HDR_SIZE),
335 APR_PKT_VER);
336 cvs_session_cmd.hdr.pkt_size =
337 APR_PKT_SIZE(APR_HDR_SIZE,
338 sizeof(cvs_session_cmd) -
339 APR_HDR_SIZE);
340 cvs_session_cmd.hdr.src_port = 0;
341 cvs_session_cmd.hdr.dest_port = 0;
342 cvs_session_cmd.hdr.token = 0;
343 cvs_session_cmd.hdr.opcode =
344 VSS_ISTREAM_CMD_CREATE_PASSIVE_CONTROL_SESSION;
345 strncpy(cvs_session_cmd.cvs_session.name,
Helen Zeng69b00962011-07-08 11:38:36 -0700346 "default modem voice", SESSION_NAME_LEN);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700347
348 v->cvs_state = CMD_STATUS_FAIL;
349
350 ret = apr_send_pkt(apr_cvs,
351 (uint32_t *) &cvs_session_cmd);
352 if (ret < 0) {
353 pr_err("Fail in sending STREAM_CONTROL_SESSION\n");
354 goto fail;
355 }
356 ret = wait_event_timeout(v->cvs_wait,
357 (v->cvs_state == CMD_STATUS_SUCCESS),
358 msecs_to_jiffies(TIMEOUT_MS));
359 if (!ret) {
360 pr_err("%s: wait_event timeout\n", __func__);
361 goto fail;
362 }
363 /* Get the created CVS handle. */
364 cvs_handle = voice_get_cvs_handle(v);
365
366 } else {
367 pr_debug("creating CVS full session\n");
368
369 cvs_full_ctl_cmd.hdr.hdr_field =
370 APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
371 APR_HDR_LEN(APR_HDR_SIZE),
372 APR_PKT_VER);
373
374 cvs_full_ctl_cmd.hdr.pkt_size =
375 APR_PKT_SIZE(APR_HDR_SIZE,
376 sizeof(cvs_full_ctl_cmd) -
377 APR_HDR_SIZE);
378
379 cvs_full_ctl_cmd.hdr.src_port = 0;
380 cvs_full_ctl_cmd.hdr.dest_port = 0;
381 cvs_full_ctl_cmd.hdr.token = 0;
382 cvs_full_ctl_cmd.hdr.opcode =
383 VSS_ISTREAM_CMD_CREATE_FULL_CONTROL_SESSION;
384 cvs_full_ctl_cmd.cvs_session.direction = 2;
385 cvs_full_ctl_cmd.cvs_session.enc_media_type =
386 v->mvs_info.media_type;
387 cvs_full_ctl_cmd.cvs_session.dec_media_type =
388 v->mvs_info.media_type;
389 cvs_full_ctl_cmd.cvs_session.network_id =
390 v->mvs_info.network_type;
391 strncpy(cvs_full_ctl_cmd.cvs_session.name,
392 "default q6 voice", 16);
393
394 v->cvs_state = CMD_STATUS_FAIL;
395
396 ret = apr_send_pkt(apr_cvs,
397 (uint32_t *) &cvs_full_ctl_cmd);
398
399 if (ret < 0) {
400 pr_err("%s: Err %d sending CREATE_FULL_CTRL\n",
401 __func__, ret);
402 goto fail;
403 }
404 ret = wait_event_timeout(v->cvs_wait,
405 (v->cvs_state == CMD_STATUS_SUCCESS),
406 msecs_to_jiffies(TIMEOUT_MS));
407 if (!ret) {
408 pr_err("%s: wait_event timeout\n", __func__);
409 goto fail;
410 }
411 /* Get the created CVS handle. */
412 cvs_handle = voice_get_cvs_handle(v);
413
414 /* Attach MVM to CVS. */
415 pr_debug("Attach MVM to stream\n");
416
417 attach_stream_cmd.hdr.hdr_field =
418 APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
419 APR_HDR_LEN(APR_HDR_SIZE),
420 APR_PKT_VER);
421 attach_stream_cmd.hdr.pkt_size =
422 APR_PKT_SIZE(APR_HDR_SIZE,
423 sizeof(attach_stream_cmd) -
424 APR_HDR_SIZE);
425 attach_stream_cmd.hdr.src_port = 0;
426 attach_stream_cmd.hdr.dest_port = mvm_handle;
427 attach_stream_cmd.hdr.token = 0;
428 attach_stream_cmd.hdr.opcode =
429 VSS_IMVM_CMD_ATTACH_STREAM;
430 attach_stream_cmd.attach_stream.handle = cvs_handle;
431
432 v->mvm_state = CMD_STATUS_FAIL;
433 ret = apr_send_pkt(apr_mvm,
434 (uint32_t *) &attach_stream_cmd);
435 if (ret < 0) {
436 pr_err("%s: Error %d sending ATTACH_STREAM\n",
437 __func__, ret);
438 goto fail;
439 }
440 ret = wait_event_timeout(v->mvm_wait,
441 (v->mvm_state == CMD_STATUS_SUCCESS),
442 msecs_to_jiffies(TIMEOUT_MS));
443 if (!ret) {
444 pr_err("%s: wait_event timeout\n", __func__);
445 goto fail;
446 }
447 }
448 }
449 return 0;
450
451fail:
452 return -EINVAL;
453}
454
455static int voice_destroy_mvm_cvs_session(struct voice_data *v)
456{
457 int ret = 0;
458 struct mvm_detach_stream_cmd detach_stream;
459 struct apr_hdr mvm_destroy;
460 struct apr_hdr cvs_destroy;
461 void *apr_mvm, *apr_cvs;
462 u16 mvm_handle, cvs_handle;
463
464 if (v == NULL) {
465 pr_err("%s: v is NULL\n", __func__);
466 return -EINVAL;
467 }
468 apr_mvm = v->apr_q6_mvm;
469 apr_cvs = v->apr_q6_cvs;
470
471 if (!apr_mvm || !apr_cvs) {
472 pr_err("%s: apr_mvm or apr_cvs is NULL\n", __func__);
473 return -EINVAL;
474 }
475 mvm_handle = voice_get_mvm_handle(v);
476 cvs_handle = voice_get_cvs_handle(v);
477
478 /* MVM, CVS sessions are destroyed only for Full control sessions. */
479 if (v->voc_path == VOC_PATH_FULL) {
480 pr_debug("MVM detach stream\n");
481
482 /* Detach voice stream. */
483 detach_stream.hdr.hdr_field =
484 APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
485 APR_HDR_LEN(APR_HDR_SIZE),
486 APR_PKT_VER);
487 detach_stream.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
488 sizeof(detach_stream) - APR_HDR_SIZE);
489 detach_stream.hdr.src_port = 0;
490 detach_stream.hdr.dest_port = mvm_handle;
491 detach_stream.hdr.token = 0;
492 detach_stream.hdr.opcode = VSS_IMVM_CMD_DETACH_STREAM;
493 detach_stream.detach_stream.handle = cvs_handle;
494
495 v->mvm_state = CMD_STATUS_FAIL;
496
497 ret = apr_send_pkt(apr_mvm, (uint32_t *) &detach_stream);
498 if (ret < 0) {
499 pr_err("%s: Error %d sending DETACH_STREAM\n",
500 __func__, ret);
501 goto fail;
502 }
503 ret = wait_event_timeout(v->mvm_wait,
504 (v->mvm_state == CMD_STATUS_SUCCESS),
505 msecs_to_jiffies(TIMEOUT_MS));
506 if (!ret) {
507 pr_err("%s: wait event timeout\n", __func__);
508 goto fail;
509 }
510 /* Destroy CVS. */
511 pr_debug("CVS destroy session\n");
512
513 cvs_destroy.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
514 APR_HDR_LEN(APR_HDR_SIZE),
515 APR_PKT_VER);
516 cvs_destroy.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
517 sizeof(cvs_destroy) - APR_HDR_SIZE);
518 cvs_destroy.src_port = 0;
519 cvs_destroy.dest_port = cvs_handle;
520 cvs_destroy.token = 0;
521 cvs_destroy.opcode = APRV2_IBASIC_CMD_DESTROY_SESSION;
522
523 v->cvs_state = CMD_STATUS_FAIL;
524
525 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_destroy);
526 if (ret < 0) {
527 pr_err("%s: Error %d sending CVS DESTROY\n",
528 __func__, ret);
529 goto fail;
530 }
531 ret = wait_event_timeout(v->cvs_wait,
532 (v->cvs_state == CMD_STATUS_SUCCESS),
533 msecs_to_jiffies(TIMEOUT_MS));
534 if (!ret) {
535 pr_err("%s: wait event timeout\n", __func__);
536
537 goto fail;
538 }
539 cvs_handle = 0;
540 voice_set_cvs_handle(v, cvs_handle);
541
542 /* Destroy MVM. */
543 pr_debug("MVM destroy session\n");
544
545 mvm_destroy.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
546 APR_HDR_LEN(APR_HDR_SIZE),
547 APR_PKT_VER);
548 mvm_destroy.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
549 sizeof(mvm_destroy) - APR_HDR_SIZE);
550 mvm_destroy.src_port = 0;
551 mvm_destroy.dest_port = mvm_handle;
552 mvm_destroy.token = 0;
553 mvm_destroy.opcode = APRV2_IBASIC_CMD_DESTROY_SESSION;
554
555 v->mvm_state = CMD_STATUS_FAIL;
556
557 ret = apr_send_pkt(apr_mvm, (uint32_t *) &mvm_destroy);
558 if (ret < 0) {
559 pr_err("%s: Error %d sending MVM DESTROY\n",
560 __func__, ret);
561
562 goto fail;
563 }
564 ret = wait_event_timeout(v->mvm_wait,
565 (v->mvm_state == CMD_STATUS_SUCCESS),
566 msecs_to_jiffies(TIMEOUT_MS));
567 if (!ret) {
568 pr_err("%s: wait event timeout\n", __func__);
569
570 goto fail;
571 }
572 mvm_handle = 0;
573 voice_set_mvm_handle(v, mvm_handle);
574 }
575 return 0;
576fail:
577 return -EINVAL;
578}
579
580static int voice_send_tty_mode_cmd(struct voice_data *v)
581{
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700582 int ret = 0;
583 struct mvm_set_tty_mode_cmd mvm_tty_mode_cmd;
584 void *apr_mvm;
585 u16 mvm_handle;
586
587 if (v == NULL) {
588 pr_err("%s: v is NULL\n", __func__);
589 return -EINVAL;
590 }
591 apr_mvm = v->apr_q6_mvm;
592
593 if (!apr_mvm) {
594 pr_err("%s: apr_mvm is NULL.\n", __func__);
595 return -EINVAL;
596 }
597 mvm_handle = voice_get_mvm_handle(v);
598
Helen Zengcc65b5b2011-07-06 19:14:48 -0700599 if (v->tty_mode) {
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700600 /* send tty mode cmd to mvm */
601 mvm_tty_mode_cmd.hdr.hdr_field = APR_HDR_FIELD(
602 APR_MSG_TYPE_SEQ_CMD,
603 APR_HDR_LEN(APR_HDR_SIZE),
604 APR_PKT_VER);
605 mvm_tty_mode_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
606 sizeof(mvm_tty_mode_cmd) -
607 APR_HDR_SIZE);
608 pr_debug("pkt size = %d\n", mvm_tty_mode_cmd.hdr.pkt_size);
609 mvm_tty_mode_cmd.hdr.src_port = 0;
610 mvm_tty_mode_cmd.hdr.dest_port = mvm_handle;
611 mvm_tty_mode_cmd.hdr.token = 0;
612 mvm_tty_mode_cmd.hdr.opcode = VSS_ISTREAM_CMD_SET_TTY_MODE;
Helen Zengcc65b5b2011-07-06 19:14:48 -0700613 mvm_tty_mode_cmd.tty_mode.mode = v->tty_mode;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -0700614 pr_debug("tty mode =%d\n", mvm_tty_mode_cmd.tty_mode.mode);
615
616 v->mvm_state = CMD_STATUS_FAIL;
617 ret = apr_send_pkt(apr_mvm, (uint32_t *) &mvm_tty_mode_cmd);
618 if (ret < 0) {
619 pr_err("Fail: sending VSS_ISTREAM_CMD_SET_TTY_MODE\n");
620 goto fail;
621 }
622 ret = wait_event_timeout(v->mvm_wait,
623 (v->mvm_state == CMD_STATUS_SUCCESS),
624 msecs_to_jiffies(TIMEOUT_MS));
625 if (!ret) {
626 pr_err("%s: wait_event timeout\n", __func__);
627 goto fail;
628 }
629 }
630 return 0;
631fail:
632 return -EINVAL;
633}
634
635static int voice_config_cvs_vocoder(struct voice_data *v)
636{
637 int ret = 0;
638 void *apr_cvs;
639 u16 cvs_handle;
640 /* Set media type. */
641 struct cvs_set_media_type_cmd cvs_set_media_cmd;
642
643 if (v == NULL) {
644 pr_err("%s: v is NULL\n", __func__);
645 return -EINVAL;
646 }
647 apr_cvs = v->apr_q6_cvs;
648
649 if (!apr_cvs) {
650 pr_err("%s: apr_cvs is NULL.\n", __func__);
651 return -EINVAL;
652 }
653
654 cvs_handle = voice_get_cvs_handle(v);
655
656 cvs_set_media_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
657 APR_HDR_LEN(APR_HDR_SIZE),
658 APR_PKT_VER);
659 cvs_set_media_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
660 sizeof(cvs_set_media_cmd) - APR_HDR_SIZE);
661 cvs_set_media_cmd.hdr.src_port = 0;
662 cvs_set_media_cmd.hdr.dest_port = cvs_handle;
663 cvs_set_media_cmd.hdr.token = 0;
664 cvs_set_media_cmd.hdr.opcode = VSS_ISTREAM_CMD_SET_MEDIA_TYPE;
665 cvs_set_media_cmd.media_type.tx_media_id = v->mvs_info.media_type;
666 cvs_set_media_cmd.media_type.rx_media_id = v->mvs_info.media_type;
667
668 v->cvs_state = CMD_STATUS_FAIL;
669
670 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_set_media_cmd);
671 if (ret < 0) {
672 pr_err("%s: Error %d sending SET_MEDIA_TYPE\n",
673 __func__, ret);
674
675 goto fail;
676 }
677 ret = wait_event_timeout(v->cvs_wait,
678 (v->cvs_state == CMD_STATUS_SUCCESS),
679 msecs_to_jiffies(TIMEOUT_MS));
680 if (!ret) {
681 pr_err("%s: wait_event timeout\n", __func__);
682
683 goto fail;
684 }
685 /* Set encoder properties. */
686 switch (v->mvs_info.media_type) {
687 case VSS_MEDIA_ID_EVRC_MODEM: {
688 struct cvs_set_cdma_enc_minmax_rate_cmd cvs_set_cdma_rate;
689
690 pr_debug("Setting EVRC min-max rate\n");
691
692 cvs_set_cdma_rate.hdr.hdr_field =
693 APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
694 APR_HDR_LEN(APR_HDR_SIZE),
695 APR_PKT_VER);
696 cvs_set_cdma_rate.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
697 sizeof(cvs_set_cdma_rate) - APR_HDR_SIZE);
698 cvs_set_cdma_rate.hdr.src_port = 0;
699 cvs_set_cdma_rate.hdr.dest_port = cvs_handle;
700 cvs_set_cdma_rate.hdr.token = 0;
701 cvs_set_cdma_rate.hdr.opcode =
702 VSS_ISTREAM_CMD_CDMA_SET_ENC_MINMAX_RATE;
703 cvs_set_cdma_rate.cdma_rate.min_rate = v->mvs_info.rate;
704 cvs_set_cdma_rate.cdma_rate.max_rate = v->mvs_info.rate;
705
706 v->cvs_state = CMD_STATUS_FAIL;
707
708 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_set_cdma_rate);
709 if (ret < 0) {
710 pr_err("%s: Error %d sending SET_EVRC_MINMAX_RATE\n",
711 __func__, ret);
712 goto fail;
713 }
714 ret = wait_event_timeout(v->cvs_wait,
715 (v->cvs_state == CMD_STATUS_SUCCESS),
716 msecs_to_jiffies(TIMEOUT_MS));
717 if (!ret) {
718 pr_err("%s: wait_event timeout\n", __func__);
719
720 goto fail;
721 }
722 break;
723 }
724 case VSS_MEDIA_ID_AMR_NB_MODEM: {
725 struct cvs_set_amr_enc_rate_cmd cvs_set_amr_rate;
726 struct cvs_set_enc_dtx_mode_cmd cvs_set_dtx;
727
728 pr_debug("Setting AMR rate\n");
729
730 cvs_set_amr_rate.hdr.hdr_field =
731 APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
732 APR_HDR_LEN(APR_HDR_SIZE),
733 APR_PKT_VER);
734 cvs_set_amr_rate.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
735 sizeof(cvs_set_amr_rate) - APR_HDR_SIZE);
736 cvs_set_amr_rate.hdr.src_port = 0;
737 cvs_set_amr_rate.hdr.dest_port = cvs_handle;
738 cvs_set_amr_rate.hdr.token = 0;
739 cvs_set_amr_rate.hdr.opcode =
740 VSS_ISTREAM_CMD_VOC_AMR_SET_ENC_RATE;
741 cvs_set_amr_rate.amr_rate.mode = v->mvs_info.rate;
742
743 v->cvs_state = CMD_STATUS_FAIL;
744
745 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_set_amr_rate);
746 if (ret < 0) {
747 pr_err("%s: Error %d sending SET_AMR_RATE\n",
748 __func__, ret);
749 goto fail;
750 }
751 ret = wait_event_timeout(v->cvs_wait,
752 (v->cvs_state == CMD_STATUS_SUCCESS),
753 msecs_to_jiffies(TIMEOUT_MS));
754 if (!ret) {
755 pr_err("%s: wait_event timeout\n", __func__);
756 goto fail;
757 }
758 /* Disable DTX */
759 pr_debug("Disabling DTX\n");
760
761 cvs_set_dtx.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
762 APR_HDR_LEN(APR_HDR_SIZE),
763 APR_PKT_VER);
764 cvs_set_dtx.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
765 sizeof(cvs_set_dtx) - APR_HDR_SIZE);
766 cvs_set_dtx.hdr.src_port = 0;
767 cvs_set_dtx.hdr.dest_port = cvs_handle;
768 cvs_set_dtx.hdr.token = 0;
769 cvs_set_dtx.hdr.opcode = VSS_ISTREAM_CMD_SET_ENC_DTX_MODE;
770 cvs_set_dtx.dtx_mode.enable = 0;
771
772 v->cvs_state = CMD_STATUS_FAIL;
773
774 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_set_dtx);
775 if (ret < 0) {
776 pr_err("%s: Error %d sending SET_DTX\n",
777 __func__, ret);
778 goto fail;
779 }
780 ret = wait_event_timeout(v->cvs_wait,
781 (v->cvs_state == CMD_STATUS_SUCCESS),
782 msecs_to_jiffies(TIMEOUT_MS));
783 if (!ret) {
784 pr_err("%s: wait_event timeout\n", __func__);
785 goto fail;
786 }
787 break;
788 }
789 case VSS_MEDIA_ID_AMR_WB_MODEM: {
790 struct cvs_set_amrwb_enc_rate_cmd cvs_set_amrwb_rate;
791 struct cvs_set_enc_dtx_mode_cmd cvs_set_dtx;
792
793 pr_debug("Setting AMR WB rate\n");
794
795 cvs_set_amrwb_rate.hdr.hdr_field =
796 APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
797 APR_HDR_LEN(APR_HDR_SIZE),
798 APR_PKT_VER);
799 cvs_set_amrwb_rate.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
800 sizeof(cvs_set_amrwb_rate) -
801 APR_HDR_SIZE);
802 cvs_set_amrwb_rate.hdr.src_port = 0;
803 cvs_set_amrwb_rate.hdr.dest_port = cvs_handle;
804 cvs_set_amrwb_rate.hdr.token = 0;
805 cvs_set_amrwb_rate.hdr.opcode =
806 VSS_ISTREAM_CMD_VOC_AMRWB_SET_ENC_RATE;
807 cvs_set_amrwb_rate.amrwb_rate.mode = v->mvs_info.rate;
808
809 v->cvs_state = CMD_STATUS_FAIL;
810
811 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_set_amrwb_rate);
812 if (ret < 0) {
813 pr_err("%s: Error %d sending SET_AMRWB_RATE\n",
814 __func__, ret);
815 goto fail;
816 }
817 ret = wait_event_timeout(v->cvs_wait,
818 (v->cvs_state == CMD_STATUS_SUCCESS),
819 msecs_to_jiffies(TIMEOUT_MS));
820 if (!ret) {
821 pr_err("%s: wait_event timeout\n", __func__);
822 goto fail;
823 }
824 /* Disable DTX */
825 pr_debug("Disabling DTX\n");
826
827 cvs_set_dtx.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
828 APR_HDR_LEN(APR_HDR_SIZE),
829 APR_PKT_VER);
830 cvs_set_dtx.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
831 sizeof(cvs_set_dtx) - APR_HDR_SIZE);
832 cvs_set_dtx.hdr.src_port = 0;
833 cvs_set_dtx.hdr.dest_port = cvs_handle;
834 cvs_set_dtx.hdr.token = 0;
835 cvs_set_dtx.hdr.opcode = VSS_ISTREAM_CMD_SET_ENC_DTX_MODE;
836 cvs_set_dtx.dtx_mode.enable = 0;
837
838 v->cvs_state = CMD_STATUS_FAIL;
839
840 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_set_dtx);
841 if (ret < 0) {
842 pr_err("%s: Error %d sending SET_DTX\n",
843 __func__, ret);
844 goto fail;
845 }
846 ret = wait_event_timeout(v->cvs_wait,
847 (v->cvs_state == CMD_STATUS_SUCCESS),
848 msecs_to_jiffies(TIMEOUT_MS));
849 if (!ret) {
850 pr_err("%s: wait_event timeout\n", __func__);
851 goto fail;
852 }
853 break;
854 }
855 case VSS_MEDIA_ID_G729:
856 case VSS_MEDIA_ID_G711_ALAW:
857 case VSS_MEDIA_ID_G711_MULAW: {
858 struct cvs_set_enc_dtx_mode_cmd cvs_set_dtx;
859 /* Disable DTX */
860 pr_debug("Disabling DTX\n");
861
862 cvs_set_dtx.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
863 APR_HDR_LEN(APR_HDR_SIZE),
864 APR_PKT_VER);
865 cvs_set_dtx.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
866 sizeof(cvs_set_dtx) - APR_HDR_SIZE);
867 cvs_set_dtx.hdr.src_port = 0;
868 cvs_set_dtx.hdr.dest_port = cvs_handle;
869 cvs_set_dtx.hdr.token = 0;
870 cvs_set_dtx.hdr.opcode = VSS_ISTREAM_CMD_SET_ENC_DTX_MODE;
871 cvs_set_dtx.dtx_mode.enable = 0;
872
873 v->cvs_state = CMD_STATUS_FAIL;
874
875 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_set_dtx);
876 if (ret < 0) {
877 pr_err("%s: Error %d sending SET_DTX\n",
878 __func__, ret);
879 goto fail;
880 }
881 ret = wait_event_timeout(v->cvs_wait,
882 (v->cvs_state == CMD_STATUS_SUCCESS),
883 msecs_to_jiffies(TIMEOUT_MS));
884 if (!ret) {
885 pr_err("%s: wait_event timeout\n", __func__);
886 goto fail;
887 }
888 break;
889 }
890 default:
891 /* Do nothing. */
892 break;
893 }
894 return 0;
895
896fail:
897 return -EINVAL;
898}
899
900static int voice_send_start_voice_cmd(struct voice_data *v)
901{
902 struct apr_hdr mvm_start_voice_cmd;
903 int ret = 0;
904 void *apr_mvm;
905 u16 mvm_handle;
906
907 if (v == NULL) {
908 pr_err("%s: v is NULL\n", __func__);
909 return -EINVAL;
910 }
911 apr_mvm = v->apr_q6_mvm;
912
913 if (!apr_mvm) {
914 pr_err("%s: apr_mvm is NULL.\n", __func__);
915 return -EINVAL;
916 }
917 mvm_handle = voice_get_mvm_handle(v);
918
919 mvm_start_voice_cmd.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
920 APR_HDR_LEN(APR_HDR_SIZE),
921 APR_PKT_VER);
922 mvm_start_voice_cmd.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
923 sizeof(mvm_start_voice_cmd) - APR_HDR_SIZE);
924 pr_debug("send mvm_start_voice_cmd pkt size = %d\n",
925 mvm_start_voice_cmd.pkt_size);
926 mvm_start_voice_cmd.src_port = 0;
927 mvm_start_voice_cmd.dest_port = mvm_handle;
928 mvm_start_voice_cmd.token = 0;
929 mvm_start_voice_cmd.opcode = VSS_IMVM_CMD_START_VOICE;
930
931 v->mvm_state = CMD_STATUS_FAIL;
932 ret = apr_send_pkt(apr_mvm, (uint32_t *) &mvm_start_voice_cmd);
933 if (ret < 0) {
934 pr_err("Fail in sending VSS_IMVM_CMD_START_VOICE\n");
935 goto fail;
936 }
937 ret = wait_event_timeout(v->mvm_wait,
938 (v->mvm_state == CMD_STATUS_SUCCESS),
939 msecs_to_jiffies(TIMEOUT_MS));
940 if (!ret) {
941 pr_err("%s: wait_event timeout\n", __func__);
942 goto fail;
943 }
944 return 0;
945fail:
946 return -EINVAL;
947}
948
949static int voice_send_disable_vocproc_cmd(struct voice_data *v)
950{
951 struct apr_hdr cvp_disable_cmd;
952 int ret = 0;
953 void *apr_cvp;
954 u16 cvp_handle;
955
956 if (v == NULL) {
957 pr_err("%s: v is NULL\n", __func__);
958 return -EINVAL;
959 }
960 apr_cvp = v->apr_q6_cvp;
961
962 if (!apr_cvp) {
963 pr_err("%s: apr regist failed\n", __func__);
964 return -EINVAL;
965 }
966 cvp_handle = voice_get_cvp_handle(v);
967
968 /* disable vocproc and wait for respose */
969 cvp_disable_cmd.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
970 APR_HDR_LEN(APR_HDR_SIZE),
971 APR_PKT_VER);
972 cvp_disable_cmd.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
973 sizeof(cvp_disable_cmd) - APR_HDR_SIZE);
974 pr_debug("cvp_disable_cmd pkt size = %d, cvp_handle=%d\n",
975 cvp_disable_cmd.pkt_size, cvp_handle);
976 cvp_disable_cmd.src_port = 0;
977 cvp_disable_cmd.dest_port = cvp_handle;
978 cvp_disable_cmd.token = 0;
979 cvp_disable_cmd.opcode = VSS_IVOCPROC_CMD_DISABLE;
980
981 v->cvp_state = CMD_STATUS_FAIL;
982 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_disable_cmd);
983 if (ret < 0) {
984 pr_err("Fail in sending VSS_IVOCPROC_CMD_DISABLE\n");
985 goto fail;
986 }
987 ret = wait_event_timeout(v->cvp_wait,
988 (v->cvp_state == CMD_STATUS_SUCCESS),
989 msecs_to_jiffies(TIMEOUT_MS));
990 if (!ret) {
991 pr_err("%s: wait_event timeout\n", __func__);
992 goto fail;
993 }
994
995 return 0;
996fail:
997 return -EINVAL;
998}
999
1000static int voice_send_set_device_cmd(struct voice_data *v)
1001{
1002 struct cvp_set_device_cmd cvp_setdev_cmd;
1003 int ret = 0;
1004 void *apr_cvp;
1005 u16 cvp_handle;
1006
1007 if (v == NULL) {
1008 pr_err("%s: v is NULL\n", __func__);
1009 return -EINVAL;
1010 }
1011 apr_cvp = v->apr_q6_cvp;
1012
1013 if (!apr_cvp) {
1014 pr_err("%s: apr_cvp is NULL.\n", __func__);
1015 return -EINVAL;
1016 }
1017 cvp_handle = voice_get_cvp_handle(v);
1018
1019 /* set device and wait for response */
1020 cvp_setdev_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1021 APR_HDR_LEN(APR_HDR_SIZE),
1022 APR_PKT_VER);
1023 cvp_setdev_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1024 sizeof(cvp_setdev_cmd) - APR_HDR_SIZE);
1025 pr_debug(" send create cvp setdev, pkt size = %d\n",
1026 cvp_setdev_cmd.hdr.pkt_size);
1027 cvp_setdev_cmd.hdr.src_port = 0;
1028 cvp_setdev_cmd.hdr.dest_port = cvp_handle;
1029 cvp_setdev_cmd.hdr.token = 0;
1030 cvp_setdev_cmd.hdr.opcode = VSS_IVOCPROC_CMD_SET_DEVICE;
1031
1032 /* Use default topology if invalid value in ACDB */
1033 cvp_setdev_cmd.cvp_set_device.tx_topology_id =
1034 get_voice_tx_topology();
1035 if (cvp_setdev_cmd.cvp_set_device.tx_topology_id == 0)
1036 cvp_setdev_cmd.cvp_set_device.tx_topology_id =
1037 VSS_IVOCPROC_TOPOLOGY_ID_TX_SM_ECNS;
1038
1039 cvp_setdev_cmd.cvp_set_device.rx_topology_id =
1040 get_voice_rx_topology();
1041 if (cvp_setdev_cmd.cvp_set_device.rx_topology_id == 0)
1042 cvp_setdev_cmd.cvp_set_device.rx_topology_id =
1043 VSS_IVOCPROC_TOPOLOGY_ID_RX_DEFAULT;
1044 cvp_setdev_cmd.cvp_set_device.tx_port_id = v->dev_tx.port_id;
1045 cvp_setdev_cmd.cvp_set_device.rx_port_id = v->dev_rx.port_id;
1046 pr_debug("topology=%d , tx_port_id=%d, rx_port_id=%d\n",
1047 cvp_setdev_cmd.cvp_set_device.tx_topology_id,
1048 cvp_setdev_cmd.cvp_set_device.tx_port_id,
1049 cvp_setdev_cmd.cvp_set_device.rx_port_id);
1050
1051 v->cvp_state = CMD_STATUS_FAIL;
1052 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_setdev_cmd);
1053 if (ret < 0) {
1054 pr_err("Fail in sending VOCPROC_FULL_CONTROL_SESSION\n");
1055 goto fail;
1056 }
1057 pr_debug("wait for cvp create session event\n");
1058 ret = wait_event_timeout(v->cvp_wait,
1059 (v->cvp_state == CMD_STATUS_SUCCESS),
1060 msecs_to_jiffies(TIMEOUT_MS));
1061 if (!ret) {
1062 pr_err("%s: wait_event timeout\n", __func__);
1063 goto fail;
1064 }
1065
1066 return 0;
1067fail:
1068 return -EINVAL;
1069}
1070
1071static int voice_send_stop_voice_cmd(struct voice_data *v)
1072{
1073 struct apr_hdr mvm_stop_voice_cmd;
1074 int ret = 0;
1075 void *apr_mvm;
1076 u16 mvm_handle;
1077
1078 if (v == NULL) {
1079 pr_err("%s: v is NULL\n", __func__);
1080 return -EINVAL;
1081 }
1082 apr_mvm = v->apr_q6_mvm;
1083
1084 if (!apr_mvm) {
1085 pr_err("%s: apr_mvm is NULL.\n", __func__);
1086 return -EINVAL;
1087 }
1088 mvm_handle = voice_get_mvm_handle(v);
1089
1090 mvm_stop_voice_cmd.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1091 APR_HDR_LEN(APR_HDR_SIZE),
1092 APR_PKT_VER);
1093 mvm_stop_voice_cmd.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1094 sizeof(mvm_stop_voice_cmd) - APR_HDR_SIZE);
1095 pr_debug("send mvm_stop_voice_cmd pkt size = %d\n",
1096 mvm_stop_voice_cmd.pkt_size);
1097 mvm_stop_voice_cmd.src_port = 0;
1098 mvm_stop_voice_cmd.dest_port = mvm_handle;
1099 mvm_stop_voice_cmd.token = 0;
1100 mvm_stop_voice_cmd.opcode = VSS_IMVM_CMD_STOP_VOICE;
1101
1102 v->mvm_state = CMD_STATUS_FAIL;
1103 ret = apr_send_pkt(apr_mvm, (uint32_t *) &mvm_stop_voice_cmd);
1104 if (ret < 0) {
1105 pr_err("Fail in sending VSS_IMVM_CMD_STOP_VOICE\n");
1106 goto fail;
1107 }
1108 ret = wait_event_timeout(v->mvm_wait,
1109 (v->mvm_state == CMD_STATUS_SUCCESS),
1110 msecs_to_jiffies(TIMEOUT_MS));
1111 if (!ret) {
1112 pr_err("%s: wait_event timeout\n", __func__);
1113 goto fail;
1114 }
1115
1116 return 0;
1117fail:
1118 return -EINVAL;
1119}
1120
Helen Zeng29eb7442011-06-20 11:06:29 -07001121static int voice_send_cvs_register_cal_cmd(struct voice_data *v)
1122{
1123 struct cvs_register_cal_data_cmd cvs_reg_cal_cmd;
1124 struct acdb_cal_block cal_block;
1125 int ret = 0;
1126 void *apr_cvs;
1127 u16 cvs_handle;
1128
1129 /* get the cvs cal data */
1130 get_all_vocstrm_cal(&cal_block);
1131 if (cal_block.cal_size == 0)
1132 goto fail;
1133
1134 if (v == NULL) {
1135 pr_err("%s: v is NULL\n", __func__);
1136 return -EINVAL;
1137 }
1138 apr_cvs = v->apr_q6_cvs;
1139
1140 if (!apr_cvs) {
1141 pr_err("%s: apr_cvs is NULL.\n", __func__);
1142 return -EINVAL;
1143 }
1144 cvs_handle = voice_get_cvs_handle(v);
1145
1146 /* fill in the header */
1147 cvs_reg_cal_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1148 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
1149 cvs_reg_cal_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1150 sizeof(cvs_reg_cal_cmd) - APR_HDR_SIZE);
1151 cvs_reg_cal_cmd.hdr.src_port = 0;
1152 cvs_reg_cal_cmd.hdr.dest_port = cvs_handle;
1153 cvs_reg_cal_cmd.hdr.token = 0;
1154 cvs_reg_cal_cmd.hdr.opcode = VSS_ISTREAM_CMD_REGISTER_CALIBRATION_DATA;
1155
1156 cvs_reg_cal_cmd.cvs_cal_data.phys_addr = cal_block.cal_paddr;
1157 cvs_reg_cal_cmd.cvs_cal_data.mem_size = cal_block.cal_size;
1158
1159 v->cvs_state = CMD_STATUS_FAIL;
1160 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_reg_cal_cmd);
1161 if (ret < 0) {
1162 pr_err("Fail: sending cvs cal,\n");
1163 goto fail;
1164 }
1165 ret = wait_event_timeout(v->cvs_wait,
1166 (v->cvs_state == CMD_STATUS_SUCCESS),
1167 msecs_to_jiffies(TIMEOUT_MS));
1168 if (!ret) {
1169 pr_err("%s: wait_event timeout\n", __func__);
1170 goto fail;
1171 }
1172 return 0;
1173fail:
1174 return -EINVAL;
1175
1176}
1177
1178static int voice_send_cvs_deregister_cal_cmd(struct voice_data *v)
1179{
1180 struct cvs_deregister_cal_data_cmd cvs_dereg_cal_cmd;
1181 struct acdb_cal_block cal_block;
1182 int ret = 0;
1183 void *apr_cvs;
1184 u16 cvs_handle;
1185
1186 get_all_vocstrm_cal(&cal_block);
1187 if (cal_block.cal_size == 0)
1188 return 0;
1189
1190 if (v == NULL) {
1191 pr_err("%s: v is NULL\n", __func__);
1192 return -EINVAL;
1193 }
1194 apr_cvs = v->apr_q6_cvs;
1195
1196 if (!apr_cvs) {
1197 pr_err("%s: apr_cvs is NULL.\n", __func__);
1198 return -EINVAL;
1199 }
1200 cvs_handle = voice_get_cvs_handle(v);
1201
1202 /* fill in the header */
1203 cvs_dereg_cal_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1204 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
1205 cvs_dereg_cal_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1206 sizeof(cvs_dereg_cal_cmd) - APR_HDR_SIZE);
1207 cvs_dereg_cal_cmd.hdr.src_port = 0;
1208 cvs_dereg_cal_cmd.hdr.dest_port = cvs_handle;
1209 cvs_dereg_cal_cmd.hdr.token = 0;
1210 cvs_dereg_cal_cmd.hdr.opcode =
1211 VSS_ISTREAM_CMD_DEREGISTER_CALIBRATION_DATA;
1212
1213 v->cvs_state = CMD_STATUS_FAIL;
1214 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_dereg_cal_cmd);
1215 if (ret < 0) {
1216 pr_err("Fail: sending cvs cal,\n");
1217 goto fail;
1218 }
1219 ret = wait_event_timeout(v->cvs_wait,
1220 (v->cvs_state == CMD_STATUS_SUCCESS),
1221 msecs_to_jiffies(TIMEOUT_MS));
1222 if (!ret) {
1223 pr_err("%s: wait_event timeout\n", __func__);
1224 goto fail;
1225 }
1226 return 0;
1227fail:
1228 return -EINVAL;
1229
1230}
1231
1232static int voice_send_cvp_map_memory_cmd(struct voice_data *v)
1233{
1234 struct vss_map_memory_cmd cvp_map_mem_cmd;
1235 struct acdb_cal_block cal_block;
1236 int ret = 0;
1237 void *apr_cvp;
1238 u16 cvp_handle;
1239
1240 /* get all cvp cal data */
1241 get_all_cvp_cal(&cal_block);
1242 if (cal_block.cal_size == 0)
1243 goto fail;
1244
1245 if (v == NULL) {
1246 pr_err("%s: v is NULL\n", __func__);
1247 return -EINVAL;
1248 }
1249 apr_cvp = v->apr_q6_cvp;
1250
1251 if (!apr_cvp) {
1252 pr_err("%s: apr_cvp is NULL.\n", __func__);
1253 return -EINVAL;
1254 }
1255 cvp_handle = voice_get_cvp_handle(v);
1256
1257 /* fill in the header */
1258 cvp_map_mem_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1259 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
1260 cvp_map_mem_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1261 sizeof(cvp_map_mem_cmd) - APR_HDR_SIZE);
1262 cvp_map_mem_cmd.hdr.src_port = 0;
1263 cvp_map_mem_cmd.hdr.dest_port = cvp_handle;
1264 cvp_map_mem_cmd.hdr.token = 0;
1265 cvp_map_mem_cmd.hdr.opcode = VSS_ICOMMON_CMD_MAP_MEMORY;
1266
1267 pr_debug("%s, phy_addr:%d, mem_size:%d\n", __func__,
1268 cal_block.cal_paddr, cal_block.cal_size);
1269 cvp_map_mem_cmd.vss_map_mem.phys_addr = cal_block.cal_paddr;
1270 cvp_map_mem_cmd.vss_map_mem.mem_size = cal_block.cal_size;
1271 cvp_map_mem_cmd.vss_map_mem.mem_pool_id =
1272 VSS_ICOMMON_MAP_MEMORY_SHMEM8_4K_POOL;
1273
1274 v->cvp_state = CMD_STATUS_FAIL;
1275 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_map_mem_cmd);
1276 if (ret < 0) {
1277 pr_err("Fail: sending cvp cal,\n");
1278 goto fail;
1279 }
1280 ret = wait_event_timeout(v->cvp_wait,
1281 (v->cvp_state == CMD_STATUS_SUCCESS),
1282 msecs_to_jiffies(TIMEOUT_MS));
1283 if (!ret) {
1284 pr_err("%s: wait_event timeout\n", __func__);
1285 goto fail;
1286 }
1287 return 0;
1288fail:
1289 return -EINVAL;
1290
1291}
1292
1293static int voice_send_cvp_unmap_memory_cmd(struct voice_data *v)
1294{
1295 struct vss_unmap_memory_cmd cvp_unmap_mem_cmd;
1296 struct acdb_cal_block cal_block;
1297 int ret = 0;
1298 void *apr_cvp;
1299 u16 cvp_handle;
1300
1301 get_all_cvp_cal(&cal_block);
1302 if (cal_block.cal_size == 0)
1303 return 0;
1304
1305 if (v == NULL) {
1306 pr_err("%s: v is NULL\n", __func__);
1307 return -EINVAL;
1308 }
1309 apr_cvp = v->apr_q6_cvp;
1310
1311 if (!apr_cvp) {
1312 pr_err("%s: apr_cvp is NULL.\n", __func__);
1313 return -EINVAL;
1314 }
1315 cvp_handle = voice_get_cvp_handle(v);
1316
1317 /* fill in the header */
1318 cvp_unmap_mem_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1319 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
1320 cvp_unmap_mem_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1321 sizeof(cvp_unmap_mem_cmd) - APR_HDR_SIZE);
1322 cvp_unmap_mem_cmd.hdr.src_port = 0;
1323 cvp_unmap_mem_cmd.hdr.dest_port = cvp_handle;
1324 cvp_unmap_mem_cmd.hdr.token = 0;
1325 cvp_unmap_mem_cmd.hdr.opcode = VSS_ICOMMON_CMD_UNMAP_MEMORY;
1326
1327 cvp_unmap_mem_cmd.vss_unmap_mem.phys_addr = cal_block.cal_paddr;
1328
1329 v->cvp_state = CMD_STATUS_FAIL;
1330 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_unmap_mem_cmd);
1331 if (ret < 0) {
1332 pr_err("Fail: sending cvp cal,\n");
1333 goto fail;
1334 }
1335 ret = wait_event_timeout(v->cvp_wait,
1336 (v->cvp_state == CMD_STATUS_SUCCESS),
1337 msecs_to_jiffies(TIMEOUT_MS));
1338 if (!ret) {
1339 pr_err("%s: wait_event timeout\n", __func__);
1340 goto fail;
1341 }
1342 return 0;
1343fail:
1344 return -EINVAL;
1345
1346}
1347
1348static int voice_send_cvs_map_memory_cmd(struct voice_data *v)
1349{
1350 struct vss_map_memory_cmd cvs_map_mem_cmd;
1351 struct acdb_cal_block cal_block;
1352 int ret = 0;
1353 void *apr_cvs;
1354 u16 cvs_handle;
1355
1356 /* get all cvs cal data */
1357 get_all_vocstrm_cal(&cal_block);
1358 if (cal_block.cal_size == 0)
1359 goto fail;
1360
1361 if (v == NULL) {
1362 pr_err("%s: v is NULL\n", __func__);
1363 return -EINVAL;
1364 }
1365 apr_cvs = v->apr_q6_cvs;
1366
1367 if (!apr_cvs) {
1368 pr_err("%s: apr_cvs is NULL.\n", __func__);
1369 return -EINVAL;
1370 }
1371 cvs_handle = voice_get_cvs_handle(v);
1372
1373 /* fill in the header */
1374 cvs_map_mem_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1375 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
1376 cvs_map_mem_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1377 sizeof(cvs_map_mem_cmd) - APR_HDR_SIZE);
1378 cvs_map_mem_cmd.hdr.src_port = 0;
1379 cvs_map_mem_cmd.hdr.dest_port = cvs_handle;
1380 cvs_map_mem_cmd.hdr.token = 0;
1381 cvs_map_mem_cmd.hdr.opcode = VSS_ICOMMON_CMD_MAP_MEMORY;
1382
1383 pr_debug("%s, phys_addr: %d, mem_size: %d\n", __func__,
1384 cal_block.cal_paddr, cal_block.cal_size);
1385 cvs_map_mem_cmd.vss_map_mem.phys_addr = cal_block.cal_paddr;
1386 cvs_map_mem_cmd.vss_map_mem.mem_size = cal_block.cal_size;
1387 cvs_map_mem_cmd.vss_map_mem.mem_pool_id =
1388 VSS_ICOMMON_MAP_MEMORY_SHMEM8_4K_POOL;
1389
1390 v->cvs_state = CMD_STATUS_FAIL;
1391 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_map_mem_cmd);
1392 if (ret < 0) {
1393 pr_err("Fail: sending cvs cal,\n");
1394 goto fail;
1395 }
1396 ret = wait_event_timeout(v->cvs_wait,
1397 (v->cvs_state == CMD_STATUS_SUCCESS),
1398 msecs_to_jiffies(TIMEOUT_MS));
1399 if (!ret) {
1400 pr_err("%s: wait_event timeout\n", __func__);
1401 goto fail;
1402 }
1403 return 0;
1404fail:
1405 return -EINVAL;
1406
1407}
1408
1409static int voice_send_cvs_unmap_memory_cmd(struct voice_data *v)
1410{
1411 struct vss_unmap_memory_cmd cvs_unmap_mem_cmd;
1412 struct acdb_cal_block cal_block;
1413 int ret = 0;
1414 void *apr_cvs;
1415 u16 cvs_handle;
1416
1417 get_all_vocstrm_cal(&cal_block);
1418 if (cal_block.cal_size == 0)
1419 return 0;
1420
1421 if (v == NULL) {
1422 pr_err("%s: v is NULL\n", __func__);
1423 return -EINVAL;
1424 }
1425 apr_cvs = v->apr_q6_cvs;
1426
1427 if (!apr_cvs) {
1428 pr_err("%s: apr_cvs is NULL.\n", __func__);
1429 return -EINVAL;
1430 }
1431 cvs_handle = voice_get_cvs_handle(v);
1432
1433 /* fill in the header */
1434 cvs_unmap_mem_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1435 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
1436 cvs_unmap_mem_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1437 sizeof(cvs_unmap_mem_cmd) - APR_HDR_SIZE);
1438 cvs_unmap_mem_cmd.hdr.src_port = 0;
1439 cvs_unmap_mem_cmd.hdr.dest_port = cvs_handle;
1440 cvs_unmap_mem_cmd.hdr.token = 0;
1441 cvs_unmap_mem_cmd.hdr.opcode = VSS_ICOMMON_CMD_UNMAP_MEMORY;
1442
1443 cvs_unmap_mem_cmd.vss_unmap_mem.phys_addr = cal_block.cal_paddr;
1444
1445 v->cvs_state = CMD_STATUS_FAIL;
1446 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_unmap_mem_cmd);
1447 if (ret < 0) {
1448 pr_err("Fail: sending cvs cal,\n");
1449 goto fail;
1450 }
1451 ret = wait_event_timeout(v->cvs_wait,
1452 (v->cvs_state == CMD_STATUS_SUCCESS),
1453 msecs_to_jiffies(TIMEOUT_MS));
1454 if (!ret) {
1455 pr_err("%s: wait_event timeout\n", __func__);
1456 goto fail;
1457 }
1458 return 0;
1459fail:
1460 return -EINVAL;
1461
1462}
1463
1464static int voice_send_cvp_register_cal_cmd(struct voice_data *v)
1465{
1466 struct cvp_register_cal_data_cmd cvp_reg_cal_cmd;
1467 struct acdb_cal_block cal_block;
1468 int ret = 0;
1469 void *apr_cvp;
1470 u16 cvp_handle;
1471
1472 /* get the cvp cal data */
1473 get_all_vocproc_cal(&cal_block);
1474 if (cal_block.cal_size == 0)
1475 goto fail;
1476
1477 if (v == NULL) {
1478 pr_err("%s: v is NULL\n", __func__);
1479 return -EINVAL;
1480 }
1481 apr_cvp = v->apr_q6_cvp;
1482
1483 if (!apr_cvp) {
1484 pr_err("%s: apr_cvp is NULL.\n", __func__);
1485 return -EINVAL;
1486 }
1487 cvp_handle = voice_get_cvp_handle(v);
1488
1489 /* fill in the header */
1490 cvp_reg_cal_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1491 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
1492 cvp_reg_cal_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1493 sizeof(cvp_reg_cal_cmd) - APR_HDR_SIZE);
1494 cvp_reg_cal_cmd.hdr.src_port = 0;
1495 cvp_reg_cal_cmd.hdr.dest_port = cvp_handle;
1496 cvp_reg_cal_cmd.hdr.token = 0;
1497 cvp_reg_cal_cmd.hdr.opcode = VSS_IVOCPROC_CMD_REGISTER_CALIBRATION_DATA;
1498
1499 cvp_reg_cal_cmd.cvp_cal_data.phys_addr = cal_block.cal_paddr;
1500 cvp_reg_cal_cmd.cvp_cal_data.mem_size = cal_block.cal_size;
1501
1502 v->cvp_state = CMD_STATUS_FAIL;
1503 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_reg_cal_cmd);
1504 if (ret < 0) {
1505 pr_err("Fail: sending cvp cal,\n");
1506 goto fail;
1507 }
1508 ret = wait_event_timeout(v->cvp_wait,
1509 (v->cvp_state == CMD_STATUS_SUCCESS),
1510 msecs_to_jiffies(TIMEOUT_MS));
1511 if (!ret) {
1512 pr_err("%s: wait_event timeout\n", __func__);
1513 goto fail;
1514 }
1515 return 0;
1516fail:
1517 return -EINVAL;
1518
1519}
1520
1521static int voice_send_cvp_deregister_cal_cmd(struct voice_data *v)
1522{
1523 struct cvp_deregister_cal_data_cmd cvp_dereg_cal_cmd;
1524 struct acdb_cal_block cal_block;
1525 int ret = 0;
1526 void *apr_cvp;
1527 u16 cvp_handle;
1528
1529 get_all_vocproc_cal(&cal_block);
1530 if (cal_block.cal_size == 0)
1531 return 0;
1532
1533 if (v == NULL) {
1534 pr_err("%s: v is NULL\n", __func__);
1535 return -EINVAL;
1536 }
1537 apr_cvp = v->apr_q6_cvp;
1538
1539 if (!apr_cvp) {
1540 pr_err("%s: apr_cvp is NULL.\n", __func__);
1541 return -EINVAL;
1542 }
1543 cvp_handle = voice_get_cvp_handle(v);
1544
1545 /* fill in the header */
1546 cvp_dereg_cal_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1547 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
1548 cvp_dereg_cal_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1549 sizeof(cvp_dereg_cal_cmd) - APR_HDR_SIZE);
1550 cvp_dereg_cal_cmd.hdr.src_port = 0;
1551 cvp_dereg_cal_cmd.hdr.dest_port = cvp_handle;
1552 cvp_dereg_cal_cmd.hdr.token = 0;
1553 cvp_dereg_cal_cmd.hdr.opcode =
1554 VSS_IVOCPROC_CMD_DEREGISTER_CALIBRATION_DATA;
1555
1556 v->cvp_state = CMD_STATUS_FAIL;
1557 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_dereg_cal_cmd);
1558 if (ret < 0) {
1559 pr_err("Fail: sending cvp cal,\n");
1560 goto fail;
1561 }
1562 ret = wait_event_timeout(v->cvp_wait,
1563 (v->cvp_state == CMD_STATUS_SUCCESS),
1564 msecs_to_jiffies(TIMEOUT_MS));
1565 if (!ret) {
1566 pr_err("%s: wait_event timeout\n", __func__);
1567 goto fail;
1568 }
1569 return 0;
1570fail:
1571 return -EINVAL;
1572
1573}
1574
1575static int voice_send_cvp_register_vol_cal_table_cmd(struct voice_data *v)
1576{
1577 struct cvp_register_vol_cal_table_cmd cvp_reg_cal_tbl_cmd;
1578 struct acdb_cal_block cal_block;
1579 int ret = 0;
1580 void *apr_cvp;
1581 u16 cvp_handle;
1582
1583 /* get the cvp vol cal data */
1584 get_all_vocvol_cal(&cal_block);
1585 if (cal_block.cal_size == 0)
1586 goto fail;
1587
1588 if (v == NULL) {
1589 pr_err("%s: v is NULL\n", __func__);
1590 return -EINVAL;
1591 }
1592 apr_cvp = v->apr_q6_cvp;
1593
1594 if (!apr_cvp) {
1595 pr_err("%s: apr_cvp is NULL.\n", __func__);
1596 return -EINVAL;
1597 }
1598 cvp_handle = voice_get_cvp_handle(v);
1599
1600 /* fill in the header */
1601 cvp_reg_cal_tbl_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1602 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
1603 cvp_reg_cal_tbl_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1604 sizeof(cvp_reg_cal_tbl_cmd) - APR_HDR_SIZE);
1605 cvp_reg_cal_tbl_cmd.hdr.src_port = 0;
1606 cvp_reg_cal_tbl_cmd.hdr.dest_port = cvp_handle;
1607 cvp_reg_cal_tbl_cmd.hdr.token = 0;
1608 cvp_reg_cal_tbl_cmd.hdr.opcode =
1609 VSS_IVOCPROC_CMD_REGISTER_VOLUME_CAL_TABLE;
1610
1611 cvp_reg_cal_tbl_cmd.cvp_vol_cal_tbl.phys_addr = cal_block.cal_paddr;
1612 cvp_reg_cal_tbl_cmd.cvp_vol_cal_tbl.mem_size = cal_block.cal_size;
1613
1614 v->cvp_state = CMD_STATUS_FAIL;
1615 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_reg_cal_tbl_cmd);
1616 if (ret < 0) {
1617 pr_err("Fail: sending cvp cal table,\n");
1618 goto fail;
1619 }
1620 ret = wait_event_timeout(v->cvp_wait,
1621 (v->cvp_state == CMD_STATUS_SUCCESS),
1622 msecs_to_jiffies(TIMEOUT_MS));
1623 if (!ret) {
1624 pr_err("%s: wait_event timeout\n", __func__);
1625 goto fail;
1626 }
1627 return 0;
1628fail:
1629 return -EINVAL;
1630
1631}
1632
1633static int voice_send_cvp_deregister_vol_cal_table_cmd(struct voice_data *v)
1634{
1635 struct cvp_deregister_vol_cal_table_cmd cvp_dereg_cal_tbl_cmd;
1636 struct acdb_cal_block cal_block;
1637 int ret = 0;
1638 void *apr_cvp;
1639 u16 cvp_handle;
1640
1641 get_all_vocvol_cal(&cal_block);
1642 if (cal_block.cal_size == 0)
1643 return 0;
1644
1645 if (v == NULL) {
1646 pr_err("%s: v is NULL\n", __func__);
1647 return -EINVAL;
1648 }
1649 apr_cvp = v->apr_q6_cvp;
1650
1651 if (!apr_cvp) {
1652 pr_err("%s: apr_cvp is NULL.\n", __func__);
1653 return -EINVAL;
1654 }
1655 cvp_handle = voice_get_cvp_handle(v);
1656
1657 /* fill in the header */
1658 cvp_dereg_cal_tbl_cmd.hdr.hdr_field = APR_HDR_FIELD(
1659 APR_MSG_TYPE_SEQ_CMD,
1660 APR_HDR_LEN(APR_HDR_SIZE),
1661 APR_PKT_VER);
1662 cvp_dereg_cal_tbl_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1663 sizeof(cvp_dereg_cal_tbl_cmd) - APR_HDR_SIZE);
1664 cvp_dereg_cal_tbl_cmd.hdr.src_port = 0;
1665 cvp_dereg_cal_tbl_cmd.hdr.dest_port = cvp_handle;
1666 cvp_dereg_cal_tbl_cmd.hdr.token = 0;
1667 cvp_dereg_cal_tbl_cmd.hdr.opcode =
1668 VSS_IVOCPROC_CMD_DEREGISTER_VOLUME_CAL_TABLE;
1669
1670 v->cvp_state = CMD_STATUS_FAIL;
1671 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_dereg_cal_tbl_cmd);
1672 if (ret < 0) {
1673 pr_err("Fail: sending cvp cal table,\n");
1674 goto fail;
1675 }
1676 ret = wait_event_timeout(v->cvp_wait,
1677 (v->cvp_state == CMD_STATUS_SUCCESS),
1678 msecs_to_jiffies(TIMEOUT_MS));
1679 if (!ret) {
1680 pr_err("%s: wait_event timeout\n", __func__);
1681 goto fail;
1682 }
1683 return 0;
1684fail:
1685 return -EINVAL;
1686
1687}
Helen Zeng44d4d272011-08-10 14:49:20 -07001688static int voice_send_set_widevoice_enable_cmd(struct voice_data *v)
1689{
1690 struct mvm_set_widevoice_enable_cmd mvm_set_wv_cmd;
1691 int ret = 0;
1692 void *apr_mvm;
1693 u16 mvm_handle;
1694
1695 if (v == NULL) {
1696 pr_err("%s: v is NULL\n", __func__);
1697 return -EINVAL;
1698 }
1699 apr_mvm = v->apr_q6_mvm;
1700
1701 if (!apr_mvm) {
1702 pr_err("%s: apr_mvm is NULL.\n", __func__);
1703 return -EINVAL;
1704 }
1705 mvm_handle = voice_get_mvm_handle(v);
1706
1707 /* fill in the header */
1708 mvm_set_wv_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1709 APR_HDR_LEN(APR_HDR_SIZE), APR_PKT_VER);
1710 mvm_set_wv_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1711 sizeof(mvm_set_wv_cmd) - APR_HDR_SIZE);
1712 mvm_set_wv_cmd.hdr.src_port = 0;
1713 mvm_set_wv_cmd.hdr.dest_port = mvm_handle;
1714 mvm_set_wv_cmd.hdr.token = 0;
1715 mvm_set_wv_cmd.hdr.opcode = VSS_IWIDEVOICE_CMD_SET_WIDEVOICE;
1716
1717 mvm_set_wv_cmd.vss_set_wv.enable = v->wv_enable;
1718
1719 v->mvm_state = CMD_STATUS_FAIL;
1720 ret = apr_send_pkt(apr_mvm, (uint32_t *) &mvm_set_wv_cmd);
1721 if (ret < 0) {
1722 pr_err("Fail: sending mvm set widevoice enable,\n");
1723 goto fail;
1724 }
1725 ret = wait_event_timeout(v->mvm_wait,
1726 (v->mvm_state == CMD_STATUS_SUCCESS),
1727 msecs_to_jiffies(TIMEOUT_MS));
1728 if (!ret) {
1729 pr_err("%s: wait_event timeout\n", __func__);
1730 goto fail;
1731 }
1732 return 0;
1733fail:
1734 return -EINVAL;
1735}
1736
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001737static int voice_setup_vocproc(struct voice_data *v)
1738{
1739 struct cvp_create_full_ctl_session_cmd cvp_session_cmd;
1740 int ret = 0;
1741 void *apr_cvp;
1742 if (v == NULL) {
1743 pr_err("%s: v is NULL\n", __func__);
1744 return -EINVAL;
1745 }
1746 apr_cvp = v->apr_q6_cvp;
1747
1748 if (!apr_cvp) {
1749 pr_err("%s: apr_cvp is NULL.\n", __func__);
1750 return -EINVAL;
1751 }
1752
1753 /* create cvp session and wait for response */
1754 cvp_session_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1755 APR_HDR_LEN(APR_HDR_SIZE),
1756 APR_PKT_VER);
1757 cvp_session_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1758 sizeof(cvp_session_cmd) - APR_HDR_SIZE);
1759 pr_debug(" send create cvp session, pkt size = %d\n",
1760 cvp_session_cmd.hdr.pkt_size);
1761 cvp_session_cmd.hdr.src_port = 0;
1762 cvp_session_cmd.hdr.dest_port = 0;
1763 cvp_session_cmd.hdr.token = 0;
1764 cvp_session_cmd.hdr.opcode =
1765 VSS_IVOCPROC_CMD_CREATE_FULL_CONTROL_SESSION;
1766
1767 /* Use default topology if invalid value in ACDB */
1768 cvp_session_cmd.cvp_session.tx_topology_id =
1769 get_voice_tx_topology();
1770 if (cvp_session_cmd.cvp_session.tx_topology_id == 0)
1771 cvp_session_cmd.cvp_session.tx_topology_id =
1772 VSS_IVOCPROC_TOPOLOGY_ID_TX_SM_ECNS;
1773
1774 cvp_session_cmd.cvp_session.rx_topology_id =
1775 get_voice_rx_topology();
1776 if (cvp_session_cmd.cvp_session.rx_topology_id == 0)
1777 cvp_session_cmd.cvp_session.rx_topology_id =
1778 VSS_IVOCPROC_TOPOLOGY_ID_RX_DEFAULT;
1779
1780 cvp_session_cmd.cvp_session.direction = 2; /*tx and rx*/
1781 cvp_session_cmd.cvp_session.network_id = VSS_NETWORK_ID_DEFAULT;
1782 cvp_session_cmd.cvp_session.tx_port_id = v->dev_tx.port_id;
1783 cvp_session_cmd.cvp_session.rx_port_id = v->dev_rx.port_id;
1784
1785 pr_debug("topology=%d net_id=%d, dir=%d tx_port_id=%d, rx_port_id=%d\n",
1786 cvp_session_cmd.cvp_session.tx_topology_id,
1787 cvp_session_cmd.cvp_session.network_id,
1788 cvp_session_cmd.cvp_session.direction,
1789 cvp_session_cmd.cvp_session.tx_port_id,
1790 cvp_session_cmd.cvp_session.rx_port_id);
1791
1792 v->cvp_state = CMD_STATUS_FAIL;
1793 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_session_cmd);
1794 if (ret < 0) {
1795 pr_err("Fail in sending VOCPROC_FULL_CONTROL_SESSION\n");
1796 goto fail;
1797 }
1798 ret = wait_event_timeout(v->cvp_wait,
1799 (v->cvp_state == CMD_STATUS_SUCCESS),
1800 msecs_to_jiffies(TIMEOUT_MS));
1801 if (!ret) {
1802 pr_err("%s: wait_event timeout\n", __func__);
1803 goto fail;
1804 }
1805
Helen Zeng29eb7442011-06-20 11:06:29 -07001806 /* send cvs cal */
1807 ret = voice_send_cvs_map_memory_cmd(v);
1808 if (!ret)
1809 voice_send_cvs_register_cal_cmd(v);
1810
1811 /* send cvp and vol cal */
1812 ret = voice_send_cvp_map_memory_cmd(v);
1813 if (!ret) {
1814 voice_send_cvp_register_cal_cmd(v);
1815 voice_send_cvp_register_vol_cal_table_cmd(v);
1816 }
1817
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001818 /* enable vocproc */
1819 ret = voice_send_enable_vocproc_cmd(v);
1820 if (ret < 0)
1821 goto fail;
1822
1823 /* attach vocproc */
1824 ret = voice_send_attach_vocproc_cmd(v);
1825 if (ret < 0)
1826 goto fail;
1827
1828 /* send tty mode if tty device is used */
1829 voice_send_tty_mode_cmd(v);
1830
Helen Zeng44d4d272011-08-10 14:49:20 -07001831 /* enable widevoice if wv_enable is set */
1832 if (v->wv_enable)
1833 voice_send_set_widevoice_enable_cmd(v);
1834
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001835 if (v->voc_path == VOC_PATH_FULL)
1836 voice_send_netid_timing_cmd(v);
1837
Ben Romberger13b74ab2011-07-18 17:36:32 -07001838 rtac_add_voice(voice_get_cvs_handle(v),
1839 voice_get_cvp_handle(v),
1840 v->dev_rx.port_id, v->dev_tx.port_id);
1841
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07001842 return 0;
1843
1844fail:
1845 return -EINVAL;
1846}
1847
1848static int voice_send_enable_vocproc_cmd(struct voice_data *v)
1849{
1850 int ret = 0;
1851 struct apr_hdr cvp_enable_cmd;
1852 void *apr_cvp;
1853 u16 cvp_handle;
1854
1855 if (v == NULL) {
1856 pr_err("%s: v is NULL\n", __func__);
1857 return -EINVAL;
1858 }
1859 apr_cvp = v->apr_q6_cvp;
1860
1861 if (!apr_cvp) {
1862 pr_err("%s: apr_cvp is NULL.\n", __func__);
1863 return -EINVAL;
1864 }
1865 cvp_handle = voice_get_cvp_handle(v);
1866
1867 /* enable vocproc and wait for respose */
1868 cvp_enable_cmd.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1869 APR_HDR_LEN(APR_HDR_SIZE),
1870 APR_PKT_VER);
1871 cvp_enable_cmd.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1872 sizeof(cvp_enable_cmd) - APR_HDR_SIZE);
1873 pr_debug("cvp_enable_cmd pkt size = %d, cvp_handle=%d\n",
1874 cvp_enable_cmd.pkt_size, cvp_handle);
1875 cvp_enable_cmd.src_port = 0;
1876 cvp_enable_cmd.dest_port = cvp_handle;
1877 cvp_enable_cmd.token = 0;
1878 cvp_enable_cmd.opcode = VSS_IVOCPROC_CMD_ENABLE;
1879
1880 v->cvp_state = CMD_STATUS_FAIL;
1881 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_enable_cmd);
1882 if (ret < 0) {
1883 pr_err("Fail in sending VSS_IVOCPROC_CMD_ENABLE\n");
1884 goto fail;
1885 }
1886 ret = wait_event_timeout(v->cvp_wait,
1887 (v->cvp_state == CMD_STATUS_SUCCESS),
1888 msecs_to_jiffies(TIMEOUT_MS));
1889 if (!ret) {
1890 pr_err("%s: wait_event timeout\n", __func__);
1891 goto fail;
1892 }
1893
1894 return 0;
1895fail:
1896 return -EINVAL;
1897}
1898
1899static int voice_send_netid_timing_cmd(struct voice_data *v)
1900{
1901 int ret = 0;
1902 void *apr_mvm;
1903 u16 mvm_handle;
1904 struct mvm_set_network_cmd mvm_set_network;
1905 struct mvm_set_voice_timing_cmd mvm_set_voice_timing;
1906
1907 if (v == NULL) {
1908 pr_err("%s: v is NULL\n", __func__);
1909 return -EINVAL;
1910 }
1911 apr_mvm = v->apr_q6_mvm;
1912
1913 if (!apr_mvm) {
1914 pr_err("%s: apr_mvm is NULL.\n", __func__);
1915 return -EINVAL;
1916 }
1917 mvm_handle = voice_get_mvm_handle(v);
1918
1919 ret = voice_config_cvs_vocoder(v);
1920 if (ret < 0) {
1921 pr_err("%s: Error %d configuring CVS voc",
1922 __func__, ret);
1923 goto fail;
1924 }
1925 /* Set network ID. */
1926 pr_debug("Setting network ID\n");
1927
1928 mvm_set_network.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1929 APR_HDR_LEN(APR_HDR_SIZE),
1930 APR_PKT_VER);
1931 mvm_set_network.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1932 sizeof(mvm_set_network) - APR_HDR_SIZE);
1933 mvm_set_network.hdr.src_port = 0;
1934 mvm_set_network.hdr.dest_port = mvm_handle;
1935 mvm_set_network.hdr.token = 0;
1936 mvm_set_network.hdr.opcode = VSS_ICOMMON_CMD_SET_NETWORK;
1937 mvm_set_network.network.network_id = v->mvs_info.network_type;
1938
1939 v->mvm_state = CMD_STATUS_FAIL;
1940 ret = apr_send_pkt(apr_mvm, (uint32_t *) &mvm_set_network);
1941 if (ret < 0) {
1942 pr_err("%s: Error %d sending SET_NETWORK\n", __func__, ret);
1943 goto fail;
1944 }
1945
1946 ret = wait_event_timeout(v->mvm_wait,
1947 (v->mvm_state == CMD_STATUS_SUCCESS),
1948 msecs_to_jiffies(TIMEOUT_MS));
1949 if (!ret) {
1950 pr_err("%s: wait_event timeout\n", __func__);
1951 goto fail;
1952 }
1953
1954 /* Set voice timing. */
1955 pr_debug("Setting voice timing\n");
1956
1957 mvm_set_voice_timing.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
1958 APR_HDR_LEN(APR_HDR_SIZE),
1959 APR_PKT_VER);
1960 mvm_set_voice_timing.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
1961 sizeof(mvm_set_voice_timing) -
1962 APR_HDR_SIZE);
1963 mvm_set_voice_timing.hdr.src_port = 0;
1964 mvm_set_voice_timing.hdr.dest_port = mvm_handle;
1965 mvm_set_voice_timing.hdr.token = 0;
1966 mvm_set_voice_timing.hdr.opcode = VSS_ICOMMON_CMD_SET_VOICE_TIMING;
1967 mvm_set_voice_timing.timing.mode = 0;
1968 mvm_set_voice_timing.timing.enc_offset = 8000;
1969 mvm_set_voice_timing.timing.dec_req_offset = 3300;
1970 mvm_set_voice_timing.timing.dec_offset = 8300;
1971
1972 v->mvm_state = CMD_STATUS_FAIL;
1973
1974 ret = apr_send_pkt(apr_mvm, (uint32_t *) &mvm_set_voice_timing);
1975 if (ret < 0) {
1976 pr_err("%s: Error %d sending SET_TIMING\n", __func__, ret);
1977 goto fail;
1978 }
1979
1980 ret = wait_event_timeout(v->mvm_wait,
1981 (v->mvm_state == CMD_STATUS_SUCCESS),
1982 msecs_to_jiffies(TIMEOUT_MS));
1983 if (!ret) {
1984 pr_err("%s: wait_event timeout\n", __func__);
1985 goto fail;
1986 }
1987
1988 return 0;
1989fail:
1990 return -EINVAL;
1991}
1992
1993static int voice_send_attach_vocproc_cmd(struct voice_data *v)
1994{
1995 int ret = 0;
1996 struct mvm_attach_vocproc_cmd mvm_a_vocproc_cmd;
1997 void *apr_mvm;
1998 u16 mvm_handle, cvp_handle;
1999
2000 if (v == NULL) {
2001 pr_err("%s: v is NULL\n", __func__);
2002 return -EINVAL;
2003 }
2004 apr_mvm = v->apr_q6_mvm;
2005
2006 if (!apr_mvm) {
2007 pr_err("%s: apr_mvm is NULL.\n", __func__);
2008 return -EINVAL;
2009 }
2010 mvm_handle = voice_get_mvm_handle(v);
2011 cvp_handle = voice_get_cvp_handle(v);
2012
2013 /* attach vocproc and wait for response */
2014 mvm_a_vocproc_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
2015 APR_HDR_LEN(APR_HDR_SIZE),
2016 APR_PKT_VER);
2017 mvm_a_vocproc_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
2018 sizeof(mvm_a_vocproc_cmd) - APR_HDR_SIZE);
2019 pr_debug("send mvm_a_vocproc_cmd pkt size = %d\n",
2020 mvm_a_vocproc_cmd.hdr.pkt_size);
2021 mvm_a_vocproc_cmd.hdr.src_port = 0;
2022 mvm_a_vocproc_cmd.hdr.dest_port = mvm_handle;
2023 mvm_a_vocproc_cmd.hdr.token = 0;
Helen Zeng69b00962011-07-08 11:38:36 -07002024 mvm_a_vocproc_cmd.hdr.opcode = VSS_IMVM_CMD_ATTACH_VOCPROC;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002025 mvm_a_vocproc_cmd.mvm_attach_cvp_handle.handle = cvp_handle;
2026
2027 v->mvm_state = CMD_STATUS_FAIL;
2028 ret = apr_send_pkt(apr_mvm, (uint32_t *) &mvm_a_vocproc_cmd);
2029 if (ret < 0) {
Helen Zeng69b00962011-07-08 11:38:36 -07002030 pr_err("Fail in sending VSS_IMVM_CMD_ATTACH_VOCPROC\n");
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002031 goto fail;
2032 }
2033 ret = wait_event_timeout(v->mvm_wait,
2034 (v->mvm_state == CMD_STATUS_SUCCESS),
2035 msecs_to_jiffies(TIMEOUT_MS));
2036 if (!ret) {
2037 pr_err("%s: wait_event timeout\n", __func__);
2038 goto fail;
2039 }
2040
2041 return 0;
2042fail:
2043 return -EINVAL;
2044}
2045
2046static int voice_destroy_vocproc(struct voice_data *v)
2047{
2048 struct mvm_detach_vocproc_cmd mvm_d_vocproc_cmd;
2049 struct apr_hdr cvp_destroy_session_cmd;
2050 int ret = 0;
2051 void *apr_mvm, *apr_cvp;
2052 u16 mvm_handle, cvp_handle;
2053
2054 if (v == NULL) {
2055 pr_err("%s: v is NULL\n", __func__);
2056 return -EINVAL;
2057 }
2058 apr_mvm = v->apr_q6_mvm;
2059 apr_cvp = v->apr_q6_cvp;
2060
2061 if (!apr_mvm || !apr_cvp) {
2062 pr_err("%s: apr_mvm or apr_cvp is NULL.\n", __func__);
2063 return -EINVAL;
2064 }
2065 mvm_handle = voice_get_mvm_handle(v);
2066 cvp_handle = voice_get_cvp_handle(v);
2067
2068 /* send stop voice cmd */
2069 voice_send_stop_voice_cmd(v);
2070
2071 /* detach VOCPROC and wait for response from mvm */
2072 mvm_d_vocproc_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
2073 APR_HDR_LEN(APR_HDR_SIZE),
2074 APR_PKT_VER);
2075 mvm_d_vocproc_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
2076 sizeof(mvm_d_vocproc_cmd) - APR_HDR_SIZE);
2077 pr_debug("mvm_d_vocproc_cmd pkt size = %d\n",
2078 mvm_d_vocproc_cmd.hdr.pkt_size);
2079 mvm_d_vocproc_cmd.hdr.src_port = 0;
2080 mvm_d_vocproc_cmd.hdr.dest_port = mvm_handle;
2081 mvm_d_vocproc_cmd.hdr.token = 0;
Helen Zeng69b00962011-07-08 11:38:36 -07002082 mvm_d_vocproc_cmd.hdr.opcode = VSS_IMVM_CMD_DETACH_VOCPROC;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002083 mvm_d_vocproc_cmd.mvm_detach_cvp_handle.handle = cvp_handle;
2084
2085 v->mvm_state = CMD_STATUS_FAIL;
2086 ret = apr_send_pkt(apr_mvm, (uint32_t *) &mvm_d_vocproc_cmd);
2087 if (ret < 0) {
Helen Zeng69b00962011-07-08 11:38:36 -07002088 pr_err("Fail in sending VSS_IMVM_CMD_DETACH_VOCPROC\n");
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002089 goto fail;
2090 }
2091 ret = wait_event_timeout(v->mvm_wait,
2092 (v->mvm_state == CMD_STATUS_SUCCESS),
2093 msecs_to_jiffies(TIMEOUT_MS));
2094 if (!ret) {
2095 pr_err("%s: wait_event timeout\n", __func__);
2096 goto fail;
2097 }
2098
Helen Zeng29eb7442011-06-20 11:06:29 -07002099 /* deregister cvp and vol cal */
2100 voice_send_cvp_deregister_vol_cal_table_cmd(v);
2101 voice_send_cvp_deregister_cal_cmd(v);
2102 voice_send_cvp_unmap_memory_cmd(v);
2103
2104 /* deregister cvs cal */
2105 voice_send_cvs_deregister_cal_cmd(v);
2106 voice_send_cvs_unmap_memory_cmd(v);
2107
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002108 /* destrop cvp session */
2109 cvp_destroy_session_cmd.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
2110 APR_HDR_LEN(APR_HDR_SIZE),
2111 APR_PKT_VER);
2112 cvp_destroy_session_cmd.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
2113 sizeof(cvp_destroy_session_cmd) - APR_HDR_SIZE);
2114 pr_debug("cvp_destroy_session_cmd pkt size = %d\n",
2115 cvp_destroy_session_cmd.pkt_size);
2116 cvp_destroy_session_cmd.src_port = 0;
2117 cvp_destroy_session_cmd.dest_port = cvp_handle;
2118 cvp_destroy_session_cmd.token = 0;
2119 cvp_destroy_session_cmd.opcode = APRV2_IBASIC_CMD_DESTROY_SESSION;
2120
2121 v->cvp_state = CMD_STATUS_FAIL;
2122 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_destroy_session_cmd);
2123 if (ret < 0) {
2124 pr_err("Fail in sending APRV2_IBASIC_CMD_DESTROY_SESSION\n");
2125 goto fail;
2126 }
2127 ret = wait_event_timeout(v->cvp_wait,
2128 (v->cvp_state == CMD_STATUS_SUCCESS),
2129 msecs_to_jiffies(TIMEOUT_MS));
2130 if (!ret) {
2131 pr_err("%s: wait_event timeout\n", __func__);
2132 goto fail;
2133 }
2134
Ben Romberger13b74ab2011-07-18 17:36:32 -07002135 rtac_remove_voice(voice_get_cvs_handle(v));
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002136 cvp_handle = 0;
2137 voice_set_cvp_handle(v, cvp_handle);
2138
2139 return 0;
2140
2141fail:
2142 return -EINVAL;
2143}
2144
2145static int voice_send_mute_cmd(struct voice_data *v)
2146{
2147 struct cvs_set_mute_cmd cvs_mute_cmd;
2148 int ret = 0;
2149 void *apr_cvs;
2150 u16 cvs_handle;
2151
2152 if (v == NULL) {
2153 pr_err("%s: v is NULL\n", __func__);
2154 return -EINVAL;
2155 }
2156 apr_cvs = v->apr_q6_cvs;
2157
2158 if (!apr_cvs) {
2159 pr_err("%s: apr_cvs is NULL.\n", __func__);
2160 return -EINVAL;
2161 }
2162 cvs_handle = voice_get_cvs_handle(v);
2163
2164 /* send mute/unmute to cvs */
2165 cvs_mute_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
2166 APR_HDR_LEN(APR_HDR_SIZE),
2167 APR_PKT_VER);
2168 cvs_mute_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
2169 sizeof(cvs_mute_cmd) - APR_HDR_SIZE);
2170 cvs_mute_cmd.hdr.src_port = 0;
2171 cvs_mute_cmd.hdr.dest_port = cvs_handle;
2172 cvs_mute_cmd.hdr.token = 0;
2173 cvs_mute_cmd.hdr.opcode = VSS_ISTREAM_CMD_SET_MUTE;
2174 cvs_mute_cmd.cvs_set_mute.direction = 0; /*tx*/
2175 cvs_mute_cmd.cvs_set_mute.mute_flag = v->dev_tx.mute;
2176
2177 pr_info(" mute value =%d\n", cvs_mute_cmd.cvs_set_mute.mute_flag);
2178 v->cvs_state = CMD_STATUS_FAIL;
2179 ret = apr_send_pkt(apr_cvs, (uint32_t *) &cvs_mute_cmd);
2180 if (ret < 0) {
2181 pr_err("Fail: send STREAM SET MUTE\n");
2182 goto fail;
2183 }
2184 ret = wait_event_timeout(v->cvs_wait,
2185 (v->cvs_state == CMD_STATUS_SUCCESS),
2186 msecs_to_jiffies(TIMEOUT_MS));
2187 if (!ret)
2188 pr_err("%s: wait_event timeout\n", __func__);
2189
2190 return 0;
2191fail:
2192 return -EINVAL;
2193}
2194
2195static int voice_send_vol_index_cmd(struct voice_data *v)
2196{
2197 struct cvp_set_rx_volume_index_cmd cvp_vol_cmd;
2198 int ret = 0;
2199 void *apr_cvp;
2200 u16 cvp_handle;
2201 if (v == NULL) {
2202 pr_err("%s: v is NULL\n", __func__);
2203 return -EINVAL;
2204 }
2205 apr_cvp = v->apr_q6_cvp;
2206
2207 if (!apr_cvp) {
2208 pr_err("%s: apr_cvp is NULL.\n", __func__);
2209 return -EINVAL;
2210 }
2211 cvp_handle = voice_get_cvp_handle(v);
2212
2213 /* send volume index to cvp */
2214 cvp_vol_cmd.hdr.hdr_field = APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
2215 APR_HDR_LEN(APR_HDR_SIZE),
2216 APR_PKT_VER);
2217 cvp_vol_cmd.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
2218 sizeof(cvp_vol_cmd) - APR_HDR_SIZE);
2219 cvp_vol_cmd.hdr.src_port = 0;
2220 cvp_vol_cmd.hdr.dest_port = cvp_handle;
2221 cvp_vol_cmd.hdr.token = 0;
2222 cvp_vol_cmd.hdr.opcode = VSS_IVOCPROC_CMD_SET_RX_VOLUME_INDEX;
2223 cvp_vol_cmd.cvp_set_vol_idx.vol_index = v->dev_rx.volume;
2224 v->cvp_state = CMD_STATUS_FAIL;
2225 ret = apr_send_pkt(apr_cvp, (uint32_t *) &cvp_vol_cmd);
2226 if (ret < 0) {
2227 pr_err("Fail in sending RX VOL INDEX\n");
2228 return -EINVAL;
2229 }
2230 ret = wait_event_timeout(v->cvp_wait,
2231 (v->cvp_state == CMD_STATUS_SUCCESS),
2232 msecs_to_jiffies(TIMEOUT_MS));
2233 if (!ret) {
2234 pr_err("%s: wait_event timeout\n", __func__);
2235 return -EINVAL;
2236 }
2237 return 0;
2238}
2239
2240int voc_disable_cvp(void)
2241{
2242 struct voice_data *v = &voice;
2243 int ret = 0;
2244
2245 mutex_lock(&v->lock);
2246
2247 if (v->voc_state == VOC_RUN) {
2248 afe_sidetone(v->dev_tx.port_id, v->dev_rx.port_id, 0, 0);
Ben Romberger13b74ab2011-07-18 17:36:32 -07002249
2250 rtac_remove_voice(voice_get_cvs_handle(v));
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002251 /* send cmd to dsp to disable vocproc */
2252 ret = voice_send_disable_vocproc_cmd(v);
2253 if (ret < 0) {
2254 pr_err("%s: disable vocproc failed\n", __func__);
2255 goto fail;
2256 }
Helen Zeng29eb7442011-06-20 11:06:29 -07002257
2258 /* deregister cvp and vol cal */
2259 voice_send_cvp_deregister_vol_cal_table_cmd(v);
2260 voice_send_cvp_deregister_cal_cmd(v);
2261 voice_send_cvp_unmap_memory_cmd(v);
2262
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002263 v->voc_state = VOC_CHANGE;
2264 }
2265
2266fail: mutex_unlock(&v->lock);
2267
2268 return ret;
2269}
2270
2271int voc_enable_cvp(void)
2272{
2273 struct voice_data *v = &voice;
Helen Zengbd58e2c2011-07-01 16:24:31 -07002274 struct sidetone_cal sidetone_cal_data;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002275 int ret = 0;
2276
2277 mutex_lock(&v->lock);
2278
2279 if (v->voc_state == VOC_CHANGE) {
2280 ret = voice_send_set_device_cmd(v);
2281 if (ret < 0) {
2282 pr_err("%s: set device failed\n", __func__);
2283 goto fail;
2284 }
Helen Zeng29eb7442011-06-20 11:06:29 -07002285 /* send cvp and vol cal */
2286 ret = voice_send_cvp_map_memory_cmd(v);
2287 if (!ret) {
2288 voice_send_cvp_register_cal_cmd(v);
2289 voice_send_cvp_register_vol_cal_table_cmd(v);
2290 }
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002291 ret = voice_send_enable_vocproc_cmd(v);
2292 if (ret < 0) {
2293 pr_err("enable vocproc failed\n");
2294 goto fail;
Helen Zengcc65b5b2011-07-06 19:14:48 -07002295
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002296 }
Helen Zengcc65b5b2011-07-06 19:14:48 -07002297 /* send tty mode if tty device is used */
2298 voice_send_tty_mode_cmd(v);
2299
Helen Zeng44d4d272011-08-10 14:49:20 -07002300 /* enable widevoice if wv_enable is set */
2301 if (v->wv_enable)
2302 voice_send_set_widevoice_enable_cmd(v);
2303
Helen Zengbd58e2c2011-07-01 16:24:31 -07002304 get_sidetone_cal(&sidetone_cal_data);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002305 ret = afe_sidetone(v->dev_tx.port_id, v->dev_rx.port_id,
Helen Zengbd58e2c2011-07-01 16:24:31 -07002306 sidetone_cal_data.enable,
2307 sidetone_cal_data.gain);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002308
2309 if (ret < 0)
2310 pr_err("AFE command sidetone failed\n");
2311
Ben Romberger13b74ab2011-07-18 17:36:32 -07002312 rtac_add_voice(voice_get_cvs_handle(v),
2313 voice_get_cvp_handle(v),
2314 v->dev_rx.port_id, v->dev_tx.port_id);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002315 v->voc_state = VOC_RUN;
2316 }
2317
2318fail:
2319 mutex_unlock(&v->lock);
2320
2321 return ret;
2322}
2323
2324int voc_set_tx_mute(uint32_t dir, uint32_t mute)
2325{
2326 struct voice_data *v = &voice;
2327 int ret = 0;
2328
2329 mutex_lock(&v->lock);
2330
2331 v->dev_tx.mute = mute;
2332
2333 if (v->voc_state == VOC_RUN)
2334 ret = voice_send_mute_cmd(v);
2335
2336 mutex_unlock(&v->lock);
2337
2338 return ret;
2339}
2340
Helen Zengcc65b5b2011-07-06 19:14:48 -07002341int voc_set_tty_mode(uint8_t tty_mode)
2342{
2343 struct voice_data *v = &voice;
2344 int ret = 0;
2345
2346 mutex_lock(&v->lock);
2347
2348 v->tty_mode = tty_mode;
2349
2350 mutex_unlock(&v->lock);
2351
2352 return ret;
2353}
2354
2355uint8_t voc_get_tty_mode(void)
2356{
2357 struct voice_data *v = &voice;
2358 int ret = 0;
2359
2360 mutex_lock(&v->lock);
2361
2362 ret = v->tty_mode;
2363
2364 mutex_unlock(&v->lock);
2365
2366 return ret;
2367}
2368
Helen Zeng44d4d272011-08-10 14:49:20 -07002369int voc_set_widevoice_enable(uint32_t wv_enable)
2370{
2371 struct voice_data *v = &voice;
2372 int ret = 0;
2373
2374 mutex_lock(&v->lock);
2375
2376 v->wv_enable = wv_enable;
2377
2378 mutex_unlock(&v->lock);
2379
2380 return ret;
2381}
2382
2383uint32_t voc_get_widevoice_enable(void)
2384{
2385 struct voice_data *v = &voice;
2386 int ret = 0;
2387
2388 mutex_lock(&v->lock);
2389
2390 ret = v->wv_enable;
2391
2392 mutex_unlock(&v->lock);
2393
2394 return ret;
2395}
2396
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002397int voc_set_rx_vol_index(uint32_t dir, uint32_t vol_idx)
2398{
2399 struct voice_data *v = &voice;
2400 int ret = 0;
2401
2402 mutex_lock(&v->lock);
2403
2404 v->dev_rx.volume = vol_idx;
2405
2406 if (v->voc_state == VOC_RUN)
2407 ret = voice_send_vol_index_cmd(v);
2408
2409 mutex_unlock(&v->lock);
2410
2411 return ret;
2412}
2413
2414void voc_set_rxtx_port(uint32_t port_id, uint32_t dev_type)
2415{
2416 struct voice_data *v = &voice;
2417
2418 pr_debug(" port_id=%d, type=%d\n", port_id, dev_type);
2419
2420 mutex_lock(&v->lock);
2421
2422 if (dev_type == DEV_RX)
2423 v->dev_rx.port_id = port_id;
2424 else
2425 v->dev_tx.port_id = port_id;
2426
2427 mutex_unlock(&v->lock);
2428
2429 return;
2430}
2431
2432void voc_set_route_flag(uint8_t path_dir, uint8_t set)
2433{
2434 struct voice_data *v = &voice;
2435
2436 pr_debug("path_dir=%d, set=%d\n", path_dir, set);
2437
2438 mutex_lock(&v->lock);
2439
2440 if (path_dir == RX_PATH)
2441 v->voc_route_state.rx_route_flag = set;
2442 else
2443 v->voc_route_state.tx_route_flag = set;
2444
2445 mutex_unlock(&v->lock);
2446
2447 return;
2448}
2449
2450uint8_t voc_get_route_flag(uint8_t path_dir)
2451{
2452 struct voice_data *v = &voice;
2453 int ret = 0;
2454
2455 mutex_lock(&v->lock);
2456
2457 if (path_dir == RX_PATH)
2458 ret = v->voc_route_state.rx_route_flag;
2459 else
2460 ret = v->voc_route_state.tx_route_flag;
2461
2462 mutex_unlock(&v->lock);
2463
2464 return ret;
2465}
2466
2467int voc_end_voice_call(void)
2468{
2469 struct voice_data *v = &voice;
2470 int ret = 0;
2471
2472 mutex_lock(&v->lock);
2473
2474 if (v->voc_state == VOC_RUN) {
Helen Zengbd58e2c2011-07-01 16:24:31 -07002475 afe_sidetone(v->dev_tx.port_id, v->dev_rx.port_id, 0, 0);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002476 ret = voice_destroy_vocproc(v);
2477 if (ret < 0)
2478 pr_err("%s: destroy voice failed\n", __func__);
2479 voice_destroy_mvm_cvs_session(v);
2480
2481 v->voc_state = VOC_RELEASE;
2482 }
2483 mutex_unlock(&v->lock);
2484 return ret;
2485}
2486
2487int voc_start_voice_call(void)
2488{
2489 struct voice_data *v = &voice;
Helen Zengbd58e2c2011-07-01 16:24:31 -07002490 struct sidetone_cal sidetone_cal_data;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002491 int ret = 0;
2492
2493 mutex_lock(&v->lock);
2494
2495 if ((v->voc_state == VOC_INIT) ||
2496 (v->voc_state == VOC_RELEASE)) {
2497 ret = voice_apr_register(v);
2498 if (ret < 0) {
2499 pr_err("%s: apr register failed\n", __func__);
2500 goto fail;
2501 }
2502 ret = voice_create_mvm_cvs_session(v);
2503 if (ret < 0) {
2504 pr_err("create mvm and cvs failed\n");
2505 goto fail;
2506 }
2507 ret = voice_setup_vocproc(v);
2508 if (ret < 0) {
2509 pr_err("setup voice failed\n");
2510 goto fail;
2511 }
2512 ret = voice_send_start_voice_cmd(v);
2513 if (ret < 0) {
2514 pr_err("start voice failed\n");
2515 goto fail;
2516 }
Helen Zengbd58e2c2011-07-01 16:24:31 -07002517 get_sidetone_cal(&sidetone_cal_data);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002518 ret = afe_sidetone(v->dev_tx.port_id,
Helen Zengbd58e2c2011-07-01 16:24:31 -07002519 v->dev_rx.port_id,
2520 sidetone_cal_data.enable,
2521 sidetone_cal_data.gain);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002522 if (ret < 0)
2523 pr_err("AFE command sidetone failed\n");
2524
2525 v->voc_state = VOC_RUN;
2526 }
2527
2528fail: mutex_unlock(&v->lock);
2529 return ret;
2530}
2531
2532int voc_set_voc_path_full(uint32_t set)
2533{
2534 int rc = 0;
2535
2536 pr_debug("set voc path: %d\n", set);
2537
2538 mutex_lock(&voice.lock);
2539
2540 if (voice.voc_state == VOC_INIT || voice.voc_state == VOC_RELEASE) {
2541 if (set)
2542 voice.voc_path = VOC_PATH_FULL;
2543 else
2544 voice.voc_path = VOC_PATH_PASSIVE;
2545 } else {
2546 pr_err("%s: Invalid voc path set to %d, in state %d\n",
2547 __func__, set, voice.voc_state);
2548 rc = -EPERM;
2549 }
2550
2551 mutex_unlock(&voice.lock);
2552
2553 return rc;
2554}
2555EXPORT_SYMBOL(voc_set_voc_path_full);
2556
2557void voc_register_mvs_cb(ul_cb_fn ul_cb,
2558 dl_cb_fn dl_cb,
2559 void *private_data)
2560{
2561 voice.mvs_info.ul_cb = ul_cb;
2562 voice.mvs_info.dl_cb = dl_cb;
2563 voice.mvs_info.private_data = private_data;
2564}
2565
2566void voc_config_vocoder(uint32_t media_type,
2567 uint32_t rate,
2568 uint32_t network_type)
2569{
2570 voice.mvs_info.media_type = media_type;
2571 voice.mvs_info.rate = rate;
2572 voice.mvs_info.network_type = network_type;
2573}
2574
2575static int32_t qdsp_mvm_callback(struct apr_client_data *data, void *priv)
2576{
2577 uint32_t *ptr;
2578 struct voice_data *v;
2579
2580 if ((data == NULL) || (priv == NULL)) {
2581 pr_err("%s: data or priv is NULL\n", __func__);
2582 return -EINVAL;
2583 }
2584 v = priv;
2585
2586 pr_debug("%s: Payload Length = %d, opcode=%x\n", __func__,
2587 data->payload_size, data->opcode);
2588
2589 if (data->opcode == APR_BASIC_RSP_RESULT) {
2590 if (data->payload_size) {
2591 ptr = data->payload;
2592
2593 pr_info("%x %x\n", ptr[0], ptr[1]);
2594 /* ping mvm service ACK */
2595 switch (ptr[0]) {
2596 case VSS_IMVM_CMD_CREATE_PASSIVE_CONTROL_SESSION:
2597 case VSS_IMVM_CMD_CREATE_FULL_CONTROL_SESSION:
2598 /* Passive session is used for CS call
2599 * Full session is used for VoIP call. */
2600 pr_debug("%s: cmd = 0x%x\n", __func__, ptr[0]);
2601 if (!ptr[1]) {
2602 pr_debug("%s: MVM handle is %d\n",
2603 __func__, data->src_port);
2604 voice_set_mvm_handle(v, data->src_port);
2605 } else
2606 pr_err("got NACK for sending \
2607 MVM create session \n");
2608 v->mvm_state = CMD_STATUS_SUCCESS;
2609 wake_up(&v->mvm_wait);
2610 break;
2611 case VSS_IMVM_CMD_START_VOICE:
Helen Zeng69b00962011-07-08 11:38:36 -07002612 case VSS_IMVM_CMD_ATTACH_VOCPROC:
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002613 case VSS_IMVM_CMD_STOP_VOICE:
Helen Zeng69b00962011-07-08 11:38:36 -07002614 case VSS_IMVM_CMD_DETACH_VOCPROC:
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002615 case VSS_ISTREAM_CMD_SET_TTY_MODE:
2616 case APRV2_IBASIC_CMD_DESTROY_SESSION:
2617 case VSS_IMVM_CMD_ATTACH_STREAM:
2618 case VSS_IMVM_CMD_DETACH_STREAM:
2619 case VSS_ICOMMON_CMD_SET_NETWORK:
2620 case VSS_ICOMMON_CMD_SET_VOICE_TIMING:
Helen Zeng44d4d272011-08-10 14:49:20 -07002621 case VSS_IWIDEVOICE_CMD_SET_WIDEVOICE:
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002622 pr_debug("%s: cmd = 0x%x\n", __func__, ptr[0]);
2623 v->mvm_state = CMD_STATUS_SUCCESS;
2624 wake_up(&v->mvm_wait);
2625 break;
2626 default:
2627 pr_debug("%s: not match cmd = 0x%x\n",
2628 __func__, ptr[0]);
2629 break;
2630 }
2631 }
2632 }
2633
2634 return 0;
2635}
2636
2637static int32_t qdsp_cvs_callback(struct apr_client_data *data, void *priv)
2638{
2639 uint32_t *ptr;
2640 struct voice_data *v;
2641
2642 if ((data == NULL) || (priv == NULL)) {
2643 pr_err("%s: data or priv is NULL\n", __func__);
2644 return -EINVAL;
2645 }
2646 v = priv;
2647
2648 pr_debug("%s: Payload Length = %d, opcode=%x\n", __func__,
2649 data->payload_size, data->opcode);
2650
2651 if (data->opcode == APR_BASIC_RSP_RESULT) {
2652 if (data->payload_size) {
2653 ptr = data->payload;
2654
2655 pr_info("%x %x\n", ptr[0], ptr[1]);
2656 /*response from CVS */
2657 switch (ptr[0]) {
2658 case VSS_ISTREAM_CMD_CREATE_PASSIVE_CONTROL_SESSION:
2659 case VSS_ISTREAM_CMD_CREATE_FULL_CONTROL_SESSION:
2660 if (!ptr[1]) {
2661 pr_debug("%s: CVS handle is %d\n",
2662 __func__, data->src_port);
2663 voice_set_cvs_handle(v, data->src_port);
2664 } else
2665 pr_err("got NACK for sending \
2666 CVS create session \n");
2667 v->cvs_state = CMD_STATUS_SUCCESS;
2668 wake_up(&v->cvs_wait);
2669 break;
2670 case VSS_ISTREAM_CMD_SET_MUTE:
2671 case VSS_ISTREAM_CMD_SET_MEDIA_TYPE:
2672 case VSS_ISTREAM_CMD_VOC_AMR_SET_ENC_RATE:
2673 case VSS_ISTREAM_CMD_VOC_AMRWB_SET_ENC_RATE:
2674 case VSS_ISTREAM_CMD_SET_ENC_DTX_MODE:
2675 case VSS_ISTREAM_CMD_CDMA_SET_ENC_MINMAX_RATE:
2676 case APRV2_IBASIC_CMD_DESTROY_SESSION:
Helen Zeng29eb7442011-06-20 11:06:29 -07002677 case VSS_ISTREAM_CMD_REGISTER_CALIBRATION_DATA:
2678 case VSS_ISTREAM_CMD_DEREGISTER_CALIBRATION_DATA:
2679 case VSS_ICOMMON_CMD_MAP_MEMORY:
2680 case VSS_ICOMMON_CMD_UNMAP_MEMORY:
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002681 pr_debug("%s: cmd = 0x%x\n", __func__, ptr[0]);
2682 v->cvs_state = CMD_STATUS_SUCCESS;
2683 wake_up(&v->cvs_wait);
2684 break;
Ben Romberger13b74ab2011-07-18 17:36:32 -07002685 case VOICE_CMD_SET_PARAM:
2686 rtac_make_voice_callback(RTAC_CVS, ptr,
2687 data->payload_size);
2688 break;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002689 default:
2690 pr_debug("%s: cmd = 0x%x\n", __func__, ptr[0]);
2691 break;
2692 }
2693 }
2694 } else if (data->opcode == VSS_ISTREAM_EVT_SEND_ENC_BUFFER) {
2695 uint32_t *voc_pkt = data->payload;
2696 uint32_t pkt_len = data->payload_size;
2697
2698 if (voc_pkt != NULL && v->mvs_info.ul_cb != NULL) {
2699 pr_debug("%s: Media type is 0x%x\n",
2700 __func__, voc_pkt[0]);
2701
2702 /* Remove media ID from payload. */
2703 voc_pkt++;
2704 pkt_len = pkt_len - 4;
2705
2706 v->mvs_info.ul_cb((uint8_t *)voc_pkt,
2707 pkt_len,
2708 v->mvs_info.private_data);
2709 } else
2710 pr_err("%s: voc_pkt is 0x%x ul_cb is 0x%x\n",
2711 __func__, (unsigned int)voc_pkt,
2712 (unsigned int) v->mvs_info.ul_cb);
2713 } else if (data->opcode == VSS_ISTREAM_EVT_REQUEST_DEC_BUFFER) {
2714 struct cvs_send_dec_buf_cmd send_dec_buf;
2715 int ret = 0;
2716 uint32_t pkt_len = 0;
2717
2718 if (v->mvs_info.dl_cb != NULL) {
2719 send_dec_buf.dec_buf.media_id = v->mvs_info.media_type;
2720
2721 v->mvs_info.dl_cb(
2722 (uint8_t *)&send_dec_buf.dec_buf.packet_data,
2723 &pkt_len,
2724 v->mvs_info.private_data);
2725
2726 send_dec_buf.hdr.hdr_field =
2727 APR_HDR_FIELD(APR_MSG_TYPE_SEQ_CMD,
2728 APR_HDR_LEN(APR_HDR_SIZE),
2729 APR_PKT_VER);
2730 send_dec_buf.hdr.pkt_size = APR_PKT_SIZE(APR_HDR_SIZE,
2731 sizeof(send_dec_buf.dec_buf.media_id) + pkt_len);
2732 send_dec_buf.hdr.src_port = 0;
2733 send_dec_buf.hdr.dest_port = voice_get_cvs_handle(v);
2734 send_dec_buf.hdr.token = 0;
2735 send_dec_buf.hdr.opcode =
2736 VSS_ISTREAM_EVT_SEND_DEC_BUFFER;
2737
2738 ret = apr_send_pkt(v->apr_q6_cvs,
2739 (uint32_t *) &send_dec_buf);
2740 if (ret < 0) {
2741 pr_err("%s: Error %d sending DEC_BUF\n",
2742 __func__, ret);
2743 goto fail;
2744 }
2745 } else
2746 pr_debug("%s: dl_cb is NULL\n", __func__);
Ben Romberger13b74ab2011-07-18 17:36:32 -07002747 } else if (data->opcode == VSS_ISTREAM_EVT_SEND_DEC_BUFFER) {
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002748 pr_debug("Send dec buf resp\n");
Ben Romberger13b74ab2011-07-18 17:36:32 -07002749 } else if (data->opcode == VOICE_EVT_GET_PARAM_ACK) {
2750 rtac_make_voice_callback(RTAC_CVS, data->payload,
2751 data->payload_size);
2752 } else
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002753 pr_debug("Unknown opcode 0x%x\n", data->opcode);
2754
2755fail:
2756 return 0;
2757}
2758
2759static int32_t qdsp_cvp_callback(struct apr_client_data *data, void *priv)
2760{
2761 uint32_t *ptr;
2762 struct voice_data *v;
2763
2764 if ((data == NULL) || (priv == NULL)) {
2765 pr_err("%s: data or priv is NULL\n", __func__);
2766 return -EINVAL;
2767 }
2768 v = priv;
2769
2770 pr_debug("%s: Payload Length = %d, opcode=%x\n", __func__,
2771 data->payload_size, data->opcode);
2772
2773 if (data->opcode == APR_BASIC_RSP_RESULT) {
2774 if (data->payload_size) {
2775 ptr = data->payload;
2776
2777 pr_info("%x %x\n", ptr[0], ptr[1]);
2778
2779 switch (ptr[0]) {
2780 case VSS_IVOCPROC_CMD_CREATE_FULL_CONTROL_SESSION:
2781 /*response from CVP */
2782 pr_debug("%s: cmd = 0x%x\n", __func__, ptr[0]);
2783 if (!ptr[1]) {
2784 voice_set_cvp_handle(v, data->src_port);
2785 pr_debug("cvphdl=%d\n", data->src_port);
2786 } else
2787 pr_err("got NACK from CVP create \
2788 session response\n");
2789 v->cvp_state = CMD_STATUS_SUCCESS;
2790 wake_up(&v->cvp_wait);
2791 break;
2792 case VSS_IVOCPROC_CMD_SET_DEVICE:
2793 case VSS_IVOCPROC_CMD_SET_RX_VOLUME_INDEX:
2794 case VSS_IVOCPROC_CMD_ENABLE:
2795 case VSS_IVOCPROC_CMD_DISABLE:
2796 case APRV2_IBASIC_CMD_DESTROY_SESSION:
Helen Zeng29eb7442011-06-20 11:06:29 -07002797 case VSS_IVOCPROC_CMD_REGISTER_VOLUME_CAL_TABLE:
2798 case VSS_IVOCPROC_CMD_DEREGISTER_VOLUME_CAL_TABLE:
2799 case VSS_IVOCPROC_CMD_REGISTER_CALIBRATION_DATA:
2800 case VSS_IVOCPROC_CMD_DEREGISTER_CALIBRATION_DATA:
2801 case VSS_ICOMMON_CMD_MAP_MEMORY:
2802 case VSS_ICOMMON_CMD_UNMAP_MEMORY:
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002803 v->cvp_state = CMD_STATUS_SUCCESS;
2804 wake_up(&v->cvp_wait);
2805 break;
Ben Romberger13b74ab2011-07-18 17:36:32 -07002806 case VOICE_CMD_SET_PARAM:
2807 rtac_make_voice_callback(RTAC_CVP, ptr,
2808 data->payload_size);
2809 break;
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002810 default:
2811 pr_debug("%s: not match cmd = 0x%x\n",
2812 __func__, ptr[0]);
2813 break;
2814 }
2815 }
Ben Romberger13b74ab2011-07-18 17:36:32 -07002816 } else if (data->opcode == VOICE_EVT_GET_PARAM_ACK) {
2817 rtac_make_voice_callback(RTAC_CVP, data->payload,
2818 data->payload_size);
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002819 }
2820 return 0;
2821}
2822
2823
2824static int __init voice_init(void)
2825{
2826 int rc = 0;
2827 struct voice_data *v = &voice;
2828
2829 /* set default value */
2830 v->default_mute_val = 1; /* default is mute */
2831 v->default_vol_val = 0;
2832 v->default_sample_val = 8000;
2833 v->sidetone_gain = 0x512;
2834
2835 /* initialize dev_rx and dev_tx */
2836 memset(&v->dev_tx, 0, sizeof(struct device_data));
2837 memset(&v->dev_rx, 0, sizeof(struct device_data));
2838 v->dev_rx.volume = v->default_vol_val;
2839 v->dev_tx.mute = v->default_mute_val;
2840
2841 v->dev_tx.port_id = 1;
2842 v->dev_rx.port_id = 0;
2843
Helen Zengcc65b5b2011-07-06 19:14:48 -07002844 v->tty_mode = 0;
2845
Bryan Huntsman3f2bc4d2011-08-16 17:27:22 -07002846 v->voc_state = VOC_INIT;
2847 v->voc_path = VOC_PATH_PASSIVE;
2848 init_waitqueue_head(&v->mvm_wait);
2849 init_waitqueue_head(&v->cvs_wait);
2850 init_waitqueue_head(&v->cvp_wait);
2851
2852 mutex_init(&v->lock);
2853
2854 v->mvm_full_handle = 0;
2855 v->mvm_passive_handle = 0;
2856 v->cvs_full_handle = 0;
2857 v->cvs_passive_handle = 0;
2858 v->cvp_full_handle = 0;
2859 v->cvp_passive_handle = 0;
2860
2861 v->apr_q6_mvm = NULL;
2862 v->apr_q6_cvs = NULL;
2863 v->apr_q6_cvp = NULL;
2864
2865 /* Initialize MVS info. */
2866 memset(&v->mvs_info, 0, sizeof(v->mvs_info));
2867 v->mvs_info.network_type = VSS_NETWORK_ID_DEFAULT;
2868
2869 return rc;
2870}
2871
2872device_initcall(voice_init);