blob: c7896aeddc79dd2e1719e0521b59f9b19091d907 [file] [log] [blame]
Eric Laurentb23d5282013-05-14 15:27:20 -07001/*
Shiv Maliyappanahalli3e064fd2013-12-16 15:54:40 -08002 * Copyright (c) 2013-2014, The Linux Foundation. All rights reserved.
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -07003 * Not a Contribution.
4 *
Shiv Maliyappanahalli8911f282014-01-10 15:56:19 -08005 * Copyright (C) 2013 The Android Open Source Project
Eric Laurentb23d5282013-05-14 15:27:20 -07006 *
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
18 */
19
20#define LOG_TAG "msm8974_platform"
21/*#define LOG_NDEBUG 0*/
22#define LOG_NDDEBUG 0
23
24#include <stdlib.h>
25#include <dlfcn.h>
26#include <cutils/log.h>
27#include <cutils/properties.h>
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -070028#include <cutils/str_parms.h>
Eric Laurentb23d5282013-05-14 15:27:20 -070029#include <audio_hw.h>
30#include <platform_api.h>
31#include "platform.h"
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -070032#include "audio_extn.h"
Narsinga Rao Chella05573b72013-11-15 15:21:40 -080033#include "voice_extn.h"
Eric Laurentb23d5282013-05-14 15:27:20 -070034
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -070035#define MIXER_XML_PATH "/system/etc/mixer_paths.xml"
Damir Didjustof1d46c72013-11-06 17:59:04 -080036#define MIXER_XML_PATH_AUXPCM "/system/etc/mixer_paths_auxpcm.xml"
Eric Laurentb23d5282013-05-14 15:27:20 -070037#define LIB_ACDB_LOADER "libacdbloader.so"
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -070038#define AUDIO_DATA_BLOCK_MIXER_CTL "HDMI EDID"
Eric Laurentb23d5282013-05-14 15:27:20 -070039
Eric Laurentb23d5282013-05-14 15:27:20 -070040/*
Eric Laurentb23d5282013-05-14 15:27:20 -070041 * This file will have a maximum of 38 bytes:
42 *
43 * 4 bytes: number of audio blocks
44 * 4 bytes: total length of Short Audio Descriptor (SAD) blocks
45 * Maximum 10 * 3 bytes: SAD blocks
46 */
47#define MAX_SAD_BLOCKS 10
48#define SAD_BLOCK_SIZE 3
49
50/* EDID format ID for LPCM audio */
51#define EDID_FORMAT_LPCM 1
52
sangwoo1b9f4b32013-06-21 18:22:55 -070053/* Retry for delay in FW loading*/
54#define RETRY_NUMBER 10
55#define RETRY_US 500000
Apoorv Raghuvanshi84fa2fe2013-12-04 11:57:47 -080056#define MAX_SND_CARD 8
sangwoo1b9f4b32013-06-21 18:22:55 -070057
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -070058#define SAMPLE_RATE_8KHZ 8000
59#define SAMPLE_RATE_16KHZ 16000
60
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -070061#define AUDIO_PARAMETER_KEY_FLUENCE_TYPE "fluence"
62#define AUDIO_PARAMETER_KEY_BTSCO "bt_samplerate"
63#define AUDIO_PARAMETER_KEY_SLOWTALK "st_enable"
Ben Rombergerc1dc70d2013-12-19 15:11:17 -080064#define AUDIO_PARAMETER_KEY_VOLUME_BOOST "volume_boost"
65
66enum {
67 VOICE_FEATURE_SET_DEFAULT,
68 VOICE_FEATURE_SET_VOLUME_BOOST
69};
sangwoo53b2cf02013-07-25 19:18:44 -070070
Eric Laurentb23d5282013-05-14 15:27:20 -070071struct audio_block_header
72{
73 int reserved;
74 int length;
75};
76
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -080077/* Audio calibration related functions */
Eric Laurentb23d5282013-05-14 15:27:20 -070078typedef void (*acdb_deallocate_t)();
79typedef int (*acdb_init_t)();
80typedef void (*acdb_send_audio_cal_t)(int, int);
81typedef void (*acdb_send_voice_cal_t)(int, int);
Ben Rombergerc1dc70d2013-12-19 15:11:17 -080082typedef int (*acdb_reload_vocvoltable_t)(int);
Eric Laurentb23d5282013-05-14 15:27:20 -070083
Eric Laurentb23d5282013-05-14 15:27:20 -070084struct platform_data {
85 struct audio_device *adev;
86 bool fluence_in_spkr_mode;
87 bool fluence_in_voice_call;
88 bool fluence_in_voice_rec;
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -080089 bool fluence_in_audio_rec;
Mingming Yin8e5a4f62013-10-07 15:23:41 -070090 int fluence_type;
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -070091 int btsco_sample_rate;
92 bool slowtalk;
Ravi Kumar Alamanda48c921d2013-10-29 06:07:44 -070093 /* Audio calibration related functions */
Ben Rombergerc1dc70d2013-12-19 15:11:17 -080094 void *acdb_handle;
95 int voice_feature_set;
96 acdb_init_t acdb_init;
97 acdb_deallocate_t acdb_deallocate;
98 acdb_send_audio_cal_t acdb_send_audio_cal;
99 acdb_send_voice_cal_t acdb_send_voice_cal;
100 acdb_reload_vocvoltable_t acdb_reload_vocvoltable;
Ravi Kumar Alamanda48c921d2013-10-29 06:07:44 -0700101
102 void *hw_info;
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800103 struct csd_data *csd;
Eric Laurentb23d5282013-05-14 15:27:20 -0700104};
105
106static const int pcm_device_table[AUDIO_USECASE_MAX][2] = {
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700107 [USECASE_AUDIO_PLAYBACK_DEEP_BUFFER] = {DEEP_BUFFER_PCM_DEVICE,
108 DEEP_BUFFER_PCM_DEVICE},
109 [USECASE_AUDIO_PLAYBACK_LOW_LATENCY] = {LOWLATENCY_PCM_DEVICE,
Preetam Singh Ranawatde84f1a2013-11-01 14:58:16 -0700110 LOWLATENCY_PCM_DEVICE},
111 [USECASE_AUDIO_PLAYBACK_MULTI_CH] = {MULTIMEDIA2_PCM_DEVICE,
112 MULTIMEDIA2_PCM_DEVICE},
Krishnankutty Kolathappillya43f96e2013-11-01 12:17:53 -0700113 [USECASE_AUDIO_PLAYBACK_OFFLOAD] =
114 {PLAYBACK_OFFLOAD_DEVICE, PLAYBACK_OFFLOAD_DEVICE},
Shiv Maliyappanahallida107642013-10-17 11:16:13 -0700115 [USECASE_AUDIO_RECORD] = {AUDIO_RECORD_PCM_DEVICE, AUDIO_RECORD_PCM_DEVICE},
Mingming Yine62d7842013-10-25 16:26:03 -0700116 [USECASE_AUDIO_RECORD_COMPRESS] = {COMPRESS_CAPTURE_DEVICE, COMPRESS_CAPTURE_DEVICE},
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700117 [USECASE_AUDIO_RECORD_LOW_LATENCY] = {LOWLATENCY_PCM_DEVICE,
118 LOWLATENCY_PCM_DEVICE},
Preetam Singh Ranawatde84f1a2013-11-01 14:58:16 -0700119 [USECASE_AUDIO_RECORD_FM_VIRTUAL] = {MULTIMEDIA2_PCM_DEVICE,
120 MULTIMEDIA2_PCM_DEVICE},
Apoorv Raghuvanshi6e262842013-10-06 14:39:35 -0700121 [USECASE_AUDIO_PLAYBACK_FM] = {FM_PLAYBACK_PCM_DEVICE, FM_CAPTURE_PCM_DEVICE},
Vimal Puthanveed5b4d3f12013-11-05 15:57:39 -0800122 [USECASE_AUDIO_HFP_SCO] = {HFP_PCM_RX, HFP_SCO_RX},
Vimal Puthanveed47e64852013-12-20 13:23:39 -0800123 [USECASE_AUDIO_HFP_SCO_WB] = {HFP_PCM_RX, HFP_SCO_RX},
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700124 [USECASE_VOICE_CALL] = {VOICE_CALL_PCM_DEVICE, VOICE_CALL_PCM_DEVICE},
125 [USECASE_VOICE2_CALL] = {VOICE2_CALL_PCM_DEVICE, VOICE2_CALL_PCM_DEVICE},
126 [USECASE_VOLTE_CALL] = {VOLTE_CALL_PCM_DEVICE, VOLTE_CALL_PCM_DEVICE},
127 [USECASE_QCHAT_CALL] = {QCHAT_CALL_PCM_DEVICE, QCHAT_CALL_PCM_DEVICE},
Narsinga Rao Chella05573b72013-11-15 15:21:40 -0800128 [USECASE_COMPRESS_VOIP_CALL] = {COMPRESS_VOIP_CALL_PCM_DEVICE, COMPRESS_VOIP_CALL_PCM_DEVICE},
Shiv Maliyappanahallida107642013-10-17 11:16:13 -0700129 [USECASE_INCALL_REC_UPLINK] = {AUDIO_RECORD_PCM_DEVICE,
130 AUDIO_RECORD_PCM_DEVICE},
131 [USECASE_INCALL_REC_DOWNLINK] = {AUDIO_RECORD_PCM_DEVICE,
132 AUDIO_RECORD_PCM_DEVICE},
133 [USECASE_INCALL_REC_UPLINK_AND_DOWNLINK] = {AUDIO_RECORD_PCM_DEVICE,
134 AUDIO_RECORD_PCM_DEVICE},
Helen Zenge56b4852013-12-03 16:54:40 -0800135 [USECASE_INCALL_REC_UPLINK_COMPRESS] = {COMPRESS_CAPTURE_DEVICE,
136 COMPRESS_CAPTURE_DEVICE},
137 [USECASE_INCALL_REC_DOWNLINK_COMPRESS] = {COMPRESS_CAPTURE_DEVICE,
138 COMPRESS_CAPTURE_DEVICE},
139 [USECASE_INCALL_REC_UPLINK_AND_DOWNLINK_COMPRESS] = {COMPRESS_CAPTURE_DEVICE,
140 COMPRESS_CAPTURE_DEVICE},
Shiv Maliyappanahallif3b9a422013-10-22 16:38:08 -0700141 [USECASE_INCALL_MUSIC_UPLINK] = {INCALL_MUSIC_UPLINK_PCM_DEVICE,
142 INCALL_MUSIC_UPLINK_PCM_DEVICE},
143 [USECASE_INCALL_MUSIC_UPLINK2] = {INCALL_MUSIC_UPLINK2_PCM_DEVICE,
144 INCALL_MUSIC_UPLINK2_PCM_DEVICE},
Gopikrishnaiah Anandanf538cef2013-10-28 14:06:03 -0700145 [USECASE_AUDIO_SPKR_CALIB_RX] = {SPKR_PROT_CALIB_RX_PCM_DEVICE, -1},
146 [USECASE_AUDIO_SPKR_CALIB_TX] = {-1, SPKR_PROT_CALIB_TX_PCM_DEVICE},
Eric Laurentb23d5282013-05-14 15:27:20 -0700147};
148
149/* Array to store sound devices */
150static const char * const device_table[SND_DEVICE_MAX] = {
151 [SND_DEVICE_NONE] = "none",
152 /* Playback sound devices */
153 [SND_DEVICE_OUT_HANDSET] = "handset",
154 [SND_DEVICE_OUT_SPEAKER] = "speaker",
155 [SND_DEVICE_OUT_SPEAKER_REVERSE] = "speaker-reverse",
156 [SND_DEVICE_OUT_HEADPHONES] = "headphones",
157 [SND_DEVICE_OUT_SPEAKER_AND_HEADPHONES] = "speaker-and-headphones",
158 [SND_DEVICE_OUT_VOICE_HANDSET] = "voice-handset",
159 [SND_DEVICE_OUT_VOICE_SPEAKER] = "voice-speaker",
160 [SND_DEVICE_OUT_VOICE_HEADPHONES] = "voice-headphones",
161 [SND_DEVICE_OUT_HDMI] = "hdmi",
162 [SND_DEVICE_OUT_SPEAKER_AND_HDMI] = "speaker-and-hdmi",
163 [SND_DEVICE_OUT_BT_SCO] = "bt-sco-headset",
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700164 [SND_DEVICE_OUT_BT_SCO_WB] = "bt-sco-headset-wb",
Eric Laurentb23d5282013-05-14 15:27:20 -0700165 [SND_DEVICE_OUT_VOICE_TTY_FULL_HEADPHONES] = "voice-tty-full-headphones",
166 [SND_DEVICE_OUT_VOICE_TTY_VCO_HEADPHONES] = "voice-tty-vco-headphones",
167 [SND_DEVICE_OUT_VOICE_TTY_HCO_HANDSET] = "voice-tty-hco-handset",
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700168 [SND_DEVICE_OUT_AFE_PROXY] = "afe-proxy",
169 [SND_DEVICE_OUT_USB_HEADSET] = "usb-headphones",
170 [SND_DEVICE_OUT_SPEAKER_AND_USB_HEADSET] = "speaker-and-usb-headphones",
Apoorv Raghuvanshi6e262842013-10-06 14:39:35 -0700171 [SND_DEVICE_OUT_TRANSMISSION_FM] = "transmission-fm",
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -0700172 [SND_DEVICE_OUT_ANC_HEADSET] = "anc-headphones",
173 [SND_DEVICE_OUT_ANC_FB_HEADSET] = "anc-fb-headphones",
174 [SND_DEVICE_OUT_VOICE_ANC_HEADSET] = "voice-anc-headphones",
175 [SND_DEVICE_OUT_VOICE_ANC_FB_HEADSET] = "voice-anc-fb-headphones",
176 [SND_DEVICE_OUT_SPEAKER_AND_ANC_HEADSET] = "speaker-and-anc-headphones",
177 [SND_DEVICE_OUT_ANC_HANDSET] = "anc-handset",
Gopikrishnaiah Anandanf538cef2013-10-28 14:06:03 -0700178 [SND_DEVICE_OUT_SPEAKER_PROTECTED] = "speaker-protected",
Eric Laurentb23d5282013-05-14 15:27:20 -0700179
180 /* Capture sound devices */
181 [SND_DEVICE_IN_HANDSET_MIC] = "handset-mic",
Eric Laurentb23d5282013-05-14 15:27:20 -0700182 [SND_DEVICE_IN_HANDSET_MIC_AEC] = "handset-mic",
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800183 [SND_DEVICE_IN_HANDSET_MIC_NS] = "handset-mic",
184 [SND_DEVICE_IN_HANDSET_MIC_AEC_NS] = "handset-mic",
185 [SND_DEVICE_IN_HANDSET_DMIC] = "dmic-endfire",
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800186 [SND_DEVICE_IN_HANDSET_DMIC_AEC] = "dmic-endfire",
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800187 [SND_DEVICE_IN_HANDSET_DMIC_NS] = "dmic-endfire",
188 [SND_DEVICE_IN_HANDSET_DMIC_AEC_NS] = "dmic-endfire",
189 [SND_DEVICE_IN_SPEAKER_MIC] = "speaker-mic",
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800190 [SND_DEVICE_IN_SPEAKER_MIC_AEC] = "speaker-mic",
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800191 [SND_DEVICE_IN_SPEAKER_MIC_NS] = "speaker-mic",
192 [SND_DEVICE_IN_SPEAKER_MIC_AEC_NS] = "speaker-mic",
193 [SND_DEVICE_IN_SPEAKER_DMIC] = "speaker-dmic-endfire",
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800194 [SND_DEVICE_IN_SPEAKER_DMIC_AEC] = "speaker-dmic-endfire",
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800195 [SND_DEVICE_IN_SPEAKER_DMIC_NS] = "speaker-dmic-endfire",
196 [SND_DEVICE_IN_SPEAKER_DMIC_AEC_NS] = "speaker-dmic-endfire",
197 [SND_DEVICE_IN_HEADSET_MIC] = "headset-mic",
198 [SND_DEVICE_IN_HEADSET_MIC_FLUENCE] = "headset-mic",
Eric Laurentb23d5282013-05-14 15:27:20 -0700199 [SND_DEVICE_IN_VOICE_SPEAKER_MIC] = "voice-speaker-mic",
200 [SND_DEVICE_IN_VOICE_HEADSET_MIC] = "voice-headset-mic",
201 [SND_DEVICE_IN_HDMI_MIC] = "hdmi-mic",
202 [SND_DEVICE_IN_BT_SCO_MIC] = "bt-sco-mic",
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700203 [SND_DEVICE_IN_BT_SCO_MIC_WB] = "bt-sco-mic-wb",
Eric Laurentb23d5282013-05-14 15:27:20 -0700204 [SND_DEVICE_IN_CAMCORDER_MIC] = "camcorder-mic",
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700205 [SND_DEVICE_IN_VOICE_DMIC] = "voice-dmic-ef",
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700206 [SND_DEVICE_IN_VOICE_SPEAKER_DMIC] = "voice-speaker-dmic-ef",
Vidyakumar Athotaadfe4e32013-12-13 14:51:26 -0800207 [SND_DEVICE_IN_VOICE_SPEAKER_QMIC] = "voice-speaker-qmic",
Eric Laurentb23d5282013-05-14 15:27:20 -0700208 [SND_DEVICE_IN_VOICE_TTY_FULL_HEADSET_MIC] = "voice-tty-full-headset-mic",
209 [SND_DEVICE_IN_VOICE_TTY_VCO_HANDSET_MIC] = "voice-tty-vco-handset-mic",
210 [SND_DEVICE_IN_VOICE_TTY_HCO_HEADSET_MIC] = "voice-tty-hco-headset-mic",
211 [SND_DEVICE_IN_VOICE_REC_MIC] = "voice-rec-mic",
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800212 [SND_DEVICE_IN_VOICE_REC_MIC_NS] = "voice-rec-mic",
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800213 [SND_DEVICE_IN_VOICE_REC_DMIC_STEREO] = "voice-rec-dmic-ef",
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700214 [SND_DEVICE_IN_VOICE_REC_DMIC_FLUENCE] = "voice-rec-dmic-ef-fluence",
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700215 [SND_DEVICE_IN_USB_HEADSET_MIC] = "usb-headset-mic",
Apoorv Raghuvanshi6e262842013-10-06 14:39:35 -0700216 [SND_DEVICE_IN_CAPTURE_FM] = "capture-fm",
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -0700217 [SND_DEVICE_IN_AANC_HANDSET_MIC] = "aanc-handset-mic",
Apoorv Raghuvanshi6178a3f2013-10-19 12:38:54 -0700218 [SND_DEVICE_IN_QUAD_MIC] = "quad-mic",
Apoorv Raghuvanshi6bd8dbf2013-10-19 18:37:52 -0700219 [SND_DEVICE_IN_HANDSET_STEREO_DMIC] = "handset-stereo-dmic-ef",
220 [SND_DEVICE_IN_SPEAKER_STEREO_DMIC] = "speaker-stereo-dmic-ef",
Gopikrishnaiah Anandanf538cef2013-10-28 14:06:03 -0700221 [SND_DEVICE_IN_CAPTURE_VI_FEEDBACK] = "vi-feedback",
Eric Laurentb23d5282013-05-14 15:27:20 -0700222};
223
224/* ACDB IDs (audio DSP path configuration IDs) for each sound device */
225static const int acdb_device_table[SND_DEVICE_MAX] = {
226 [SND_DEVICE_NONE] = -1,
227 [SND_DEVICE_OUT_HANDSET] = 7,
Vidyakumar Athotac29d4ab2013-11-14 16:58:02 -0800228 [SND_DEVICE_OUT_SPEAKER] = 14,
229 [SND_DEVICE_OUT_SPEAKER_REVERSE] = 14,
Eric Laurentb23d5282013-05-14 15:27:20 -0700230 [SND_DEVICE_OUT_HEADPHONES] = 10,
231 [SND_DEVICE_OUT_SPEAKER_AND_HEADPHONES] = 10,
232 [SND_DEVICE_OUT_VOICE_HANDSET] = 7,
Vidyakumar Athotac29d4ab2013-11-14 16:58:02 -0800233 [SND_DEVICE_OUT_VOICE_SPEAKER] = 14,
Eric Laurentb23d5282013-05-14 15:27:20 -0700234 [SND_DEVICE_OUT_VOICE_HEADPHONES] = 10,
235 [SND_DEVICE_OUT_HDMI] = 18,
Vidyakumar Athotac29d4ab2013-11-14 16:58:02 -0800236 [SND_DEVICE_OUT_SPEAKER_AND_HDMI] = 14,
Eric Laurentb23d5282013-05-14 15:27:20 -0700237 [SND_DEVICE_OUT_BT_SCO] = 22,
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700238 [SND_DEVICE_OUT_BT_SCO_WB] = 39,
Eric Laurentb23d5282013-05-14 15:27:20 -0700239 [SND_DEVICE_OUT_VOICE_TTY_FULL_HEADPHONES] = 17,
240 [SND_DEVICE_OUT_VOICE_TTY_VCO_HEADPHONES] = 17,
241 [SND_DEVICE_OUT_VOICE_TTY_HCO_HANDSET] = 37,
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700242 [SND_DEVICE_OUT_AFE_PROXY] = 0,
243 [SND_DEVICE_OUT_USB_HEADSET] = 0,
244 [SND_DEVICE_OUT_SPEAKER_AND_USB_HEADSET] = 14,
Apoorv Raghuvanshi6e262842013-10-06 14:39:35 -0700245 [SND_DEVICE_OUT_TRANSMISSION_FM] = 0,
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -0700246 [SND_DEVICE_OUT_ANC_HEADSET] = 26,
Ravi Kumar Alamanda48c921d2013-10-29 06:07:44 -0700247 [SND_DEVICE_OUT_ANC_FB_HEADSET] = 27,
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -0700248 [SND_DEVICE_OUT_VOICE_ANC_HEADSET] = 26,
Ravi Kumar Alamanda48c921d2013-10-29 06:07:44 -0700249 [SND_DEVICE_OUT_VOICE_ANC_FB_HEADSET] = 27,
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -0700250 [SND_DEVICE_OUT_SPEAKER_AND_ANC_HEADSET] = 26,
251 [SND_DEVICE_OUT_ANC_HANDSET] = 103,
Gopikrishnaiah Anandanf538cef2013-10-28 14:06:03 -0700252 [SND_DEVICE_OUT_SPEAKER_PROTECTED] = 101,
Eric Laurentb23d5282013-05-14 15:27:20 -0700253
254 [SND_DEVICE_IN_HANDSET_MIC] = 4,
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800255 [SND_DEVICE_IN_HANDSET_MIC_AEC] = 106,
256 [SND_DEVICE_IN_HANDSET_MIC_NS] = 107,
257 [SND_DEVICE_IN_HANDSET_MIC_AEC_NS] = 108,
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800258 [SND_DEVICE_IN_HANDSET_DMIC] = 41,
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800259 [SND_DEVICE_IN_HANDSET_DMIC_AEC] = 109,
260 [SND_DEVICE_IN_HANDSET_DMIC_NS] = 110,
261 [SND_DEVICE_IN_HANDSET_DMIC_AEC_NS] = 111,
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800262 [SND_DEVICE_IN_SPEAKER_MIC] = 11,
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800263 [SND_DEVICE_IN_SPEAKER_MIC_AEC] = 112,
264 [SND_DEVICE_IN_SPEAKER_MIC_NS] = 113,
265 [SND_DEVICE_IN_SPEAKER_MIC_AEC_NS] = 114,
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800266 [SND_DEVICE_IN_SPEAKER_DMIC] = 43,
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800267 [SND_DEVICE_IN_SPEAKER_DMIC_AEC] = 115,
268 [SND_DEVICE_IN_SPEAKER_DMIC_NS] = 116,
269 [SND_DEVICE_IN_SPEAKER_DMIC_AEC_NS] = 117,
Eric Laurentb23d5282013-05-14 15:27:20 -0700270 [SND_DEVICE_IN_HEADSET_MIC] = 8,
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800271 [SND_DEVICE_IN_HEADSET_MIC_FLUENCE] = 47,
Eric Laurentb23d5282013-05-14 15:27:20 -0700272 [SND_DEVICE_IN_VOICE_SPEAKER_MIC] = 11,
273 [SND_DEVICE_IN_VOICE_HEADSET_MIC] = 8,
274 [SND_DEVICE_IN_HDMI_MIC] = 4,
275 [SND_DEVICE_IN_BT_SCO_MIC] = 21,
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700276 [SND_DEVICE_IN_BT_SCO_MIC_WB] = 38,
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800277 [SND_DEVICE_IN_CAMCORDER_MIC] = 4,
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700278 [SND_DEVICE_IN_VOICE_DMIC] = 41,
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700279 [SND_DEVICE_IN_VOICE_SPEAKER_DMIC] = 43,
Vidyakumar Athotaadfe4e32013-12-13 14:51:26 -0800280 [SND_DEVICE_IN_VOICE_SPEAKER_QMIC] = 19,
Eric Laurentb23d5282013-05-14 15:27:20 -0700281 [SND_DEVICE_IN_VOICE_TTY_FULL_HEADSET_MIC] = 16,
282 [SND_DEVICE_IN_VOICE_TTY_VCO_HANDSET_MIC] = 36,
283 [SND_DEVICE_IN_VOICE_TTY_HCO_HEADSET_MIC] = 16,
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800284 [SND_DEVICE_IN_VOICE_REC_MIC] = 4,
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -0800285 [SND_DEVICE_IN_VOICE_REC_MIC_NS] = 107,
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800286 [SND_DEVICE_IN_VOICE_REC_DMIC_STEREO] = 34,
287 [SND_DEVICE_IN_VOICE_REC_DMIC_FLUENCE] = 41,
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700288 [SND_DEVICE_IN_USB_HEADSET_MIC] = 44,
Apoorv Raghuvanshi6e262842013-10-06 14:39:35 -0700289 [SND_DEVICE_IN_CAPTURE_FM] = 0,
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -0700290 [SND_DEVICE_IN_AANC_HANDSET_MIC] = 104,
Apoorv Raghuvanshi6178a3f2013-10-19 12:38:54 -0700291 [SND_DEVICE_IN_QUAD_MIC] = 46,
Apoorv Raghuvanshi6bd8dbf2013-10-19 18:37:52 -0700292 [SND_DEVICE_IN_HANDSET_STEREO_DMIC] = 34,
293 [SND_DEVICE_IN_SPEAKER_STEREO_DMIC] = 35,
Gopikrishnaiah Anandanf538cef2013-10-28 14:06:03 -0700294 [SND_DEVICE_IN_CAPTURE_VI_FEEDBACK] = 102,
Eric Laurentb23d5282013-05-14 15:27:20 -0700295};
296
Haynes Mathew George7ff216f2013-09-11 19:51:41 -0700297#define DEEP_BUFFER_PLATFORM_DELAY (29*1000LL)
298#define LOW_LATENCY_PLATFORM_DELAY (13*1000LL)
299
Eric Laurentb23d5282013-05-14 15:27:20 -0700300static int set_echo_reference(struct mixer *mixer, const char* ec_ref)
301{
302 struct mixer_ctl *ctl;
303 const char *mixer_ctl_name = "EC_REF_RX";
304
305 ctl = mixer_get_ctl_by_name(mixer, mixer_ctl_name);
306 if (!ctl) {
307 ALOGE("%s: Could not get ctl for mixer cmd - %s",
308 __func__, mixer_ctl_name);
309 return -EINVAL;
310 }
311 ALOGV("Setting EC Reference: %s", ec_ref);
312 mixer_ctl_set_enum_by_string(ctl, ec_ref);
313 return 0;
314}
315
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800316static struct csd_data *open_csd_client()
317{
318 struct csd_data *csd = calloc(1, sizeof(struct csd_data));
319
320 csd->csd_client = dlopen(LIB_CSD_CLIENT, RTLD_NOW);
321 if (csd->csd_client == NULL) {
322 ALOGE("%s: DLOPEN failed for %s", __func__, LIB_CSD_CLIENT);
323 goto error;
324 } else {
325 ALOGV("%s: DLOPEN successful for %s", __func__, LIB_CSD_CLIENT);
326
327 csd->deinit = (deinit_t)dlsym(csd->csd_client,
328 "csd_client_deinit");
329 if (csd->deinit == NULL) {
330 ALOGE("%s: dlsym error %s for csd_client_deinit", __func__,
331 dlerror());
332 goto error;
333 }
334 csd->disable_device = (disable_device_t)dlsym(csd->csd_client,
335 "csd_client_disable_device");
336 if (csd->disable_device == NULL) {
337 ALOGE("%s: dlsym error %s for csd_client_disable_device",
338 __func__, dlerror());
339 goto error;
340 }
341 csd->enable_device = (enable_device_t)dlsym(csd->csd_client,
342 "csd_client_enable_device");
343 if (csd->enable_device == NULL) {
344 ALOGE("%s: dlsym error %s for csd_client_enable_device",
345 __func__, dlerror());
346 goto error;
347 }
348 csd->start_voice = (start_voice_t)dlsym(csd->csd_client,
349 "csd_client_start_voice");
350 if (csd->start_voice == NULL) {
351 ALOGE("%s: dlsym error %s for csd_client_start_voice",
352 __func__, dlerror());
353 goto error;
354 }
355 csd->stop_voice = (stop_voice_t)dlsym(csd->csd_client,
356 "csd_client_stop_voice");
357 if (csd->stop_voice == NULL) {
358 ALOGE("%s: dlsym error %s for csd_client_stop_voice",
359 __func__, dlerror());
360 goto error;
361 }
362 csd->volume = (volume_t)dlsym(csd->csd_client,
363 "csd_client_volume");
364 if (csd->volume == NULL) {
365 ALOGE("%s: dlsym error %s for csd_client_volume",
366 __func__, dlerror());
367 goto error;
368 }
369 csd->mic_mute = (mic_mute_t)dlsym(csd->csd_client,
370 "csd_client_mic_mute");
371 if (csd->mic_mute == NULL) {
372 ALOGE("%s: dlsym error %s for csd_client_mic_mute",
373 __func__, dlerror());
374 goto error;
375 }
376 csd->slow_talk = (slow_talk_t)dlsym(csd->csd_client,
377 "csd_client_slow_talk");
378 if (csd->slow_talk == NULL) {
379 ALOGE("%s: dlsym error %s for csd_client_slow_talk",
380 __func__, dlerror());
381 goto error;
382 }
383 csd->start_playback = (start_playback_t)dlsym(csd->csd_client,
384 "csd_client_start_playback");
385 if (csd->start_playback == NULL) {
386 ALOGE("%s: dlsym error %s for csd_client_start_playback",
387 __func__, dlerror());
388 goto error;
389 }
390 csd->stop_playback = (stop_playback_t)dlsym(csd->csd_client,
391 "csd_client_stop_playback");
392 if (csd->stop_playback == NULL) {
393 ALOGE("%s: dlsym error %s for csd_client_stop_playback",
394 __func__, dlerror());
395 goto error;
396 }
397 csd->start_record = (start_record_t)dlsym(csd->csd_client,
398 "csd_client_start_record");
399 if (csd->start_record == NULL) {
400 ALOGE("%s: dlsym error %s for csd_client_start_record",
401 __func__, dlerror());
402 goto error;
403 }
404 csd->stop_record = (stop_record_t)dlsym(csd->csd_client,
405 "csd_client_stop_record");
406 if (csd->stop_record == NULL) {
407 ALOGE("%s: dlsym error %s for csd_client_stop_record",
408 __func__, dlerror());
409 goto error;
410 }
411 csd->init = (init_t)dlsym(csd->csd_client, "csd_client_init");
412
413 if (csd->init == NULL) {
414 ALOGE("%s: dlsym error %s for csd_client_init",
415 __func__, dlerror());
416 goto error;
417 } else {
418 csd->init();
419 }
420 }
421 return csd;
422
423error:
424 free(csd);
425 csd = NULL;
426 return csd;
427}
428
429void close_csd_client(struct csd_data *csd)
430{
431 if (csd != NULL) {
432 csd->deinit();
433 dlclose(csd->csd_client);
434 free(csd);
435 csd = NULL;
436 }
437}
438
Eric Laurentb23d5282013-05-14 15:27:20 -0700439void *platform_init(struct audio_device *adev)
440{
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800441 char platform[PROPERTY_VALUE_MAX];
442 char baseband[PROPERTY_VALUE_MAX];
Eric Laurentb23d5282013-05-14 15:27:20 -0700443 char value[PROPERTY_VALUE_MAX];
Apoorv Raghuvanshi84fa2fe2013-12-04 11:57:47 -0800444 struct platform_data *my_data = NULL;
445 int retry_num = 0, snd_card_num = 0;
Ravi Kumar Alamanda48c921d2013-10-29 06:07:44 -0700446 const char *snd_card_name;
sangwoo1b9f4b32013-06-21 18:22:55 -0700447
Eric Laurentb23d5282013-05-14 15:27:20 -0700448 my_data = calloc(1, sizeof(struct platform_data));
449
Apoorv Raghuvanshi84fa2fe2013-12-04 11:57:47 -0800450 while (snd_card_num < MAX_SND_CARD) {
451 adev->mixer = mixer_open(snd_card_num);
452
453 while (!adev->mixer && retry_num < RETRY_NUMBER) {
454 usleep(RETRY_US);
455 adev->mixer = mixer_open(snd_card_num);
456 retry_num++;
457 }
458
459 if (!adev->mixer) {
460 ALOGE("%s: Unable to open the mixer card: %d", __func__,
461 snd_card_num);
462 retry_num = 0;
463 snd_card_num++;
464 continue;
465 }
466
467 snd_card_name = mixer_get_name(adev->mixer);
468 ALOGV("%s: snd_card_name: %s", __func__, snd_card_name);
469
470 my_data->hw_info = hw_info_init(snd_card_name);
471 if (!my_data->hw_info) {
472 ALOGE("%s: Failed to init hardware info", __func__);
473 } else {
474 if (audio_extn_read_xml(adev, snd_card_num, MIXER_XML_PATH,
475 MIXER_XML_PATH_AUXPCM) == -ENOSYS)
476 adev->audio_route = audio_route_init(snd_card_num,
477 MIXER_XML_PATH);
478 if (!adev->audio_route) {
479 ALOGE("%s: Failed to init audio route controls, aborting.",
480 __func__);
481 free(my_data);
482 return NULL;
483 }
484 adev->snd_card = snd_card_num;
485 ALOGD("%s: Opened sound card:%d", __func__, snd_card_num);
486 break;
487 }
488 retry_num = 0;
489 snd_card_num++;
490 }
491
492 if (snd_card_num >= MAX_SND_CARD) {
493 ALOGE("%s: Unable to find correct sound card, aborting.", __func__);
494 free(my_data);
495 return NULL;
Ravi Kumar Alamanda48c921d2013-10-29 06:07:44 -0700496 }
497
Eric Laurentb23d5282013-05-14 15:27:20 -0700498 my_data->adev = adev;
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700499 my_data->btsco_sample_rate = SAMPLE_RATE_8KHZ;
Eric Laurentb23d5282013-05-14 15:27:20 -0700500 my_data->fluence_in_spkr_mode = false;
501 my_data->fluence_in_voice_call = false;
502 my_data->fluence_in_voice_rec = false;
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800503 my_data->fluence_in_audio_rec = false;
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700504 my_data->fluence_type = FLUENCE_NONE;
Eric Laurentb23d5282013-05-14 15:27:20 -0700505
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700506 property_get("ro.qc.sdk.audio.fluencetype", value, "");
507 if (!strncmp("fluencepro", value, sizeof("fluencepro"))) {
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800508 my_data->fluence_type = FLUENCE_QUAD_MIC | FLUENCE_DUAL_MIC;
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700509 } else if (!strncmp("fluence", value, sizeof("fluence"))) {
510 my_data->fluence_type = FLUENCE_DUAL_MIC;
511 } else {
512 my_data->fluence_type = FLUENCE_NONE;
Eric Laurentb23d5282013-05-14 15:27:20 -0700513 }
514
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700515 if (my_data->fluence_type != FLUENCE_NONE) {
Eric Laurentb23d5282013-05-14 15:27:20 -0700516 property_get("persist.audio.fluence.voicecall",value,"");
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700517 if (!strncmp("true", value, sizeof("true"))) {
Eric Laurentb23d5282013-05-14 15:27:20 -0700518 my_data->fluence_in_voice_call = true;
519 }
520
521 property_get("persist.audio.fluence.voicerec",value,"");
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700522 if (!strncmp("true", value, sizeof("true"))) {
Eric Laurentb23d5282013-05-14 15:27:20 -0700523 my_data->fluence_in_voice_rec = true;
524 }
525
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -0800526 property_get("persist.audio.fluence.audiorec",value,"");
527 if (!strncmp("true", value, sizeof("true"))) {
528 my_data->fluence_in_audio_rec = true;
529 }
530
Eric Laurentb23d5282013-05-14 15:27:20 -0700531 property_get("persist.audio.fluence.speaker",value,"");
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700532 if (!strncmp("true", value, sizeof("true"))) {
Eric Laurentb23d5282013-05-14 15:27:20 -0700533 my_data->fluence_in_spkr_mode = true;
534 }
535 }
536
Ben Rombergerc1dc70d2013-12-19 15:11:17 -0800537 my_data->voice_feature_set = VOICE_FEATURE_SET_DEFAULT;
Eric Laurentb23d5282013-05-14 15:27:20 -0700538 my_data->acdb_handle = dlopen(LIB_ACDB_LOADER, RTLD_NOW);
539 if (my_data->acdb_handle == NULL) {
540 ALOGE("%s: DLOPEN failed for %s", __func__, LIB_ACDB_LOADER);
541 } else {
542 ALOGV("%s: DLOPEN successful for %s", __func__, LIB_ACDB_LOADER);
543 my_data->acdb_deallocate = (acdb_deallocate_t)dlsym(my_data->acdb_handle,
544 "acdb_loader_deallocate_ACDB");
Ben Rombergerc1dc70d2013-12-19 15:11:17 -0800545 if (!my_data->acdb_deallocate)
546 ALOGE("%s: Could not find the symbol acdb_loader_deallocate_ACDB from %s",
547 __func__, LIB_ACDB_LOADER);
548
Eric Laurentb23d5282013-05-14 15:27:20 -0700549 my_data->acdb_send_audio_cal = (acdb_send_audio_cal_t)dlsym(my_data->acdb_handle,
550 "acdb_loader_send_audio_cal");
551 if (!my_data->acdb_send_audio_cal)
Ben Rombergerc1dc70d2013-12-19 15:11:17 -0800552 ALOGE("%s: Could not find the symbol acdb_send_audio_cal from %s",
Eric Laurentb23d5282013-05-14 15:27:20 -0700553 __func__, LIB_ACDB_LOADER);
Ben Rombergerc1dc70d2013-12-19 15:11:17 -0800554
Eric Laurentb23d5282013-05-14 15:27:20 -0700555 my_data->acdb_send_voice_cal = (acdb_send_voice_cal_t)dlsym(my_data->acdb_handle,
556 "acdb_loader_send_voice_cal");
Ben Rombergerc1dc70d2013-12-19 15:11:17 -0800557 if (!my_data->acdb_send_voice_cal)
558 ALOGE("%s: Could not find the symbol acdb_loader_send_voice_cal from %s",
559 __func__, LIB_ACDB_LOADER);
560
561 my_data->acdb_reload_vocvoltable = (acdb_reload_vocvoltable_t)dlsym(my_data->acdb_handle,
562 "acdb_loader_reload_vocvoltable");
563 if (!my_data->acdb_reload_vocvoltable)
564 ALOGE("%s: Could not find the symbol acdb_loader_reload_vocvoltable from %s",
565 __func__, LIB_ACDB_LOADER);
566
Eric Laurentb23d5282013-05-14 15:27:20 -0700567 my_data->acdb_init = (acdb_init_t)dlsym(my_data->acdb_handle,
568 "acdb_loader_init_ACDB");
569 if (my_data->acdb_init == NULL)
570 ALOGE("%s: dlsym error %s for acdb_loader_init_ACDB", __func__, dlerror());
571 else
572 my_data->acdb_init();
573 }
574
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800575 /* If platform is apq8084 and baseband is MDM, load CSD Client specific
576 * symbols. Voice call is handled by MDM and apps processor talks to
577 * MDM through CSD Client
578 */
579 property_get("ro.board.platform", platform, "");
580 property_get("ro.baseband", baseband, "");
581 if (!strncmp("apq8084", platform, sizeof("apq8084")) &&
582 !strncmp("mdm", baseband, sizeof("mdm"))) {
583 my_data->csd = open_csd_client();
584 }
585
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700586 /* init usb */
587 audio_extn_usb_init(adev);
Apoorv Raghuvanshi84fa2fe2013-12-04 11:57:47 -0800588 /* update sound cards appropriately */
589 audio_extn_usb_set_proxy_sound_card(adev->snd_card);
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700590
Apoorv Raghuvanshi6178a3f2013-10-19 12:38:54 -0700591 /* Read one time ssr property */
Mingming Yin49be8032013-12-19 12:51:25 -0800592 audio_extn_ssr_update_enabled();
Gopikrishnaiah Anandanf538cef2013-10-28 14:06:03 -0700593 audio_extn_spkr_prot_init(adev);
Eric Laurentb23d5282013-05-14 15:27:20 -0700594 return my_data;
595}
596
597void platform_deinit(void *platform)
598{
Ravi Kumar Alamanda48c921d2013-10-29 06:07:44 -0700599 struct platform_data *my_data = (struct platform_data *)platform;
600
601 hw_info_deinit(my_data->hw_info);
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800602 close_csd_client(my_data->csd);
603
Eric Laurentb23d5282013-05-14 15:27:20 -0700604 free(platform);
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700605 /* deinit usb */
606 audio_extn_usb_deinit();
Eric Laurentb23d5282013-05-14 15:27:20 -0700607}
608
609const char *platform_get_snd_device_name(snd_device_t snd_device)
610{
611 if (snd_device >= SND_DEVICE_MIN && snd_device < SND_DEVICE_MAX)
612 return device_table[snd_device];
613 else
614 return "";
615}
616
Ravi Kumar Alamanda48c921d2013-10-29 06:07:44 -0700617int platform_get_snd_device_name_extn(void *platform, snd_device_t snd_device,
618 char *device_name)
619{
620 struct platform_data *my_data = (struct platform_data *)platform;
621
622 if (snd_device >= SND_DEVICE_MIN && snd_device < SND_DEVICE_MAX) {
623 strlcpy(device_name, device_table[snd_device], DEVICE_NAME_MAX_SIZE);
624 hw_info_append_hw_type(my_data->hw_info, snd_device, device_name);
625 } else {
626 strlcpy(device_name, "", DEVICE_NAME_MAX_SIZE);
627 return -EINVAL;
628 }
629
630 return 0;
631}
632
Eric Laurentb23d5282013-05-14 15:27:20 -0700633void platform_add_backend_name(char *mixer_path, snd_device_t snd_device)
634{
635 if (snd_device == SND_DEVICE_IN_BT_SCO_MIC)
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700636 strlcat(mixer_path, " bt-sco", MIXER_PATH_MAX_LENGTH);
637 else if (snd_device == SND_DEVICE_IN_BT_SCO_MIC_WB)
638 strlcat(mixer_path, " bt-sco-wb", MIXER_PATH_MAX_LENGTH);
Eric Laurentb23d5282013-05-14 15:27:20 -0700639 else if(snd_device == SND_DEVICE_OUT_BT_SCO)
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700640 strlcat(mixer_path, " bt-sco", MIXER_PATH_MAX_LENGTH);
641 else if(snd_device == SND_DEVICE_OUT_BT_SCO_WB)
642 strlcat(mixer_path, " bt-sco-wb", MIXER_PATH_MAX_LENGTH);
Eric Laurentb23d5282013-05-14 15:27:20 -0700643 else if (snd_device == SND_DEVICE_OUT_HDMI)
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700644 strlcat(mixer_path, " hdmi", MIXER_PATH_MAX_LENGTH);
Eric Laurentb23d5282013-05-14 15:27:20 -0700645 else if (snd_device == SND_DEVICE_OUT_SPEAKER_AND_HDMI)
646 strcat(mixer_path, " speaker-and-hdmi");
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700647 else if (snd_device == SND_DEVICE_OUT_AFE_PROXY)
648 strlcat(mixer_path, " afe-proxy", MIXER_PATH_MAX_LENGTH);
649 else if (snd_device == SND_DEVICE_OUT_USB_HEADSET)
650 strlcat(mixer_path, " usb-headphones", MIXER_PATH_MAX_LENGTH);
651 else if (snd_device == SND_DEVICE_OUT_SPEAKER_AND_USB_HEADSET)
652 strlcat(mixer_path, " speaker-and-usb-headphones",
653 MIXER_PATH_MAX_LENGTH);
654 else if (snd_device == SND_DEVICE_IN_USB_HEADSET_MIC)
655 strlcat(mixer_path, " usb-headset-mic", MIXER_PATH_MAX_LENGTH);
Apoorv Raghuvanshi6e262842013-10-06 14:39:35 -0700656 else if (snd_device == SND_DEVICE_IN_CAPTURE_FM)
657 strlcat(mixer_path, " capture-fm", MIXER_PATH_MAX_LENGTH);
658 else if (snd_device == SND_DEVICE_OUT_TRANSMISSION_FM)
659 strlcat(mixer_path, " transmission-fm", MIXER_PATH_MAX_LENGTH);
Eric Laurentb23d5282013-05-14 15:27:20 -0700660}
661
662int platform_get_pcm_device_id(audio_usecase_t usecase, int device_type)
663{
664 int device_id;
665 if (device_type == PCM_PLAYBACK)
666 device_id = pcm_device_table[usecase][0];
667 else
668 device_id = pcm_device_table[usecase][1];
669 return device_id;
670}
671
672int platform_send_audio_calibration(void *platform, snd_device_t snd_device)
673{
674 struct platform_data *my_data = (struct platform_data *)platform;
675 int acdb_dev_id, acdb_dev_type;
676
677 acdb_dev_id = acdb_device_table[snd_device];
678 if (acdb_dev_id < 0) {
679 ALOGE("%s: Could not find acdb id for device(%d)",
680 __func__, snd_device);
681 return -EINVAL;
682 }
683 if (my_data->acdb_send_audio_cal) {
Eric Laurent994a6932013-07-17 11:51:42 -0700684 ("%s: sending audio calibration for snd_device(%d) acdb_id(%d)",
Eric Laurentb23d5282013-05-14 15:27:20 -0700685 __func__, snd_device, acdb_dev_id);
686 if (snd_device >= SND_DEVICE_OUT_BEGIN &&
687 snd_device < SND_DEVICE_OUT_END)
688 acdb_dev_type = ACDB_DEV_TYPE_OUT;
689 else
690 acdb_dev_type = ACDB_DEV_TYPE_IN;
691 my_data->acdb_send_audio_cal(acdb_dev_id, acdb_dev_type);
692 }
693 return 0;
694}
695
696int platform_switch_voice_call_device_pre(void *platform)
697{
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800698 struct platform_data *my_data = (struct platform_data *)platform;
699 int ret = 0;
700
Vidyakumar Athota1fd21792013-11-15 14:50:57 -0800701 if (my_data->csd != NULL &&
702 my_data->adev->mode == AUDIO_MODE_IN_CALL) {
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800703 /* This must be called before disabling mixer controls on APQ side */
704 ret = my_data->csd->disable_device();
705 if (ret < 0) {
706 ALOGE("%s: csd_client_disable_device, failed, error %d",
707 __func__, ret);
708 }
709 }
710 return ret;
Eric Laurentb23d5282013-05-14 15:27:20 -0700711}
712
713int platform_switch_voice_call_device_post(void *platform,
714 snd_device_t out_snd_device,
715 snd_device_t in_snd_device)
716{
717 struct platform_data *my_data = (struct platform_data *)platform;
718 int acdb_rx_id, acdb_tx_id;
719
720 if (my_data->acdb_send_voice_cal == NULL) {
721 ALOGE("%s: dlsym error for acdb_send_voice_call", __func__);
722 } else {
Vidyakumar Athota1fd21792013-11-15 14:50:57 -0800723 acdb_rx_id = acdb_device_table[out_snd_device];
724 acdb_tx_id = acdb_device_table[in_snd_device];
725
Eric Laurentb23d5282013-05-14 15:27:20 -0700726 if (acdb_rx_id > 0 && acdb_tx_id > 0)
727 my_data->acdb_send_voice_cal(acdb_rx_id, acdb_tx_id);
728 else
729 ALOGE("%s: Incorrect ACDB IDs (rx: %d tx: %d)", __func__,
730 acdb_rx_id, acdb_tx_id);
731 }
732
Vidyakumar Athota1fd21792013-11-15 14:50:57 -0800733 return 0;
734}
735
736int platform_switch_voice_call_usecase_route_post(void *platform,
737 snd_device_t out_snd_device,
738 snd_device_t in_snd_device)
739{
740 struct platform_data *my_data = (struct platform_data *)platform;
741 int acdb_rx_id, acdb_tx_id;
742 int ret = 0;
743
744 acdb_rx_id = acdb_device_table[out_snd_device];
745 acdb_tx_id = acdb_device_table[in_snd_device];
746
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800747 if (my_data->csd != NULL) {
Vidyakumar Athota1fd21792013-11-15 14:50:57 -0800748 if (acdb_rx_id > 0 && acdb_tx_id > 0) {
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800749 ret = my_data->csd->enable_device(acdb_rx_id, acdb_tx_id,
750 my_data->adev->acdb_settings);
751 if (ret < 0) {
752 ALOGE("%s: csd_enable_device, failed, error %d",
753 __func__, ret);
754 }
755 } else {
756 ALOGE("%s: Incorrect ACDB IDs (rx: %d tx: %d)", __func__,
757 acdb_rx_id, acdb_tx_id);
758 }
759 }
760 return ret;
Eric Laurentb23d5282013-05-14 15:27:20 -0700761}
762
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800763int platform_start_voice_call(void *platform, uint32_t vsid)
Eric Laurentb23d5282013-05-14 15:27:20 -0700764{
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800765 struct platform_data *my_data = (struct platform_data *)platform;
766 int ret = 0;
767
768 if (my_data->csd != NULL) {
769 ret = my_data->csd->start_voice(vsid);
770 if (ret < 0) {
771 ALOGE("%s: csd_start_voice error %d\n", __func__, ret);
772 }
773 }
774 return ret;
Eric Laurentb23d5282013-05-14 15:27:20 -0700775}
776
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800777int platform_stop_voice_call(void *platform, uint32_t vsid)
Eric Laurentb23d5282013-05-14 15:27:20 -0700778{
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800779 struct platform_data *my_data = (struct platform_data *)platform;
780 int ret = 0;
781
782 if (my_data->csd != NULL) {
783 ret = my_data->csd->stop_voice(vsid);
784 if (ret < 0) {
785 ALOGE("%s: csd_stop_voice error %d\n", __func__, ret);
786 }
787 }
788 return ret;
Eric Laurentb23d5282013-05-14 15:27:20 -0700789}
790
791int platform_set_voice_volume(void *platform, int volume)
792{
793 struct platform_data *my_data = (struct platform_data *)platform;
794 struct audio_device *adev = my_data->adev;
795 struct mixer_ctl *ctl;
sangwoo53b2cf02013-07-25 19:18:44 -0700796 const char *mixer_ctl_name = "Voice Rx Gain";
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800797 int vol_index = 0, ret = 0;
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700798 uint32_t set_values[ ] = {0,
799 ALL_SESSION_VSID,
800 DEFAULT_VOLUME_RAMP_DURATION_MS};
Eric Laurentb23d5282013-05-14 15:27:20 -0700801
802 // Voice volume levels are mapped to adsp volume levels as follows.
803 // 100 -> 5, 80 -> 4, 60 -> 3, 40 -> 2, 20 -> 1 0 -> 0
804 // But this values don't changed in kernel. So, below change is need.
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700805 vol_index = (int)percent_to_index(volume, MIN_VOL_INDEX, MAX_VOL_INDEX);
806 set_values[0] = vol_index;
Eric Laurentb23d5282013-05-14 15:27:20 -0700807
808 ctl = mixer_get_ctl_by_name(adev->mixer, mixer_ctl_name);
809 if (!ctl) {
810 ALOGE("%s: Could not get ctl for mixer cmd - %s",
811 __func__, mixer_ctl_name);
812 return -EINVAL;
813 }
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700814 ALOGV("Setting voice volume index: %d", set_values[0]);
815 mixer_ctl_set_array(ctl, set_values, ARRAY_SIZE(set_values));
Eric Laurentb23d5282013-05-14 15:27:20 -0700816
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800817 if (my_data->csd != NULL) {
818 ret = my_data->csd->volume(ALL_SESSION_VSID, volume);
819 if (ret < 0) {
820 ALOGE("%s: csd_volume error %d", __func__, ret);
821 }
822 }
823 return ret;
Eric Laurentb23d5282013-05-14 15:27:20 -0700824}
825
826int platform_set_mic_mute(void *platform, bool state)
827{
828 struct platform_data *my_data = (struct platform_data *)platform;
829 struct audio_device *adev = my_data->adev;
830 struct mixer_ctl *ctl;
831 const char *mixer_ctl_name = "Voice Tx Mute";
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800832 int ret = 0;
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700833 uint32_t set_values[ ] = {0,
834 ALL_SESSION_VSID,
835 DEFAULT_VOLUME_RAMP_DURATION_MS};
Eric Laurentb23d5282013-05-14 15:27:20 -0700836
Narsinga Rao Chella05573b72013-11-15 15:21:40 -0800837 set_values[0] = state;
838 ctl = mixer_get_ctl_by_name(adev->mixer, mixer_ctl_name);
839 if (!ctl) {
840 ALOGE("%s: Could not get ctl for mixer cmd - %s",
841 __func__, mixer_ctl_name);
842 return -EINVAL;
843 }
844 ALOGV("Setting voice mute state: %d", state);
845 mixer_ctl_set_array(ctl, set_values, ARRAY_SIZE(set_values));
Eric Laurentb23d5282013-05-14 15:27:20 -0700846
Narsinga Rao Chella05573b72013-11-15 15:21:40 -0800847 if (my_data->csd != NULL) {
848 ret = my_data->csd->mic_mute(ALL_SESSION_VSID, state);
849 if (ret < 0) {
850 ALOGE("%s: csd_mic_mute error %d", __func__, ret);
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -0800851 }
852 }
853 return ret;
Eric Laurentb23d5282013-05-14 15:27:20 -0700854}
855
856snd_device_t platform_get_output_snd_device(void *platform, audio_devices_t devices)
857{
858 struct platform_data *my_data = (struct platform_data *)platform;
859 struct audio_device *adev = my_data->adev;
860 audio_mode_t mode = adev->mode;
861 snd_device_t snd_device = SND_DEVICE_NONE;
862
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -0700863 audio_channel_mask_t channel_mask = (adev->active_input == NULL) ?
864 AUDIO_CHANNEL_IN_MONO : adev->active_input->channel_mask;
865 int channel_count = popcount(channel_mask);
866
Eric Laurentb23d5282013-05-14 15:27:20 -0700867 ALOGV("%s: enter: output devices(%#x)", __func__, devices);
868 if (devices == AUDIO_DEVICE_NONE ||
869 devices & AUDIO_DEVICE_BIT_IN) {
870 ALOGV("%s: Invalid output devices (%#x)", __func__, devices);
871 goto exit;
872 }
873
Mingming Yin4a72d652014-01-03 18:54:18 -0800874 if (popcount(devices) == 2) {
875 if (devices == (AUDIO_DEVICE_OUT_WIRED_HEADPHONE |
876 AUDIO_DEVICE_OUT_SPEAKER)) {
877 snd_device = SND_DEVICE_OUT_SPEAKER_AND_HEADPHONES;
878 } else if (devices == (AUDIO_DEVICE_OUT_WIRED_HEADSET |
879 AUDIO_DEVICE_OUT_SPEAKER)) {
880 if (audio_extn_get_anc_enabled())
881 snd_device = SND_DEVICE_OUT_SPEAKER_AND_ANC_HEADSET;
882 else
883 snd_device = SND_DEVICE_OUT_SPEAKER_AND_HEADPHONES;
884 } else if (devices == (AUDIO_DEVICE_OUT_AUX_DIGITAL |
885 AUDIO_DEVICE_OUT_SPEAKER)) {
886 snd_device = SND_DEVICE_OUT_SPEAKER_AND_HDMI;
887 } else if (devices == (AUDIO_DEVICE_OUT_ANLG_DOCK_HEADSET |
888 AUDIO_DEVICE_OUT_SPEAKER)) {
889 snd_device = SND_DEVICE_OUT_SPEAKER_AND_USB_HEADSET;
890 } else {
891 ALOGE("%s: Invalid combo device(%#x)", __func__, devices);
892 goto exit;
893 }
894 if (snd_device != SND_DEVICE_NONE) {
895 goto exit;
896 }
897 }
898
899 if (popcount(devices) != 1) {
900 ALOGE("%s: Invalid output devices(%#x)", __func__, devices);
901 goto exit;
902 }
903
Narsinga Rao Chella05573b72013-11-15 15:21:40 -0800904 if ((mode == AUDIO_MODE_IN_CALL) ||
905 voice_extn_compress_voip_is_active(adev)) {
Eric Laurentb23d5282013-05-14 15:27:20 -0700906 if (devices & AUDIO_DEVICE_OUT_WIRED_HEADPHONE ||
907 devices & AUDIO_DEVICE_OUT_WIRED_HEADSET) {
Narsinga Rao Chella05573b72013-11-15 15:21:40 -0800908 if ((adev->voice.tty_mode != TTY_MODE_OFF) &&
909 !voice_extn_compress_voip_is_active(adev)) {
910 switch (adev->voice.tty_mode) {
911 case TTY_MODE_FULL:
912 snd_device = SND_DEVICE_OUT_VOICE_TTY_FULL_HEADPHONES;
913 break;
914 case TTY_MODE_VCO:
915 snd_device = SND_DEVICE_OUT_VOICE_TTY_VCO_HEADPHONES;
916 break;
917 case TTY_MODE_HCO:
918 snd_device = SND_DEVICE_OUT_VOICE_TTY_HCO_HANDSET;
919 break;
920 default:
921 ALOGE("%s: Invalid TTY mode (%#x)",
922 __func__, adev->voice.tty_mode);
923 }
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700924 } else if (audio_extn_get_anc_enabled()) {
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -0700925 if (audio_extn_should_use_fb_anc())
926 snd_device = SND_DEVICE_OUT_VOICE_ANC_FB_HEADSET;
927 else
928 snd_device = SND_DEVICE_OUT_VOICE_ANC_HEADSET;
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700929 } else {
Eric Laurentb23d5282013-05-14 15:27:20 -0700930 snd_device = SND_DEVICE_OUT_VOICE_HEADPHONES;
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700931 }
Eric Laurentb23d5282013-05-14 15:27:20 -0700932 } else if (devices & AUDIO_DEVICE_OUT_ALL_SCO) {
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700933 if (my_data->btsco_sample_rate == SAMPLE_RATE_16KHZ)
934 snd_device = SND_DEVICE_OUT_BT_SCO_WB;
935 else
936 snd_device = SND_DEVICE_OUT_BT_SCO;
Eric Laurentb23d5282013-05-14 15:27:20 -0700937 } else if (devices & AUDIO_DEVICE_OUT_SPEAKER) {
938 snd_device = SND_DEVICE_OUT_VOICE_SPEAKER;
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700939 } else if (devices & AUDIO_DEVICE_OUT_ANLG_DOCK_HEADSET ||
940 devices & AUDIO_DEVICE_OUT_DGTL_DOCK_HEADSET) {
941 snd_device = SND_DEVICE_OUT_USB_HEADSET;
Apoorv Raghuvanshi6e262842013-10-06 14:39:35 -0700942 } else if (devices & AUDIO_DEVICE_OUT_FM_TX) {
943 snd_device = SND_DEVICE_OUT_TRANSMISSION_FM;
Eric Laurentb23d5282013-05-14 15:27:20 -0700944 } else if (devices & AUDIO_DEVICE_OUT_EARPIECE) {
Ravi Kumar Alamandaceb40822013-11-06 11:01:47 -0800945 if (audio_extn_should_use_handset_anc(channel_count))
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -0700946 snd_device = SND_DEVICE_OUT_ANC_HANDSET;
Eric Laurentb23d5282013-05-14 15:27:20 -0700947 else
Mingming Yin8e5a4f62013-10-07 15:23:41 -0700948 snd_device = SND_DEVICE_OUT_VOICE_HANDSET;
Eric Laurentb23d5282013-05-14 15:27:20 -0700949 }
950 if (snd_device != SND_DEVICE_NONE) {
951 goto exit;
952 }
953 }
954
Eric Laurentb23d5282013-05-14 15:27:20 -0700955 if (devices & AUDIO_DEVICE_OUT_WIRED_HEADPHONE ||
956 devices & AUDIO_DEVICE_OUT_WIRED_HEADSET) {
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -0700957 if (devices & AUDIO_DEVICE_OUT_WIRED_HEADSET
958 && audio_extn_get_anc_enabled()) {
959 if (audio_extn_should_use_fb_anc())
960 snd_device = SND_DEVICE_OUT_ANC_FB_HEADSET;
961 else
962 snd_device = SND_DEVICE_OUT_ANC_HEADSET;
963 }
964 else
965 snd_device = SND_DEVICE_OUT_HEADPHONES;
Eric Laurentb23d5282013-05-14 15:27:20 -0700966 } else if (devices & AUDIO_DEVICE_OUT_SPEAKER) {
967 if (adev->speaker_lr_swap)
968 snd_device = SND_DEVICE_OUT_SPEAKER_REVERSE;
969 else
970 snd_device = SND_DEVICE_OUT_SPEAKER;
971 } else if (devices & AUDIO_DEVICE_OUT_ALL_SCO) {
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -0700972 if (my_data->btsco_sample_rate == SAMPLE_RATE_16KHZ)
973 snd_device = SND_DEVICE_OUT_BT_SCO_WB;
974 else
975 snd_device = SND_DEVICE_OUT_BT_SCO;
Eric Laurentb23d5282013-05-14 15:27:20 -0700976 } else if (devices & AUDIO_DEVICE_OUT_AUX_DIGITAL) {
977 snd_device = SND_DEVICE_OUT_HDMI ;
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700978 } else if (devices & AUDIO_DEVICE_OUT_ANLG_DOCK_HEADSET ||
979 devices & AUDIO_DEVICE_OUT_DGTL_DOCK_HEADSET) {
980 snd_device = SND_DEVICE_OUT_USB_HEADSET;
Apoorv Raghuvanshi6e262842013-10-06 14:39:35 -0700981 } else if (devices & AUDIO_DEVICE_OUT_FM_TX) {
982 snd_device = SND_DEVICE_OUT_TRANSMISSION_FM;
Eric Laurentb23d5282013-05-14 15:27:20 -0700983 } else if (devices & AUDIO_DEVICE_OUT_EARPIECE) {
984 snd_device = SND_DEVICE_OUT_HANDSET;
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -0700985 } else if (devices & AUDIO_DEVICE_OUT_PROXY) {
986 ALOGD("%s: setting sink capability for Proxy", __func__);
987 audio_extn_set_afe_proxy_channel_mixer(adev);
988 snd_device = SND_DEVICE_OUT_AFE_PROXY;
Eric Laurentb23d5282013-05-14 15:27:20 -0700989 } else {
990 ALOGE("%s: Unknown device(s) %#x", __func__, devices);
991 }
992exit:
993 ALOGV("%s: exit: snd_device(%s)", __func__, device_table[snd_device]);
994 return snd_device;
995}
996
997snd_device_t platform_get_input_snd_device(void *platform, audio_devices_t out_device)
998{
999 struct platform_data *my_data = (struct platform_data *)platform;
1000 struct audio_device *adev = my_data->adev;
1001 audio_source_t source = (adev->active_input == NULL) ?
1002 AUDIO_SOURCE_DEFAULT : adev->active_input->source;
1003
1004 audio_mode_t mode = adev->mode;
1005 audio_devices_t in_device = ((adev->active_input == NULL) ?
1006 AUDIO_DEVICE_NONE : adev->active_input->device)
1007 & ~AUDIO_DEVICE_BIT_IN;
1008 audio_channel_mask_t channel_mask = (adev->active_input == NULL) ?
1009 AUDIO_CHANNEL_IN_MONO : adev->active_input->channel_mask;
1010 snd_device_t snd_device = SND_DEVICE_NONE;
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -07001011 int channel_count = popcount(channel_mask);
Eric Laurentb23d5282013-05-14 15:27:20 -07001012
1013 ALOGV("%s: enter: out_device(%#x) in_device(%#x)",
1014 __func__, out_device, in_device);
Helen Zeng067b96b2013-11-26 12:10:29 -08001015 if ((out_device != AUDIO_DEVICE_NONE) && ((mode == AUDIO_MODE_IN_CALL) ||
1016 voice_extn_compress_voip_is_active(adev))) {
Narsinga Rao Chella05573b72013-11-15 15:21:40 -08001017 if ((adev->voice.tty_mode != TTY_MODE_OFF) &&
1018 !voice_extn_compress_voip_is_active(adev)) {
Eric Laurentb23d5282013-05-14 15:27:20 -07001019 if (out_device & AUDIO_DEVICE_OUT_WIRED_HEADPHONE ||
1020 out_device & AUDIO_DEVICE_OUT_WIRED_HEADSET) {
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001021 switch (adev->voice.tty_mode) {
Eric Laurentb23d5282013-05-14 15:27:20 -07001022 case TTY_MODE_FULL:
1023 snd_device = SND_DEVICE_IN_VOICE_TTY_FULL_HEADSET_MIC;
1024 break;
1025 case TTY_MODE_VCO:
1026 snd_device = SND_DEVICE_IN_VOICE_TTY_VCO_HANDSET_MIC;
1027 break;
1028 case TTY_MODE_HCO:
1029 snd_device = SND_DEVICE_IN_VOICE_TTY_HCO_HEADSET_MIC;
1030 break;
1031 default:
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001032 ALOGE("%s: Invalid TTY mode (%#x)",
1033 __func__, adev->voice.tty_mode);
Eric Laurentb23d5282013-05-14 15:27:20 -07001034 }
1035 goto exit;
1036 }
1037 }
1038 if (out_device & AUDIO_DEVICE_OUT_EARPIECE ||
1039 out_device & AUDIO_DEVICE_OUT_WIRED_HEADPHONE) {
Apoorv Raghuvanshi9eaf94e2013-10-04 16:13:44 -07001040 if (out_device & AUDIO_DEVICE_OUT_EARPIECE &&
1041 audio_extn_should_use_handset_anc(channel_count)) {
1042 snd_device = SND_DEVICE_IN_AANC_HANDSET_MIC;
1043 } else if (my_data->fluence_type == FLUENCE_NONE ||
Mingming Yin8e5a4f62013-10-07 15:23:41 -07001044 my_data->fluence_in_voice_call == false) {
Eric Laurentb23d5282013-05-14 15:27:20 -07001045 snd_device = SND_DEVICE_IN_HANDSET_MIC;
Laxminath Kasam7294f522013-12-11 05:07:00 +05301046 set_echo_reference(adev->mixer, EC_REF_RX);
Eric Laurentb23d5282013-05-14 15:27:20 -07001047 } else {
Ravi Kumar Alamandaceb40822013-11-06 11:01:47 -08001048 snd_device = SND_DEVICE_IN_VOICE_DMIC;
Mingming Yin8e5a4f62013-10-07 15:23:41 -07001049 adev->acdb_settings |= DMIC_FLAG;
Eric Laurentb23d5282013-05-14 15:27:20 -07001050 }
1051 } else if (out_device & AUDIO_DEVICE_OUT_WIRED_HEADSET) {
1052 snd_device = SND_DEVICE_IN_VOICE_HEADSET_MIC;
1053 } else if (out_device & AUDIO_DEVICE_OUT_ALL_SCO) {
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001054 if (my_data->btsco_sample_rate == SAMPLE_RATE_16KHZ)
1055 snd_device = SND_DEVICE_IN_BT_SCO_MIC_WB;
1056 else
1057 snd_device = SND_DEVICE_IN_BT_SCO_MIC;
Eric Laurentb23d5282013-05-14 15:27:20 -07001058 } else if (out_device & AUDIO_DEVICE_OUT_SPEAKER) {
Mingming Yin8e5a4f62013-10-07 15:23:41 -07001059 if (my_data->fluence_type != FLUENCE_NONE &&
1060 my_data->fluence_in_voice_call &&
1061 my_data->fluence_in_spkr_mode) {
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -08001062 if(my_data->fluence_type & FLUENCE_QUAD_MIC) {
Mingming Yin8e5a4f62013-10-07 15:23:41 -07001063 adev->acdb_settings |= QMIC_FLAG;
1064 snd_device = SND_DEVICE_IN_VOICE_SPEAKER_QMIC;
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -08001065 } else {
1066 adev->acdb_settings |= DMIC_FLAG;
1067 snd_device = SND_DEVICE_IN_VOICE_SPEAKER_DMIC;
Mingming Yin8e5a4f62013-10-07 15:23:41 -07001068 }
Eric Laurentb23d5282013-05-14 15:27:20 -07001069 } else {
1070 snd_device = SND_DEVICE_IN_VOICE_SPEAKER_MIC;
1071 }
1072 }
1073 } else if (source == AUDIO_SOURCE_CAMCORDER) {
1074 if (in_device & AUDIO_DEVICE_IN_BUILTIN_MIC ||
1075 in_device & AUDIO_DEVICE_IN_BACK_MIC) {
1076 snd_device = SND_DEVICE_IN_CAMCORDER_MIC;
1077 }
1078 } else if (source == AUDIO_SOURCE_VOICE_RECOGNITION) {
1079 if (in_device & AUDIO_DEVICE_IN_BUILTIN_MIC) {
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -08001080 if (channel_count == 2) {
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -08001081 snd_device = SND_DEVICE_IN_VOICE_REC_DMIC_STEREO;
Mingming Yin8e5a4f62013-10-07 15:23:41 -07001082 adev->acdb_settings |= DMIC_FLAG;
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -08001083 } else if (adev->active_input->enable_ns)
1084 snd_device = SND_DEVICE_IN_VOICE_REC_MIC_NS;
1085 else if (my_data->fluence_type != FLUENCE_NONE &&
1086 my_data->fluence_in_voice_rec) {
1087 snd_device = SND_DEVICE_IN_VOICE_REC_DMIC_FLUENCE;
1088 adev->acdb_settings |= DMIC_FLAG;
1089 } else {
1090 snd_device = SND_DEVICE_IN_VOICE_REC_MIC;
1091 }
Eric Laurentb23d5282013-05-14 15:27:20 -07001092 }
1093 } else if (source == AUDIO_SOURCE_VOICE_COMMUNICATION) {
1094 if (out_device & AUDIO_DEVICE_OUT_SPEAKER)
1095 in_device = AUDIO_DEVICE_IN_BACK_MIC;
1096 if (adev->active_input) {
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -08001097 if (adev->active_input->enable_aec &&
1098 adev->active_input->enable_ns) {
Eric Laurentb23d5282013-05-14 15:27:20 -07001099 if (in_device & AUDIO_DEVICE_IN_BACK_MIC) {
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -08001100 if (my_data->fluence_type & FLUENCE_DUAL_MIC &&
1101 my_data->fluence_in_spkr_mode) {
1102 snd_device = SND_DEVICE_IN_SPEAKER_DMIC_AEC_NS;
1103 adev->acdb_settings |= DMIC_FLAG;
1104 } else
1105 snd_device = SND_DEVICE_IN_SPEAKER_MIC_AEC_NS;
Eric Laurentb23d5282013-05-14 15:27:20 -07001106 } else if (in_device & AUDIO_DEVICE_IN_BUILTIN_MIC) {
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -08001107 if (my_data->fluence_type & FLUENCE_DUAL_MIC) {
1108 snd_device = SND_DEVICE_IN_HANDSET_DMIC_AEC_NS;
1109 adev->acdb_settings |= DMIC_FLAG;
1110 } else
1111 snd_device = SND_DEVICE_IN_HANDSET_MIC_AEC_NS;
Eric Laurentb23d5282013-05-14 15:27:20 -07001112 } else if (in_device & AUDIO_DEVICE_IN_WIRED_HEADSET) {
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -08001113 snd_device = SND_DEVICE_IN_HEADSET_MIC_FLUENCE;
Eric Laurentb23d5282013-05-14 15:27:20 -07001114 }
Laxminath Kasam7294f522013-12-11 05:07:00 +05301115 set_echo_reference(adev->mixer, EC_REF_RX);
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -08001116 } else if (adev->active_input->enable_aec) {
1117 if (in_device & AUDIO_DEVICE_IN_BACK_MIC) {
1118 if (my_data->fluence_type & FLUENCE_DUAL_MIC) {
1119 snd_device = SND_DEVICE_IN_SPEAKER_DMIC_AEC;
1120 adev->acdb_settings |= DMIC_FLAG;
1121 } else
1122 snd_device = SND_DEVICE_IN_SPEAKER_MIC_AEC;
1123 } else if (in_device & AUDIO_DEVICE_IN_BUILTIN_MIC) {
1124 if (my_data->fluence_type & FLUENCE_DUAL_MIC) {
1125 snd_device = SND_DEVICE_IN_HANDSET_DMIC_AEC;
1126 adev->acdb_settings |= DMIC_FLAG;
1127 } else
1128 snd_device = SND_DEVICE_IN_HANDSET_MIC_AEC;
1129 } else if (in_device & AUDIO_DEVICE_IN_WIRED_HEADSET) {
1130 snd_device = SND_DEVICE_IN_HEADSET_MIC_FLUENCE;
1131 }
Laxminath Kasam7294f522013-12-11 05:07:00 +05301132 set_echo_reference(adev->mixer, EC_REF_RX);
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -08001133 } else if (adev->active_input->enable_ns) {
1134 if (in_device & AUDIO_DEVICE_IN_BACK_MIC) {
1135 if (my_data->fluence_type & FLUENCE_DUAL_MIC) {
1136 snd_device = SND_DEVICE_IN_SPEAKER_DMIC_NS;
1137 adev->acdb_settings |= DMIC_FLAG;
1138 } else
1139 snd_device = SND_DEVICE_IN_SPEAKER_MIC_NS;
1140 } else if (in_device & AUDIO_DEVICE_IN_BUILTIN_MIC) {
1141 if (my_data->fluence_type & FLUENCE_DUAL_MIC) {
1142 snd_device = SND_DEVICE_IN_HANDSET_DMIC_NS;
1143 adev->acdb_settings |= DMIC_FLAG;
1144 } else
1145 snd_device = SND_DEVICE_IN_HANDSET_MIC_NS;
1146 } else if (in_device & AUDIO_DEVICE_IN_WIRED_HEADSET) {
1147 snd_device = SND_DEVICE_IN_HEADSET_MIC_FLUENCE;
1148 }
1149 set_echo_reference(adev->mixer, "NONE");
Eric Laurentb23d5282013-05-14 15:27:20 -07001150 } else
1151 set_echo_reference(adev->mixer, "NONE");
1152 }
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -08001153 } else if (source == AUDIO_SOURCE_MIC) {
Apoorv Raghuvanshic0536542013-11-14 16:25:59 -08001154 if (in_device & AUDIO_DEVICE_IN_BUILTIN_MIC &&
1155 channel_count == 1 ) {
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -08001156 if(my_data->fluence_type & FLUENCE_DUAL_MIC &&
1157 my_data->fluence_in_audio_rec)
1158 snd_device = SND_DEVICE_IN_HANDSET_DMIC;
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -08001159 }
Mingming Yinab429782013-11-07 11:16:55 -08001160 } else if (source == AUDIO_SOURCE_FM_RX ||
Ravi Kumar Alamanda198185e2013-11-07 15:42:19 -08001161 source == AUDIO_SOURCE_FM_RX_A2DP) {
Preetam Singh Ranawatde84f1a2013-11-01 14:58:16 -07001162 snd_device = SND_DEVICE_IN_CAPTURE_FM;
Eric Laurentb23d5282013-05-14 15:27:20 -07001163 } else if (source == AUDIO_SOURCE_DEFAULT) {
1164 goto exit;
1165 }
1166
1167
1168 if (snd_device != SND_DEVICE_NONE) {
1169 goto exit;
1170 }
1171
1172 if (in_device != AUDIO_DEVICE_NONE &&
1173 !(in_device & AUDIO_DEVICE_IN_VOICE_CALL) &&
1174 !(in_device & AUDIO_DEVICE_IN_COMMUNICATION)) {
1175 if (in_device & AUDIO_DEVICE_IN_BUILTIN_MIC) {
Apoorv Raghuvanshi6178a3f2013-10-19 12:38:54 -07001176 if (audio_extn_ssr_get_enabled() && channel_count == 6)
1177 snd_device = SND_DEVICE_IN_QUAD_MIC;
Ravi Kumar Alamandafae42112013-11-07 23:31:54 -08001178 else if (channel_count == 2)
Apoorv Raghuvanshi6bd8dbf2013-10-19 18:37:52 -07001179 snd_device = SND_DEVICE_IN_HANDSET_STEREO_DMIC;
Apoorv Raghuvanshi6178a3f2013-10-19 12:38:54 -07001180 else
1181 snd_device = SND_DEVICE_IN_HANDSET_MIC;
Eric Laurentb23d5282013-05-14 15:27:20 -07001182 } else if (in_device & AUDIO_DEVICE_IN_BACK_MIC) {
1183 snd_device = SND_DEVICE_IN_SPEAKER_MIC;
1184 } else if (in_device & AUDIO_DEVICE_IN_WIRED_HEADSET) {
1185 snd_device = SND_DEVICE_IN_HEADSET_MIC;
1186 } else if (in_device & AUDIO_DEVICE_IN_BLUETOOTH_SCO_HEADSET) {
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001187 if (my_data->btsco_sample_rate == SAMPLE_RATE_16KHZ)
1188 snd_device = SND_DEVICE_IN_BT_SCO_MIC_WB;
1189 else
1190 snd_device = SND_DEVICE_IN_BT_SCO_MIC;
Eric Laurentb23d5282013-05-14 15:27:20 -07001191 } else if (in_device & AUDIO_DEVICE_IN_AUX_DIGITAL) {
1192 snd_device = SND_DEVICE_IN_HDMI_MIC;
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -07001193 } else if (in_device & AUDIO_DEVICE_IN_ANLG_DOCK_HEADSET ||
1194 in_device & AUDIO_DEVICE_IN_DGTL_DOCK_HEADSET) {
1195 snd_device = SND_DEVICE_IN_USB_HEADSET_MIC;
Apoorv Raghuvanshi6e262842013-10-06 14:39:35 -07001196 } else if (in_device & AUDIO_DEVICE_IN_FM_RX) {
1197 snd_device = SND_DEVICE_IN_CAPTURE_FM;
Eric Laurentb23d5282013-05-14 15:27:20 -07001198 } else {
1199 ALOGE("%s: Unknown input device(s) %#x", __func__, in_device);
1200 ALOGW("%s: Using default handset-mic", __func__);
1201 snd_device = SND_DEVICE_IN_HANDSET_MIC;
1202 }
1203 } else {
1204 if (out_device & AUDIO_DEVICE_OUT_EARPIECE) {
1205 snd_device = SND_DEVICE_IN_HANDSET_MIC;
1206 } else if (out_device & AUDIO_DEVICE_OUT_WIRED_HEADSET) {
1207 snd_device = SND_DEVICE_IN_HEADSET_MIC;
1208 } else if (out_device & AUDIO_DEVICE_OUT_SPEAKER) {
Apoorv Raghuvanshi6bd8dbf2013-10-19 18:37:52 -07001209 if (channel_count > 1)
1210 snd_device = SND_DEVICE_IN_SPEAKER_STEREO_DMIC;
1211 else
1212 snd_device = SND_DEVICE_IN_SPEAKER_MIC;
Eric Laurentb23d5282013-05-14 15:27:20 -07001213 } else if (out_device & AUDIO_DEVICE_OUT_WIRED_HEADPHONE) {
1214 snd_device = SND_DEVICE_IN_HANDSET_MIC;
1215 } else if (out_device & AUDIO_DEVICE_OUT_BLUETOOTH_SCO_HEADSET) {
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001216 if (my_data->btsco_sample_rate == SAMPLE_RATE_16KHZ)
1217 snd_device = SND_DEVICE_IN_BT_SCO_MIC_WB;
1218 else
1219 snd_device = SND_DEVICE_IN_BT_SCO_MIC;
Eric Laurentb23d5282013-05-14 15:27:20 -07001220 } else if (out_device & AUDIO_DEVICE_OUT_AUX_DIGITAL) {
1221 snd_device = SND_DEVICE_IN_HDMI_MIC;
Apoorv Raghuvanshi5792d4b2013-10-07 18:40:05 -07001222 } else if (out_device & AUDIO_DEVICE_OUT_ANLG_DOCK_HEADSET ||
1223 out_device & AUDIO_DEVICE_OUT_DGTL_DOCK_HEADSET) {
1224 snd_device = SND_DEVICE_IN_USB_HEADSET_MIC;
Eric Laurentb23d5282013-05-14 15:27:20 -07001225 } else {
1226 ALOGE("%s: Unknown output device(s) %#x", __func__, out_device);
1227 ALOGW("%s: Using default handset-mic", __func__);
1228 snd_device = SND_DEVICE_IN_HANDSET_MIC;
1229 }
1230 }
1231exit:
1232 ALOGV("%s: exit: in_snd_device(%s)", __func__, device_table[snd_device]);
1233 return snd_device;
1234}
1235
1236int platform_set_hdmi_channels(void *platform, int channel_count)
1237{
1238 struct platform_data *my_data = (struct platform_data *)platform;
1239 struct audio_device *adev = my_data->adev;
1240 struct mixer_ctl *ctl;
1241 const char *channel_cnt_str = NULL;
1242 const char *mixer_ctl_name = "HDMI_RX Channels";
1243 switch (channel_count) {
1244 case 8:
1245 channel_cnt_str = "Eight"; break;
1246 case 7:
1247 channel_cnt_str = "Seven"; break;
1248 case 6:
1249 channel_cnt_str = "Six"; break;
1250 case 5:
1251 channel_cnt_str = "Five"; break;
1252 case 4:
1253 channel_cnt_str = "Four"; break;
1254 case 3:
1255 channel_cnt_str = "Three"; break;
1256 default:
1257 channel_cnt_str = "Two"; break;
1258 }
1259 ctl = mixer_get_ctl_by_name(adev->mixer, mixer_ctl_name);
1260 if (!ctl) {
1261 ALOGE("%s: Could not get ctl for mixer cmd - %s",
1262 __func__, mixer_ctl_name);
1263 return -EINVAL;
1264 }
1265 ALOGV("HDMI channel count: %s", channel_cnt_str);
1266 mixer_ctl_set_enum_by_string(ctl, channel_cnt_str);
1267 return 0;
1268}
1269
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -07001270int platform_edid_get_max_channels(void *platform)
Eric Laurentb23d5282013-05-14 15:27:20 -07001271{
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -07001272 struct platform_data *my_data = (struct platform_data *)platform;
1273 struct audio_device *adev = my_data->adev;
Eric Laurentb23d5282013-05-14 15:27:20 -07001274 char block[MAX_SAD_BLOCKS * SAD_BLOCK_SIZE];
1275 char *sad = block;
1276 int num_audio_blocks;
1277 int channel_count;
1278 int max_channels = 0;
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -07001279 int i, ret, count;
Eric Laurentb23d5282013-05-14 15:27:20 -07001280
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -07001281 struct mixer_ctl *ctl;
1282
1283 ctl = mixer_get_ctl_by_name(adev->mixer, AUDIO_DATA_BLOCK_MIXER_CTL);
1284 if (!ctl) {
1285 ALOGE("%s: Could not get ctl for mixer cmd - %s",
1286 __func__, AUDIO_DATA_BLOCK_MIXER_CTL);
Eric Laurentb23d5282013-05-14 15:27:20 -07001287 return 0;
1288 }
1289
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -07001290 mixer_ctl_update(ctl);
1291
1292 count = mixer_ctl_get_num_values(ctl);
Eric Laurentb23d5282013-05-14 15:27:20 -07001293
1294 /* Read SAD blocks, clamping the maximum size for safety */
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -07001295 if (count > (int)sizeof(block))
1296 count = (int)sizeof(block);
Eric Laurentb23d5282013-05-14 15:27:20 -07001297
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -07001298 ret = mixer_ctl_get_array(ctl, block, count);
1299 if (ret != 0) {
1300 ALOGE("%s: mixer_ctl_get_array() failed to get EDID info", __func__);
1301 return 0;
1302 }
Eric Laurentb23d5282013-05-14 15:27:20 -07001303
1304 /* Calculate the number of SAD blocks */
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -07001305 num_audio_blocks = count / SAD_BLOCK_SIZE;
Eric Laurentb23d5282013-05-14 15:27:20 -07001306
1307 for (i = 0; i < num_audio_blocks; i++) {
1308 /* Only consider LPCM blocks */
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -07001309 if ((sad[0] >> 3) != EDID_FORMAT_LPCM) {
1310 sad += 3;
Eric Laurentb23d5282013-05-14 15:27:20 -07001311 continue;
Haynes Mathew George47cd4cb2013-07-19 11:58:50 -07001312 }
Eric Laurentb23d5282013-05-14 15:27:20 -07001313
1314 channel_count = (sad[0] & 0x7) + 1;
1315 if (channel_count > max_channels)
1316 max_channels = channel_count;
1317
1318 /* Advance to next block */
1319 sad += 3;
1320 }
1321
1322 return max_channels;
1323}
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001324
1325static int platform_set_slowtalk(struct platform_data *my_data, bool state)
1326{
1327 int ret = 0;
1328 struct audio_device *adev = my_data->adev;
1329 struct mixer_ctl *ctl;
1330 const char *mixer_ctl_name = "Slowtalk Enable";
1331 uint32_t set_values[ ] = {0,
1332 ALL_SESSION_VSID};
1333
1334 set_values[0] = state;
1335 ctl = mixer_get_ctl_by_name(adev->mixer, mixer_ctl_name);
1336 if (!ctl) {
1337 ALOGE("%s: Could not get ctl for mixer cmd - %s",
1338 __func__, mixer_ctl_name);
1339 ret = -EINVAL;
1340 } else {
1341 ALOGV("Setting slowtalk state: %d", state);
1342 ret = mixer_ctl_set_array(ctl, set_values, ARRAY_SIZE(set_values));
1343 my_data->slowtalk = state;
1344 }
1345
Vidyakumar Athotad9d9ff32013-11-13 11:46:52 -08001346 if (my_data->csd != NULL) {
1347 ret = my_data->csd->slow_talk(ALL_SESSION_VSID, state);
1348 if (ret < 0) {
1349 ALOGE("%s: csd_client_disable_device, failed, error %d",
1350 __func__, ret);
1351 }
1352 }
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001353 return ret;
1354}
1355
1356int platform_set_parameters(void *platform, struct str_parms *parms)
1357{
1358 struct platform_data *my_data = (struct platform_data *)platform;
1359 char *str;
Vidyakumar Athota3ade2792013-12-02 11:02:20 -08001360 char value[256] = {0};
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001361 int val;
Shiv Maliyappanahalli3e064fd2013-12-16 15:54:40 -08001362 int ret = 0, err;
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001363
1364 ALOGV("%s: enter: %s", __func__, str_parms_to_str(parms));
1365
Shiv Maliyappanahalli3e064fd2013-12-16 15:54:40 -08001366 err = str_parms_get_int(parms, AUDIO_PARAMETER_KEY_BTSCO, &val);
1367 if (err >= 0) {
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001368 str_parms_del(parms, AUDIO_PARAMETER_KEY_BTSCO);
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001369 my_data->btsco_sample_rate = val;
Vidyakumar Athota67c42712013-12-04 14:03:06 -08001370 if (val == SAMPLE_RATE_16KHZ) {
1371 audio_route_apply_path(my_data->adev->audio_route,
1372 "bt-sco-wb-samplerate");
1373 audio_route_update_mixer(my_data->adev->audio_route);
1374 }
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001375 }
1376
Shiv Maliyappanahalli3e064fd2013-12-16 15:54:40 -08001377 err = str_parms_get_str(parms, AUDIO_PARAMETER_KEY_SLOWTALK, value, sizeof(value));
1378 if (err >= 0) {
Vidyakumar Athota3ade2792013-12-02 11:02:20 -08001379 bool state = false;
1380 if (!strncmp("true", value, sizeof("true"))) {
1381 state = true;
1382 }
1383
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001384 str_parms_del(parms, AUDIO_PARAMETER_KEY_SLOWTALK);
Vidyakumar Athota3ade2792013-12-02 11:02:20 -08001385 ret = platform_set_slowtalk(my_data, state);
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001386 if (ret)
1387 ALOGE("%s: Failed to set slow talk err: %d", __func__, ret);
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001388 }
1389
Shiv Maliyappanahalli3e064fd2013-12-16 15:54:40 -08001390 err = str_parms_get_str(parms, AUDIO_PARAMETER_KEY_VOLUME_BOOST,
Ben Rombergerc1dc70d2013-12-19 15:11:17 -08001391 value, sizeof(value));
Shiv Maliyappanahalli3e064fd2013-12-16 15:54:40 -08001392 if (err >= 0) {
Ben Rombergerc1dc70d2013-12-19 15:11:17 -08001393 str_parms_del(parms, AUDIO_PARAMETER_KEY_VOLUME_BOOST);
1394
1395 if (my_data->acdb_reload_vocvoltable == NULL) {
1396 ALOGE("%s: acdb_reload_vocvoltable is NULL", __func__);
1397 } else if (!strcmp(value, "on")) {
1398 if (!my_data->acdb_reload_vocvoltable(VOICE_FEATURE_SET_VOLUME_BOOST)) {
1399 my_data->voice_feature_set = 1;
1400 }
1401 } else {
1402 if (!my_data->acdb_reload_vocvoltable(VOICE_FEATURE_SET_DEFAULT)) {
1403 my_data->voice_feature_set = 0;
1404 }
1405 }
1406 }
1407
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001408 ALOGV("%s: exit with code(%d)", __func__, ret);
1409 return ret;
1410}
1411
Vidyakumar Athota2850d532013-11-19 16:02:12 -08001412int platform_set_incall_recording_session_id(void *platform,
1413 uint32_t session_id, int rec_mode)
Shiv Maliyappanahallida107642013-10-17 11:16:13 -07001414{
1415 int ret = 0;
1416 struct platform_data *my_data = (struct platform_data *)platform;
1417 struct audio_device *adev = my_data->adev;
1418 struct mixer_ctl *ctl;
1419 const char *mixer_ctl_name = "Voc VSID";
1420 int num_ctl_values;
1421 int i;
1422
1423 ctl = mixer_get_ctl_by_name(adev->mixer, mixer_ctl_name);
1424 if (!ctl) {
1425 ALOGE("%s: Could not get ctl for mixer cmd - %s",
1426 __func__, mixer_ctl_name);
1427 ret = -EINVAL;
1428 } else {
1429 num_ctl_values = mixer_ctl_get_num_values(ctl);
1430 for (i = 0; i < num_ctl_values; i++) {
1431 if (mixer_ctl_set_value(ctl, i, session_id)) {
1432 ALOGV("Error: invalid session_id: %x", session_id);
1433 ret = -EINVAL;
1434 break;
1435 }
1436 }
1437 }
1438
Vidyakumar Athota2850d532013-11-19 16:02:12 -08001439 if (my_data->csd != NULL) {
1440 ret = my_data->csd->start_record(ALL_SESSION_VSID, rec_mode);
1441 if (ret < 0) {
1442 ALOGE("%s: csd_client_start_record failed, error %d",
1443 __func__, ret);
1444 }
1445 }
1446
1447 return ret;
1448}
1449
1450int platform_stop_incall_recording_usecase(void *platform)
1451{
1452 int ret = 0;
1453 struct platform_data *my_data = (struct platform_data *)platform;
1454
1455 if (my_data->csd != NULL) {
1456 ret = my_data->csd->stop_record(ALL_SESSION_VSID);
1457 if (ret < 0) {
1458 ALOGE("%s: csd_client_stop_record failed, error %d",
1459 __func__, ret);
1460 }
1461 }
1462
1463 return ret;
1464}
1465
1466int platform_start_incall_music_usecase(void *platform)
1467{
1468 int ret = 0;
1469 struct platform_data *my_data = (struct platform_data *)platform;
1470
1471 if (my_data->csd != NULL) {
1472 ret = my_data->csd->start_playback(ALL_SESSION_VSID);
1473 if (ret < 0) {
1474 ALOGE("%s: csd_client_start_playback failed, error %d",
1475 __func__, ret);
1476 }
1477 }
1478
1479 return ret;
1480}
1481
1482int platform_stop_incall_music_usecase(void *platform)
1483{
1484 int ret = 0;
1485 struct platform_data *my_data = (struct platform_data *)platform;
1486
1487 if (my_data->csd != NULL) {
1488 ret = my_data->csd->stop_playback(ALL_SESSION_VSID);
1489 if (ret < 0) {
1490 ALOGE("%s: csd_client_stop_playback failed, error %d",
1491 __func__, ret);
1492 }
1493 }
1494
Shiv Maliyappanahallida107642013-10-17 11:16:13 -07001495 return ret;
1496}
1497
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001498void platform_get_parameters(void *platform,
1499 struct str_parms *query,
1500 struct str_parms *reply)
1501{
1502 struct platform_data *my_data = (struct platform_data *)platform;
1503 char *str = NULL;
1504 char value[256] = {0};
1505 int ret;
1506 int fluence_type;
1507
1508 ret = str_parms_get_str(query, AUDIO_PARAMETER_KEY_FLUENCE_TYPE,
1509 value, sizeof(value));
1510 if (ret >= 0) {
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -08001511 if (my_data->fluence_type & FLUENCE_QUAD_MIC) {
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001512 strlcpy(value, "fluencepro", sizeof(value));
Ravi Kumar Alamandab034ddb2013-11-06 15:52:18 -08001513 } else if (my_data->fluence_type & FLUENCE_DUAL_MIC) {
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001514 strlcpy(value, "fluence", sizeof(value));
1515 } else {
1516 strlcpy(value, "none", sizeof(value));
1517 }
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001518
1519 str_parms_add_str(reply, AUDIO_PARAMETER_KEY_FLUENCE_TYPE, value);
1520 }
1521
Shiv Maliyappanahalli9d899292013-11-20 14:43:01 -08001522 memset(value, 0, sizeof(value));
1523 ret = str_parms_get_str(query, AUDIO_PARAMETER_KEY_SLOWTALK,
1524 value, sizeof(value));
1525 if (ret >= 0) {
Vidyakumar Athota3ade2792013-12-02 11:02:20 -08001526 str_parms_add_str(reply, AUDIO_PARAMETER_KEY_SLOWTALK,
1527 my_data->slowtalk?"true":"false");
Shiv Maliyappanahalli9d899292013-11-20 14:43:01 -08001528 }
1529
Ben Rombergerc1dc70d2013-12-19 15:11:17 -08001530 ret = str_parms_get_str(query, AUDIO_PARAMETER_KEY_VOLUME_BOOST,
1531 value, sizeof(value));
1532 if (ret >= 0) {
1533 if (my_data->voice_feature_set == VOICE_FEATURE_SET_VOLUME_BOOST) {
1534 strlcpy(value, "on", sizeof(value));
1535 } else {
1536 strlcpy(value, "off", sizeof(value));
1537 }
1538
1539 str_parms_add_str(reply, AUDIO_PARAMETER_KEY_VOLUME_BOOST, value);
1540 }
1541
Shiv Maliyappanahalli34b585f2013-10-01 15:49:05 -07001542 ALOGV("%s: exit: returns - %s", __func__, str_parms_to_str(reply));
1543}
1544
Haynes Mathew George7ff216f2013-09-11 19:51:41 -07001545/* Delay in Us */
1546int64_t platform_render_latency(audio_usecase_t usecase)
1547{
1548 switch (usecase) {
1549 case USECASE_AUDIO_PLAYBACK_DEEP_BUFFER:
1550 return DEEP_BUFFER_PLATFORM_DELAY;
1551 case USECASE_AUDIO_PLAYBACK_LOW_LATENCY:
1552 return LOW_LATENCY_PLATFORM_DELAY;
1553 default:
1554 return 0;
1555 }
1556}
Preetam Singh Ranawatde84f1a2013-11-01 14:58:16 -07001557
Mingming Yine62d7842013-10-25 16:26:03 -07001558int platform_update_usecase_from_source(int source, int usecase)
Preetam Singh Ranawatde84f1a2013-11-01 14:58:16 -07001559{
Mingming Yinab429782013-11-07 11:16:55 -08001560 ALOGV("%s: input source :%d", __func__, source);
1561 if(source == AUDIO_SOURCE_FM_RX_A2DP)
Mingming Yine62d7842013-10-25 16:26:03 -07001562 usecase = USECASE_AUDIO_RECORD_FM_VIRTUAL;
1563 return usecase;
Preetam Singh Ranawatde84f1a2013-11-01 14:58:16 -07001564}
Kiran Kandide144c82013-11-20 15:58:32 -08001565
1566bool platform_listen_update_status(snd_device_t snd_device)
1567{
1568 if ((snd_device >= SND_DEVICE_IN_BEGIN) &&
1569 (snd_device < SND_DEVICE_IN_END) &&
1570 (snd_device != SND_DEVICE_IN_CAPTURE_FM) &&
1571 (snd_device != SND_DEVICE_IN_CAPTURE_VI_FEEDBACK))
1572 return true;
1573 else
1574 return false;
1575}