AudioHardware.cpp revision 16327daa90dffd97f03d24c59ec0a4d38aa94b90
1/*
2** Copyright 2008, Google Inc.
3**
4** Licensed under the Apache License, Version 2.0 (the "License");
5** you may not use this file except in compliance with the License.
6** You may obtain a copy of the License at
7**
8**     http://www.apache.org/licenses/LICENSE-2.0
9**
10** Unless required by applicable law or agreed to in writing, software
11** distributed under the License is distributed on an "AS IS" BASIS,
12** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13** See the License for the specific language governing permissions and
14** limitations under the License.
15*/
16
17#include <math.h>
18
19//#define LOG_NDEBUG 0
20#define LOG_TAG "AudioHardwareMSM72XX"
21#include <utils/Log.h>
22#include <utils/String8.h>
23
24#include <stdio.h>
25#include <unistd.h>
26#include <sys/ioctl.h>
27#include <sys/types.h>
28#include <sys/stat.h>
29#include <dlfcn.h>
30#include <fcntl.h>
31
32// hardware specific functions
33
34#include "AudioHardware.h"
35#include <media/AudioRecord.h>
36
37#define LOG_SND_RPC 0  // Set to 1 to log sound RPC's
38
39namespace android {
40static int audpre_index, tx_iir_index;
41static void * acoustic;
42const uint32_t AudioHardware::inputSamplingRates[] = {
43        8000, 11025, 12000, 16000, 22050, 24000, 32000, 44100, 48000
44};
45// ----------------------------------------------------------------------------
46
47AudioHardware::AudioHardware() :
48    mInit(false), mMicMute(true), mBluetoothNrec(true), mBluetoothId(0),
49    mOutput(0), mSndEndpoints(NULL), mCurSndDevice(-1),
50    SND_DEVICE_CURRENT(-1),
51    SND_DEVICE_HANDSET(-1),
52    SND_DEVICE_SPEAKER(-1),
53    SND_DEVICE_HEADSET(-1),
54    SND_DEVICE_BT(-1),
55    SND_DEVICE_CARKIT(-1),
56    SND_DEVICE_TTY_FULL(-1),
57    SND_DEVICE_TTY_VCO(-1),
58    SND_DEVICE_TTY_HCO(-1),
59    SND_DEVICE_NO_MIC_HEADSET(-1),
60    SND_DEVICE_FM_HEADSET(-1),
61    SND_DEVICE_HEADSET_AND_SPEAKER(-1),
62    SND_DEVICE_FM_SPEAKER(-1),
63    SND_DEVICE_BT_EC_OFF(-1)
64{
65
66    int (*snd_get_num)();
67    int (*snd_get_endpoint)(int, msm_snd_endpoint *);
68    int (*set_acoustic_parameters)();
69
70    struct msm_snd_endpoint *ept;
71
72    acoustic = ::dlopen("/system/lib/libhtc_acoustic.so", RTLD_NOW);
73    if (acoustic == NULL ) {
74        LOGE("Could not open libhtc_acoustic.so");
75        /* this is not really an error on non-htc devices... */
76        mNumSndEndpoints = 0;
77        mInit = true;
78        return;
79    }
80
81    set_acoustic_parameters = (int (*)(void))::dlsym(acoustic, "set_acoustic_parameters");
82    if ((*set_acoustic_parameters) == 0 ) {
83        LOGE("Could not open set_acoustic_parameters()");
84        return;
85    }
86
87    int rc = set_acoustic_parameters();
88    if (rc < 0) {
89        LOGE("Could not set acoustic parameters to share memory: %d", rc);
90//        return;
91    }
92
93    snd_get_num = (int (*)(void))::dlsym(acoustic, "snd_get_num_endpoints");
94    if ((*snd_get_num) == 0 ) {
95        LOGE("Could not open snd_get_num()");
96//        return;
97    }
98
99    mNumSndEndpoints = snd_get_num();
100    LOGD("mNumSndEndpoints = %d", mNumSndEndpoints);
101    mSndEndpoints = new msm_snd_endpoint[mNumSndEndpoints];
102    mInit = true;
103    LOGV("constructed %d SND endpoints)", mNumSndEndpoints);
104    ept = mSndEndpoints;
105    snd_get_endpoint = (int (*)(int, msm_snd_endpoint *))::dlsym(acoustic, "snd_get_endpoint");
106    if ((*snd_get_endpoint) == 0 ) {
107        LOGE("Could not open snd_get_endpoint()");
108        return;
109    }
110
111    for (int cnt = 0; cnt < mNumSndEndpoints; cnt++, ept++) {
112        ept->id = cnt;
113        snd_get_endpoint(cnt, ept);
114#define CHECK_FOR(desc) \
115        if (!strcmp(ept->name, #desc)) { \
116            SND_DEVICE_##desc = ept->id; \
117            LOGD("BT MATCH " #desc); \
118        } else
119        CHECK_FOR(CURRENT)
120        CHECK_FOR(HANDSET)
121        CHECK_FOR(SPEAKER)
122        CHECK_FOR(BT)
123        CHECK_FOR(BT_EC_OFF)
124        CHECK_FOR(HEADSET)
125        CHECK_FOR(CARKIT)
126        CHECK_FOR(TTY_FULL)
127        CHECK_FOR(TTY_VCO)
128        CHECK_FOR(TTY_HCO)
129        CHECK_FOR(NO_MIC_HEADSET)
130        CHECK_FOR(FM_HEADSET)
131        CHECK_FOR(FM_SPEAKER)
132        CHECK_FOR(HEADSET_AND_SPEAKER) {}
133#undef CHECK_FOR
134    }
135}
136
137AudioHardware::~AudioHardware()
138{
139    for (size_t index = 0; index < mInputs.size(); index++) {
140        closeInputStream((AudioStreamIn*)mInputs[index]);
141    }
142    mInputs.clear();
143    closeOutputStream((AudioStreamOut*)mOutput);
144    delete [] mSndEndpoints;
145    if (acoustic) {
146        ::dlclose(acoustic);
147        acoustic = 0;
148    }
149    mInit = false;
150}
151
152status_t AudioHardware::initCheck()
153{
154    return mInit ? NO_ERROR : NO_INIT;
155}
156
157AudioStreamOut* AudioHardware::openOutputStream(
158        uint32_t devices, int *format, uint32_t *channels, uint32_t *sampleRate, status_t *status)
159{
160    { // scope for the lock
161        Mutex::Autolock lock(mLock);
162
163        // only one output stream allowed
164        if (mOutput) {
165            if (status) {
166                *status = INVALID_OPERATION;
167            }
168            return 0;
169        }
170
171        // create new output stream
172        AudioStreamOutMSM72xx* out = new AudioStreamOutMSM72xx();
173        status_t lStatus = out->set(this, devices, format, channels, sampleRate);
174        if (status) {
175            *status = lStatus;
176        }
177        if (lStatus == NO_ERROR) {
178            mOutput = out;
179        } else {
180            delete out;
181        }
182    }
183    return mOutput;
184}
185
186void AudioHardware::closeOutputStream(AudioStreamOut* out) {
187    Mutex::Autolock lock(mLock);
188    if (mOutput == 0 || mOutput != out) {
189        LOGW("Attempt to close invalid output stream");
190    }
191    else {
192        delete mOutput;
193        mOutput = 0;
194    }
195}
196
197AudioStreamIn* AudioHardware::openInputStream(
198        uint32_t devices, int *format, uint32_t *channels, uint32_t *sampleRate, status_t *status,
199        AudioSystem::audio_in_acoustics acoustic_flags)
200{
201    // check for valid input source
202    if (!AudioSystem::isInputDevice((AudioSystem::audio_devices)devices)) {
203        return 0;
204    }
205
206    mLock.lock();
207
208    AudioStreamInMSM72xx* in = new AudioStreamInMSM72xx();
209    status_t lStatus = in->set(this, devices, format, channels, sampleRate, acoustic_flags);
210    if (status) {
211        *status = lStatus;
212    }
213    if (lStatus != NO_ERROR) {
214        mLock.unlock();
215        delete in;
216        return 0;
217    }
218
219    mInputs.add(in);
220    mLock.unlock();
221
222    return in;
223}
224
225void AudioHardware::closeInputStream(AudioStreamIn* in) {
226    Mutex::Autolock lock(mLock);
227
228    ssize_t index = mInputs.indexOf((AudioStreamInMSM72xx *)in);
229    if (index < 0) {
230        LOGW("Attempt to close invalid input stream");
231    } else {
232        mLock.unlock();
233        delete mInputs[index];
234        mLock.lock();
235        mInputs.removeAt(index);
236    }
237}
238
239bool AudioHardware::checkOutputStandby()
240{
241    if (mOutput)
242        if (!mOutput->checkStandby())
243            return false;
244
245    return true;
246}
247
248status_t AudioHardware::setMicMute(bool state)
249{
250    Mutex::Autolock lock(mLock);
251    return setMicMute_nosync(state);
252}
253
254// always call with mutex held
255status_t AudioHardware::setMicMute_nosync(bool state)
256{
257    if (mMicMute != state) {
258        mMicMute = state;
259        return doAudioRouteOrMute(SND_DEVICE_CURRENT);
260    }
261    return NO_ERROR;
262}
263
264status_t AudioHardware::getMicMute(bool* state)
265{
266    *state = mMicMute;
267    return NO_ERROR;
268}
269
270status_t AudioHardware::setParameters(const String8& keyValuePairs)
271{
272    AudioParameter param = AudioParameter(keyValuePairs);
273    String8 value;
274    String8 key;
275    const char BT_NREC_KEY[] = "bt_headset_nrec";
276    const char BT_NAME_KEY[] = "bt_headset_name";
277    const char BT_NREC_VALUE_ON[] = "on";
278
279
280    LOGV("setParameters() %s", keyValuePairs.string());
281
282    if (keyValuePairs.length() == 0) return BAD_VALUE;
283
284    key = String8(BT_NREC_KEY);
285    if (param.get(key, value) == NO_ERROR) {
286        if (value == BT_NREC_VALUE_ON) {
287            mBluetoothNrec = true;
288        } else {
289            mBluetoothNrec = false;
290            LOGI("Turning noise reduction and echo cancellation off for BT "
291                 "headset");
292        }
293    }
294    key = String8(BT_NAME_KEY);
295    if (param.get(key, value) == NO_ERROR) {
296        mBluetoothId = 0;
297        for (int i = 0; i < mNumSndEndpoints; i++) {
298            if (!strcasecmp(value.string(), mSndEndpoints[i].name)) {
299                mBluetoothId = mSndEndpoints[i].id;
300                LOGI("Using custom acoustic parameters for %s", value.string());
301                break;
302            }
303        }
304        if (mBluetoothId == 0) {
305            LOGI("Using default acoustic parameters "
306                 "(%s not in acoustic database)", value.string());
307            doRouting(NULL);
308        }
309    }
310    return NO_ERROR;
311}
312
313String8 AudioHardware::getParameters(const String8& keys)
314{
315    AudioParameter param = AudioParameter(keys);
316    return param.toString();
317}
318
319
320static unsigned calculate_audpre_table_index(unsigned index)
321{
322    switch (index) {
323        case 48000:    return SAMP_RATE_INDX_48000;
324        case 44100:    return SAMP_RATE_INDX_44100;
325        case 32000:    return SAMP_RATE_INDX_32000;
326        case 24000:    return SAMP_RATE_INDX_24000;
327        case 22050:    return SAMP_RATE_INDX_22050;
328        case 16000:    return SAMP_RATE_INDX_16000;
329        case 12000:    return SAMP_RATE_INDX_12000;
330        case 11025:    return SAMP_RATE_INDX_11025;
331        case 8000:    return SAMP_RATE_INDX_8000;
332        default:     return -1;
333    }
334}
335size_t AudioHardware::getInputBufferSize(uint32_t sampleRate, int format, int channelCount)
336{
337    if (format != AudioSystem::PCM_16_BIT) {
338        LOGW("getInputBufferSize bad format: %d", format);
339        return 0;
340    }
341    if (channelCount < 1 || channelCount > 2) {
342        LOGW("getInputBufferSize bad channel count: %d", channelCount);
343        return 0;
344    }
345
346    return 2048*channelCount;
347}
348
349static status_t set_volume_rpc(uint32_t device,
350                               uint32_t method,
351                               uint32_t volume)
352{
353    int fd;
354#if LOG_SND_RPC
355    LOGD("rpc_snd_set_volume(%d, %d, %d)\n", device, method, volume);
356#endif
357
358    if (device == -1UL) return NO_ERROR;
359
360    fd = open("/dev/msm_snd", O_RDWR);
361    if (fd < 0) {
362        LOGE("Can not open snd device");
363        return -EPERM;
364    }
365    /* rpc_snd_set_volume(
366     *     device,            # Any hardware device enum, including
367     *                        # SND_DEVICE_CURRENT
368     *     method,            # must be SND_METHOD_VOICE to do anything useful
369     *     volume,            # integer volume level, in range [0,5].
370     *                        # note that 0 is audible (not quite muted)
371     *  )
372     * rpc_snd_set_volume only works for in-call sound volume.
373     */
374     struct msm_snd_volume_config args;
375     args.device = device;
376     args.method = method;
377     args.volume = volume;
378
379     if (ioctl(fd, SND_SET_VOLUME, &args) < 0) {
380         LOGE("snd_set_volume error.");
381         close(fd);
382         return -EIO;
383     }
384     close(fd);
385     return NO_ERROR;
386}
387
388status_t AudioHardware::setVoiceVolume(float v)
389{
390    if (v < 0.0) {
391        LOGW("setVoiceVolume(%f) under 0.0, assuming 0.0\n", v);
392        v = 0.0;
393    } else if (v > 1.0) {
394        LOGW("setVoiceVolume(%f) over 1.0, assuming 1.0\n", v);
395        v = 1.0;
396    }
397
398    int vol = lrint(v * 5.0);
399    LOGD("setVoiceVolume(%f)\n", v);
400    LOGI("Setting in-call volume to %d (available range is 0 to 5)\n", vol);
401
402    Mutex::Autolock lock(mLock);
403    set_volume_rpc(SND_DEVICE_CURRENT, SND_METHOD_VOICE, vol);
404    return NO_ERROR;
405}
406
407status_t AudioHardware::setMasterVolume(float v)
408{
409    Mutex::Autolock lock(mLock);
410    int vol = ceil(v * 5.0);
411    LOGI("Set master volume to %d.\n", vol);
412    /*
413    set_volume_rpc(SND_DEVICE_HANDSET, SND_METHOD_VOICE, vol);
414    set_volume_rpc(SND_DEVICE_SPEAKER, SND_METHOD_VOICE, vol);
415    set_volume_rpc(SND_DEVICE_BT,      SND_METHOD_VOICE, vol);
416    set_volume_rpc(SND_DEVICE_HEADSET, SND_METHOD_VOICE, vol);
417    */
418    // We return an error code here to let the audioflinger do in-software
419    // volume on top of the maximum volume that we set through the SND API.
420    // return error - software mixer will handle it
421    return -1;
422}
423
424static status_t do_route_audio_rpc(uint32_t device,
425                                   bool ear_mute, bool mic_mute)
426{
427    if (device == -1UL)
428        return NO_ERROR;
429
430    int fd;
431#if LOG_SND_RPC
432    LOGD("rpc_snd_set_device(%d, %d, %d)\n", device, ear_mute, mic_mute);
433#endif
434
435    fd = open("/dev/msm_snd", O_RDWR);
436    if (fd < 0) {
437        LOGE("Can not open snd device");
438        return -EPERM;
439    }
440    // RPC call to switch audio path
441    /* rpc_snd_set_device(
442     *     device,            # Hardware device enum to use
443     *     ear_mute,          # Set mute for outgoing voice audio
444     *                        # this should only be unmuted when in-call
445     *     mic_mute,          # Set mute for incoming voice audio
446     *                        # this should only be unmuted when in-call or
447     *                        # recording.
448     *  )
449     */
450    struct msm_snd_device_config args;
451    args.device = device;
452    args.ear_mute = ear_mute ? SND_MUTE_MUTED : SND_MUTE_UNMUTED;
453    args.mic_mute = mic_mute ? SND_MUTE_MUTED : SND_MUTE_UNMUTED;
454
455    if (ioctl(fd, SND_SET_DEVICE, &args) < 0) {
456        LOGE("snd_set_device error.");
457        close(fd);
458        return -EIO;
459    }
460
461    close(fd);
462    return NO_ERROR;
463}
464
465// always call with mutex held
466status_t AudioHardware::doAudioRouteOrMute(uint32_t device)
467{
468    if (device == (uint32_t)SND_DEVICE_BT || device == (uint32_t)SND_DEVICE_CARKIT) {
469        if (mBluetoothId) {
470            device = mBluetoothId;
471        } else if (!mBluetoothNrec) {
472            device = SND_DEVICE_BT_EC_OFF;
473        }
474    }
475    LOGV("doAudioRouteOrMute() device %x, mMode %d, mMicMute %d", device, mMode, mMicMute);
476    return do_route_audio_rpc(device,
477                              mMode != AudioSystem::MODE_IN_CALL, mMicMute);
478}
479
480status_t AudioHardware::doRouting(AudioStreamInMSM72xx *input)
481{
482    /* currently this code doesn't work without the htc libacoustic */
483    if (!acoustic)
484        return 0;
485
486    Mutex::Autolock lock(mLock);
487    uint32_t outputDevices = mOutput->devices();
488    status_t ret = NO_ERROR;
489    int (*msm72xx_enable_audpp)(int);
490    msm72xx_enable_audpp = (int (*)(int))::dlsym(acoustic, "msm72xx_enable_audpp");
491    int audProcess = (ADRC_DISABLE | EQ_DISABLE | RX_IIR_DISABLE);
492    int sndDevice = -1;
493
494    if (input != NULL) {
495        uint32_t inputDevice = input->devices();
496        LOGI("do input routing device %x\n", inputDevice);
497        if (inputDevice != 0) {
498            if (inputDevice & AudioSystem::DEVICE_IN_BLUETOOTH_SCO_HEADSET) {
499                LOGI("Routing audio to Bluetooth PCM\n");
500                sndDevice = SND_DEVICE_BT;
501            } else if (inputDevice & AudioSystem::DEVICE_IN_WIRED_HEADSET) {
502                if ((outputDevices & AudioSystem::DEVICE_OUT_WIRED_HEADSET) &&
503                    (outputDevices & AudioSystem::DEVICE_OUT_SPEAKER)) {
504                    LOGI("Routing audio to Wired Headset and Speaker\n");
505                    sndDevice = SND_DEVICE_HEADSET_AND_SPEAKER;
506                    audProcess = (ADRC_ENABLE | EQ_ENABLE | RX_IIR_ENABLE);
507                } else {
508                    LOGI("Routing audio to Wired Headset\n");
509                    sndDevice = SND_DEVICE_HEADSET;
510                }
511            } else {
512                if (outputDevices & AudioSystem::DEVICE_OUT_SPEAKER) {
513                    LOGI("Routing audio to Speakerphone\n");
514                    sndDevice = SND_DEVICE_SPEAKER;
515                    audProcess = (ADRC_ENABLE | EQ_ENABLE | RX_IIR_ENABLE);
516                } else {
517                    LOGI("Routing audio to Handset\n");
518                    sndDevice = SND_DEVICE_HANDSET;
519                }
520            }
521        }
522        // if inputDevice == 0, restore output routing
523    }
524
525    if (sndDevice == -1) {
526        if (outputDevices & (outputDevices - 1)) {
527            if ((outputDevices & AudioSystem::DEVICE_OUT_SPEAKER) == 0) {
528                LOGW("Hardware does not support requested route combination (%#X),"
529                     " picking closest possible route...", outputDevices);
530            }
531        }
532
533        if (outputDevices & AudioSystem::DEVICE_OUT_TTY) {
534                LOGI("Routing audio to TTY\n");
535                sndDevice = SND_DEVICE_TTY_FULL;
536        } else if (outputDevices &
537                   (AudioSystem::DEVICE_OUT_BLUETOOTH_SCO | AudioSystem::DEVICE_OUT_BLUETOOTH_SCO_HEADSET)) {
538            LOGI("Routing audio to Bluetooth PCM\n");
539            sndDevice = SND_DEVICE_BT;
540        } else if (outputDevices & AudioSystem::DEVICE_OUT_BLUETOOTH_SCO_CARKIT) {
541            LOGI("Routing audio to Bluetooth PCM\n");
542            sndDevice = SND_DEVICE_CARKIT;
543        } else if ((outputDevices & AudioSystem::DEVICE_OUT_WIRED_HEADSET) &&
544                   (outputDevices & AudioSystem::DEVICE_OUT_SPEAKER)) {
545            LOGI("Routing audio to Wired Headset and Speaker\n");
546            sndDevice = SND_DEVICE_HEADSET_AND_SPEAKER;
547            audProcess = (ADRC_ENABLE | EQ_ENABLE | RX_IIR_ENABLE);
548        } else if (outputDevices & AudioSystem::DEVICE_OUT_FM_SPEAKER) {
549            LOGI("Routing audio to FM Speakerphone (%d,%x)\n", mMode, outputDevices);
550            sndDevice = SND_DEVICE_FM_SPEAKER;
551            audProcess = (ADRC_ENABLE | EQ_ENABLE | RX_IIR_DISABLE);
552        } else if (outputDevices & AudioSystem::DEVICE_OUT_FM_HEADPHONE) {
553            if (outputDevices & AudioSystem::DEVICE_OUT_SPEAKER) {
554                LOGI("Routing audio to FM Headset and Speaker (%d,%x)\n", mMode, outputDevices);
555                sndDevice = SND_DEVICE_HEADSET_AND_SPEAKER;
556                audProcess = (ADRC_ENABLE | EQ_ENABLE | RX_IIR_ENABLE);
557            } else {
558                LOGI("Routing audio to FM Headset (%d,%x)\n", mMode, outputDevices);
559                sndDevice = SND_DEVICE_FM_HEADSET;
560            }
561        } else if (outputDevices & AudioSystem::DEVICE_OUT_WIRED_HEADPHONE) {
562            if (outputDevices & AudioSystem::DEVICE_OUT_SPEAKER) {
563                LOGI("Routing audio to No microphone Wired Headset and Speaker (%d,%x)\n", mMode, outputDevices);
564                sndDevice = SND_DEVICE_HEADSET_AND_SPEAKER;
565                audProcess = (ADRC_ENABLE | EQ_ENABLE | RX_IIR_ENABLE);
566            } else {
567                LOGI("Routing audio to No microphone Wired Headset (%d,%x)\n", mMode, outputDevices);
568                sndDevice = SND_DEVICE_NO_MIC_HEADSET;
569            }
570        } else if (outputDevices & AudioSystem::DEVICE_OUT_WIRED_HEADSET) {
571            LOGI("Routing audio to Wired Headset\n");
572            sndDevice = SND_DEVICE_HEADSET;
573        } else if (outputDevices & AudioSystem::DEVICE_OUT_SPEAKER) {
574            LOGI("Routing audio to Speakerphone\n");
575            sndDevice = SND_DEVICE_SPEAKER;
576            audProcess = (ADRC_ENABLE | EQ_ENABLE | RX_IIR_ENABLE);
577        } else {
578            LOGI("Routing audio to Handset\n");
579            sndDevice = SND_DEVICE_HANDSET;
580        }
581    }
582
583    if (sndDevice != -1 && sndDevice != mCurSndDevice) {
584        ret = doAudioRouteOrMute(sndDevice);
585        if ((*msm72xx_enable_audpp) == 0 ) {
586            LOGE("Could not open msm72xx_enable_audpp()");
587        } else {
588            msm72xx_enable_audpp(audProcess);
589        }
590        mCurSndDevice = sndDevice;
591    }
592
593    return ret;
594}
595
596status_t AudioHardware::checkMicMute()
597{
598    Mutex::Autolock lock(mLock);
599    if (mMode != AudioSystem::MODE_IN_CALL) {
600        setMicMute_nosync(true);
601    }
602
603    return NO_ERROR;
604}
605
606status_t AudioHardware::dumpInternals(int fd, const Vector<String16>& args)
607{
608    const size_t SIZE = 256;
609    char buffer[SIZE];
610    String8 result;
611    result.append("AudioHardware::dumpInternals\n");
612    snprintf(buffer, SIZE, "\tmInit: %s\n", mInit? "true": "false");
613    result.append(buffer);
614    snprintf(buffer, SIZE, "\tmMicMute: %s\n", mMicMute? "true": "false");
615    result.append(buffer);
616    snprintf(buffer, SIZE, "\tmBluetoothNrec: %s\n", mBluetoothNrec? "true": "false");
617    result.append(buffer);
618    snprintf(buffer, SIZE, "\tmBluetoothId: %d\n", mBluetoothId);
619    result.append(buffer);
620    ::write(fd, result.string(), result.size());
621    return NO_ERROR;
622}
623
624status_t AudioHardware::dump(int fd, const Vector<String16>& args)
625{
626    dumpInternals(fd, args);
627    for (size_t index = 0; index < mInputs.size(); index++) {
628        mInputs[index]->dump(fd, args);
629    }
630
631    if (mOutput) {
632        mOutput->dump(fd, args);
633    }
634    return NO_ERROR;
635}
636
637uint32_t AudioHardware::getInputSampleRate(uint32_t sampleRate)
638{
639    uint32_t i;
640    uint32_t prevDelta;
641    uint32_t delta;
642
643    for (i = 0, prevDelta = 0xFFFFFFFF; i < sizeof(inputSamplingRates)/sizeof(uint32_t); i++, prevDelta = delta) {
644        delta = abs(sampleRate - inputSamplingRates[i]);
645        if (delta > prevDelta) break;
646    }
647    // i is always > 0 here
648    return inputSamplingRates[i-1];
649}
650
651// ----------------------------------------------------------------------------
652
653AudioHardware::AudioStreamOutMSM72xx::AudioStreamOutMSM72xx() :
654    mHardware(0), mFd(-1), mStartCount(0), mRetryCount(0), mStandby(true), mDevices(0)
655{
656}
657
658status_t AudioHardware::AudioStreamOutMSM72xx::set(
659        AudioHardware* hw, uint32_t devices, int *pFormat, uint32_t *pChannels, uint32_t *pRate)
660{
661    int lFormat = pFormat ? *pFormat : 0;
662    uint32_t lChannels = pChannels ? *pChannels : 0;
663    uint32_t lRate = pRate ? *pRate : 0;
664
665    mHardware = hw;
666
667    // fix up defaults
668    if (lFormat == 0) lFormat = format();
669    if (lChannels == 0) lChannels = channels();
670    if (lRate == 0) lRate = sampleRate();
671
672    // check values
673    if ((lFormat != format()) ||
674        (lChannels != channels()) ||
675        (lRate != sampleRate())) {
676        if (pFormat) *pFormat = format();
677        if (pChannels) *pChannels = channels();
678        if (pRate) *pRate = sampleRate();
679        return BAD_VALUE;
680    }
681
682    if (pFormat) *pFormat = lFormat;
683    if (pChannels) *pChannels = lChannels;
684    if (pRate) *pRate = lRate;
685
686    mDevices = devices;
687
688    return NO_ERROR;
689}
690
691AudioHardware::AudioStreamOutMSM72xx::~AudioStreamOutMSM72xx()
692{
693    if (mFd > 0) close(mFd);
694}
695
696ssize_t AudioHardware::AudioStreamOutMSM72xx::write(const void* buffer, size_t bytes)
697{
698    // LOGD("AudioStreamOutMSM72xx::write(%p, %u)", buffer, bytes);
699    status_t status = NO_INIT;
700    size_t count = bytes;
701    const uint8_t* p = static_cast<const uint8_t*>(buffer);
702
703    if (mStandby) {
704
705        // open driver
706        LOGV("open driver");
707        status = ::open("/dev/msm_pcm_out", O_RDWR);
708        if (status < 0) {
709            LOGE("Cannot open /dev/msm_pcm_out errno: %d", errno);
710            goto Error;
711        }
712        mFd = status;
713
714        // configuration
715        LOGV("get config");
716        struct msm_audio_config config;
717        status = ioctl(mFd, AUDIO_GET_CONFIG, &config);
718        if (status < 0) {
719            LOGE("Cannot read config");
720            goto Error;
721        }
722
723        LOGV("set config");
724        config.channel_count = AudioSystem::popCount(channels());
725        config.sample_rate = sampleRate();
726        config.buffer_size = bufferSize();
727        config.buffer_count = AUDIO_HW_NUM_OUT_BUF;
728        config.codec_type = CODEC_TYPE_PCM;
729        status = ioctl(mFd, AUDIO_SET_CONFIG, &config);
730        if (status < 0) {
731            LOGE("Cannot set config");
732            goto Error;
733        }
734
735        LOGV("buffer_size: %u", config.buffer_size);
736        LOGV("buffer_count: %u", config.buffer_count);
737        LOGV("channel_count: %u", config.channel_count);
738        LOGV("sample_rate: %u", config.sample_rate);
739
740        // fill 2 buffers before AUDIO_START
741        mStartCount = AUDIO_HW_NUM_OUT_BUF;
742        mStandby = false;
743    }
744
745    while (count) {
746        ssize_t written = ::write(mFd, p, count);
747        if (written >= 0) {
748            count -= written;
749            p += written;
750        } else {
751            if (errno != EAGAIN) return written;
752            mRetryCount++;
753            LOGW("EAGAIN - retry");
754        }
755    }
756
757    // start audio after we fill 2 buffers
758    if (mStartCount) {
759        if (--mStartCount == 0) {
760            ioctl(mFd, AUDIO_START, 0);
761        }
762    }
763    return bytes;
764
765Error:
766    if (mFd > 0) {
767        ::close(mFd);
768        mFd = -1;
769    }
770    // Simulate audio output timing in case of error
771    usleep(bytes * 1000000 / frameSize() / sampleRate());
772
773    return status;
774}
775
776status_t AudioHardware::AudioStreamOutMSM72xx::standby()
777{
778    status_t status = NO_ERROR;
779    if (!mStandby && mFd > 0) {
780        ::close(mFd);
781        mFd = -1;
782    }
783    mStandby = true;
784    return status;
785}
786
787status_t AudioHardware::AudioStreamOutMSM72xx::dump(int fd, const Vector<String16>& args)
788{
789    const size_t SIZE = 256;
790    char buffer[SIZE];
791    String8 result;
792    result.append("AudioStreamOutMSM72xx::dump\n");
793    snprintf(buffer, SIZE, "\tsample rate: %d\n", sampleRate());
794    result.append(buffer);
795    snprintf(buffer, SIZE, "\tbuffer size: %d\n", bufferSize());
796    result.append(buffer);
797    snprintf(buffer, SIZE, "\tchannels: %d\n", channels());
798    result.append(buffer);
799    snprintf(buffer, SIZE, "\tformat: %d\n", format());
800    result.append(buffer);
801    snprintf(buffer, SIZE, "\tmHardware: %p\n", mHardware);
802    result.append(buffer);
803    snprintf(buffer, SIZE, "\tmFd: %d\n", mFd);
804    result.append(buffer);
805    snprintf(buffer, SIZE, "\tmStartCount: %d\n", mStartCount);
806    result.append(buffer);
807    snprintf(buffer, SIZE, "\tmRetryCount: %d\n", mRetryCount);
808    result.append(buffer);
809    snprintf(buffer, SIZE, "\tmStandby: %s\n", mStandby? "true": "false");
810    result.append(buffer);
811    ::write(fd, result.string(), result.size());
812    return NO_ERROR;
813}
814
815bool AudioHardware::AudioStreamOutMSM72xx::checkStandby()
816{
817    return mStandby;
818}
819
820
821status_t AudioHardware::AudioStreamOutMSM72xx::setParameters(const String8& keyValuePairs)
822{
823    AudioParameter param = AudioParameter(keyValuePairs);
824    String8 key = String8(AudioParameter::keyRouting);
825    status_t status = NO_ERROR;
826    int device;
827    LOGV("AudioStreamOutMSM72xx::setParameters() %s", keyValuePairs.string());
828
829    if (param.getInt(key, device) == NO_ERROR) {
830        mDevices = device;
831        LOGV("set output routing %x", mDevices);
832        status = mHardware->doRouting(NULL);
833        param.remove(key);
834    }
835
836    if (param.size()) {
837        status = BAD_VALUE;
838    }
839    return status;
840}
841
842String8 AudioHardware::AudioStreamOutMSM72xx::getParameters(const String8& keys)
843{
844    AudioParameter param = AudioParameter(keys);
845    String8 value;
846    String8 key = String8(AudioParameter::keyRouting);
847
848    if (param.get(key, value) == NO_ERROR) {
849        LOGV("get routing %x", mDevices);
850        param.addInt(key, (int)mDevices);
851    }
852
853    LOGV("AudioStreamOutMSM72xx::getParameters() %s", param.toString().string());
854    return param.toString();
855}
856
857
858// ----------------------------------------------------------------------------
859
860AudioHardware::AudioStreamInMSM72xx::AudioStreamInMSM72xx() :
861    mHardware(0), mFd(-1), mState(AUDIO_INPUT_CLOSED), mRetryCount(0),
862    mFormat(AUDIO_HW_IN_FORMAT), mChannels(AUDIO_HW_IN_CHANNELS),
863    mSampleRate(AUDIO_HW_IN_SAMPLERATE), mBufferSize(AUDIO_HW_IN_BUFFERSIZE),
864    mAcoustics((AudioSystem::audio_in_acoustics)0), mDevices(0)
865{
866}
867
868status_t AudioHardware::AudioStreamInMSM72xx::set(
869        AudioHardware* hw, uint32_t devices, int *pFormat, uint32_t *pChannels, uint32_t *pRate,
870        AudioSystem::audio_in_acoustics acoustic_flags)
871{
872    if (pFormat == 0 || *pFormat != AUDIO_HW_IN_FORMAT) {
873        *pFormat = AUDIO_HW_IN_FORMAT;
874        return BAD_VALUE;
875    }
876    if (pRate == 0) {
877        return BAD_VALUE;
878    }
879    uint32_t rate = hw->getInputSampleRate(*pRate);
880    if (rate != *pRate) {
881        *pRate = rate;
882        return BAD_VALUE;
883    }
884
885    if (pChannels == 0 || (*pChannels != AudioSystem::CHANNEL_IN_MONO &&
886        *pChannels != AudioSystem::CHANNEL_IN_STEREO)) {
887        *pChannels = AUDIO_HW_IN_CHANNELS;
888        return BAD_VALUE;
889    }
890
891    mHardware = hw;
892
893    LOGV("AudioStreamInMSM72xx::set(%d, %d, %u)", *pFormat, *pChannels, *pRate);
894    if (mFd >= 0) {
895        LOGE("Audio record already open");
896        return -EPERM;
897    }
898
899    // open audio input device
900    status_t status = ::open("/dev/msm_pcm_in", O_RDWR);
901    if (status < 0) {
902        LOGE("Cannot open /dev/msm_pcm_in errno: %d", errno);
903        goto Error;
904    }
905    mFd = status;
906
907    // configuration
908    LOGV("get config");
909    struct msm_audio_config config;
910    status = ioctl(mFd, AUDIO_GET_CONFIG, &config);
911    if (status < 0) {
912        LOGE("Cannot read config");
913        goto Error;
914    }
915
916    LOGV("set config");
917    config.channel_count = AudioSystem::popCount(*pChannels);
918    config.sample_rate = *pRate;
919    config.buffer_size = bufferSize();
920    config.buffer_count = 2;
921    config.codec_type = CODEC_TYPE_PCM;
922    status = ioctl(mFd, AUDIO_SET_CONFIG, &config);
923    if (status < 0) {
924        LOGE("Cannot set config");
925        if (ioctl(mFd, AUDIO_GET_CONFIG, &config) == 0) {
926            if (config.channel_count == 1) {
927                *pChannels = AudioSystem::CHANNEL_IN_MONO;
928            } else {
929                *pChannels = AudioSystem::CHANNEL_IN_STEREO;
930            }
931            *pRate = config.sample_rate;
932        }
933        goto Error;
934    }
935
936    LOGV("confirm config");
937    status = ioctl(mFd, AUDIO_GET_CONFIG, &config);
938    if (status < 0) {
939        LOGE("Cannot read config");
940        goto Error;
941    }
942    LOGV("buffer_size: %u", config.buffer_size);
943    LOGV("buffer_count: %u", config.buffer_count);
944    LOGV("channel_count: %u", config.channel_count);
945    LOGV("sample_rate: %u", config.sample_rate);
946
947    mDevices = devices;
948    mFormat = AUDIO_HW_IN_FORMAT;
949    mChannels = *pChannels;
950    mSampleRate = config.sample_rate;
951    mBufferSize = config.buffer_size;
952
953    //mHardware->setMicMute_nosync(false);
954    mState = AUDIO_INPUT_OPENED;
955
956    if (!acoustic)
957        return NO_ERROR;
958
959    audpre_index = calculate_audpre_table_index(mSampleRate);
960    tx_iir_index = (audpre_index * 2) + (hw->checkOutputStandby() ? 0 : 1);
961    LOGD("audpre_index = %d, tx_iir_index = %d\n", audpre_index, tx_iir_index);
962
963    /**
964     * If audio-preprocessing failed, we should not block record.
965     */
966    int (*msm72xx_set_audpre_params)(int, int);
967    msm72xx_set_audpre_params = (int (*)(int, int))::dlsym(acoustic, "msm72xx_set_audpre_params");
968    status = msm72xx_set_audpre_params(audpre_index, tx_iir_index);
969    if (status < 0)
970        LOGE("Cannot set audpre parameters");
971
972    int (*msm72xx_enable_audpre)(int, int, int);
973    msm72xx_enable_audpre = (int (*)(int, int, int))::dlsym(acoustic, "msm72xx_enable_audpre");
974    mAcoustics = acoustic_flags;
975    status = msm72xx_enable_audpre((int)acoustic_flags, audpre_index, tx_iir_index);
976    if (status < 0)
977        LOGE("Cannot enable audpre");
978
979    return NO_ERROR;
980
981Error:
982    if (mFd > 0) {
983        ::close(mFd);
984        mFd = -1;
985    }
986    return status;
987}
988
989AudioHardware::AudioStreamInMSM72xx::~AudioStreamInMSM72xx()
990{
991    LOGV("AudioStreamInMSM72xx destructor");
992    standby();
993}
994
995ssize_t AudioHardware::AudioStreamInMSM72xx::read( void* buffer, ssize_t bytes)
996{
997    LOGV("AudioStreamInMSM72xx::read(%p, %ld)", buffer, bytes);
998    if (!mHardware) return -1;
999
1000    size_t count = bytes;
1001    uint8_t* p = static_cast<uint8_t*>(buffer);
1002
1003    if (mState < AUDIO_INPUT_OPENED) {
1004        Mutex::Autolock lock(mHardware->mLock);
1005        if (set(mHardware, mDevices, &mFormat, &mChannels, &mSampleRate, mAcoustics) != NO_ERROR) {
1006            return -1;
1007        }
1008    }
1009
1010    if (mState < AUDIO_INPUT_STARTED) {
1011        if (ioctl(mFd, AUDIO_START, 0)) {
1012            LOGE("Error starting record");
1013            return -1;
1014        }
1015        mState = AUDIO_INPUT_STARTED;
1016    }
1017
1018    while (count) {
1019        ssize_t bytesRead = ::read(mFd, buffer, count);
1020        if (bytesRead >= 0) {
1021            count -= bytesRead;
1022            p += bytesRead;
1023        } else {
1024            if (errno != EAGAIN) return bytesRead;
1025            mRetryCount++;
1026            LOGW("EAGAIN - retrying");
1027        }
1028    }
1029    return bytes;
1030}
1031
1032status_t AudioHardware::AudioStreamInMSM72xx::standby()
1033{
1034    if (!mHardware) return -1;
1035    if (mState > AUDIO_INPUT_CLOSED) {
1036        if (mFd > 0) {
1037            ::close(mFd);
1038            mFd = -1;
1039        }
1040        //mHardware->checkMicMute();
1041        mState = AUDIO_INPUT_CLOSED;
1042    }
1043    return NO_ERROR;
1044}
1045
1046status_t AudioHardware::AudioStreamInMSM72xx::dump(int fd, const Vector<String16>& args)
1047{
1048    const size_t SIZE = 256;
1049    char buffer[SIZE];
1050    String8 result;
1051    result.append("AudioStreamInMSM72xx::dump\n");
1052    snprintf(buffer, SIZE, "\tsample rate: %d\n", sampleRate());
1053    result.append(buffer);
1054    snprintf(buffer, SIZE, "\tbuffer size: %d\n", bufferSize());
1055    result.append(buffer);
1056    snprintf(buffer, SIZE, "\tchannels: %d\n", channels());
1057    result.append(buffer);
1058    snprintf(buffer, SIZE, "\tformat: %d\n", format());
1059    result.append(buffer);
1060    snprintf(buffer, SIZE, "\tmHardware: %p\n", mHardware);
1061    result.append(buffer);
1062    snprintf(buffer, SIZE, "\tmFd count: %d\n", mFd);
1063    result.append(buffer);
1064    snprintf(buffer, SIZE, "\tmState: %d\n", mState);
1065    result.append(buffer);
1066    snprintf(buffer, SIZE, "\tmRetryCount: %d\n", mRetryCount);
1067    result.append(buffer);
1068    ::write(fd, result.string(), result.size());
1069    return NO_ERROR;
1070}
1071
1072status_t AudioHardware::AudioStreamInMSM72xx::setParameters(const String8& keyValuePairs)
1073{
1074    AudioParameter param = AudioParameter(keyValuePairs);
1075    String8 key = String8(AudioParameter::keyRouting);
1076    status_t status = NO_ERROR;
1077    int device;
1078    LOGV("AudioStreamInMSM72xx::setParameters() %s", keyValuePairs.string());
1079
1080    if (param.getInt(key, device) == NO_ERROR) {
1081        LOGV("set input routing %x", device);
1082        if (device & (device - 1)) {
1083            status = BAD_VALUE;
1084        } else {
1085            mDevices = device;
1086            status = mHardware->doRouting(this);
1087        }
1088        param.remove(key);
1089    }
1090
1091    if (param.size()) {
1092        status = BAD_VALUE;
1093    }
1094    return status;
1095}
1096
1097String8 AudioHardware::AudioStreamInMSM72xx::getParameters(const String8& keys)
1098{
1099    AudioParameter param = AudioParameter(keys);
1100    String8 value;
1101    String8 key = String8(AudioParameter::keyRouting);
1102
1103    if (param.get(key, value) == NO_ERROR) {
1104        LOGV("get routing %x", mDevices);
1105        param.addInt(key, (int)mDevices);
1106    }
1107
1108    LOGV("AudioStreamInMSM72xx::getParameters() %s", param.toString().string());
1109    return param.toString();
1110}
1111
1112// ----------------------------------------------------------------------------
1113
1114extern "C" AudioHardwareInterface* createAudioHardware(void) {
1115    return new AudioHardware();
1116}
1117
1118}; // namespace android
1119