156ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi/*
256ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi * Copyright (C) 2015 The Android Open Source Project
356ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi *
456ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi * Licensed under the Apache License, Version 2.0 (the "License");
556ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi * you may not use this file except in compliance with the License.
656ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi * You may obtain a copy of the License at
756ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi *
856ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi *      http://www.apache.org/licenses/LICENSE-2.0
956ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi *
1056ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi * Unless required by applicable law or agreed to in writing, software
1156ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi * distributed under the License is distributed on an "AS IS" BASIS,
1256ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1356ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi * See the License for the specific language governing permissions and
1456ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi * limitations under the License.
1556ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi */
1656ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi
17ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie#pragma once
18ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie
1998cc191247388132b6fd8a4ecd07abd6e4c5a0edFrançois Gaffie#include "AudioPort.h"
20599c758b258cc5da0dba9b530425381facc37d77Eric Laurent#include "AudioSession.h"
218c7cf3b7d0d7bccb9affbc34ae2ab2d6b332f972Jean-Michel Trivi#include "AudioSessionInfoProvider.h"
22ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie#include <utils/Errors.h>
23ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie#include <system/audio.h>
24ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie#include <utils/SortedVector.h>
2553615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie#include <utils/KeyedVector.h>
26ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie
2756ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivinamespace android {
2856ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi
29ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffieclass IOProfile;
30ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffieclass AudioMix;
31ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie
3256ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi// descriptor for audio inputs. Used to maintain current configuration of each opened audio input
3356ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi// and keep track of the usage of this input.
348c7cf3b7d0d7bccb9affbc34ae2ab2d6b332f972Jean-Michel Triviclass AudioInputDescriptor: public AudioPortConfig, public AudioSessionInfoProvider
3556ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi{
3656ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivipublic:
37e964d4e421e2d1ca937227a580c0c837091a11e3Chih-Hung Hsieh    explicit AudioInputDescriptor(const sp<IOProfile>& profile);
3898cc191247388132b6fd8a4ecd07abd6e4c5a0edFrançois Gaffie    void setIoHandle(audio_io_handle_t ioHandle);
39322b4d25387a04c9afebe998326d005bbdf17edeEric Laurent    audio_port_handle_t getId() const;
4053615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie    audio_module_handle_t getModuleHandle() const;
4165bfe916ca972b95f41d7f6cc2566c2e12a3eadaJean-Michel Trivi    uint32_t getOpenRefCount() const;
4253615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie
4356ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi    status_t    dump(int fd);
4456ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi
4556ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi    audio_io_handle_t             mIoHandle;       // input handle
4656ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi    audio_devices_t               mDevice;         // current device this input is routed to
4756ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi    AudioMix                      *mPolicyMix;     // non NULL when used by a dynamic policy
4856ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi    const sp<IOProfile>           mProfile;        // I/O profile this output derives from
4956ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi
5056ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi    virtual void toAudioPortConfig(struct audio_port_config *dstConfig,
5156ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi            const struct audio_port_config *srcConfig = NULL) const;
5256ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi    virtual sp<AudioPort> getAudioPort() const { return mProfile; }
5356ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi    void toAudioPort(struct audio_port *port) const;
5464265b2fb8f5be63b6c2ad4fcbec9acf74705bc4Eric Laurent    void setPreemptedSessions(const SortedVector<audio_session_t>& sessions);
5564265b2fb8f5be63b6c2ad4fcbec9acf74705bc4Eric Laurent    SortedVector<audio_session_t> getPreemptedSessions() const;
5664265b2fb8f5be63b6c2ad4fcbec9acf74705bc4Eric Laurent    bool hasPreemptedSession(audio_session_t session) const;
5764265b2fb8f5be63b6c2ad4fcbec9acf74705bc4Eric Laurent    void clearPreemptedSessions();
58599c758b258cc5da0dba9b530425381facc37d77Eric Laurent    bool isActive() const;
59599c758b258cc5da0dba9b530425381facc37d77Eric Laurent    bool isSourceActive(audio_source_t source) const;
60bb9480975322b0d1a09f76ef14f3285fc8af4e5fEric Laurent    audio_source_t inputSource(bool activeOnly = false) const;
61599c758b258cc5da0dba9b530425381facc37d77Eric Laurent    bool isSoundTrigger() const;
62599c758b258cc5da0dba9b530425381facc37d77Eric Laurent    status_t addAudioSession(audio_session_t session,
63599c758b258cc5da0dba9b530425381facc37d77Eric Laurent                             const sp<AudioSession>& audioSession);
64599c758b258cc5da0dba9b530425381facc37d77Eric Laurent    status_t removeAudioSession(audio_session_t session);
65599c758b258cc5da0dba9b530425381facc37d77Eric Laurent    sp<AudioSession> getAudioSession(audio_session_t session) const;
66fb66dd9f95a1168698f072c4e5c2a2cf8c49a80fEric Laurent    AudioSessionCollection getAudioSessions(bool activeOnly) const;
6756afc7a5cc0f0bfc8021f6413b2e2267050bdc8aJean-Michel Trivi    size_t getAudioSessionCount(bool activeOnly) const;
68fb66dd9f95a1168698f072c4e5c2a2cf8c49a80fEric Laurent    audio_source_t getHighestPrioritySource(bool activeOnly) const;
69322b4d25387a04c9afebe998326d005bbdf17edeEric Laurent
708c7cf3b7d0d7bccb9affbc34ae2ab2d6b332f972Jean-Michel Trivi    // implementation of AudioSessionInfoProvider
718c7cf3b7d0d7bccb9affbc34ae2ab2d6b332f972Jean-Michel Trivi    virtual audio_config_base_t getConfig() const;
728c7cf3b7d0d7bccb9affbc34ae2ab2d6b332f972Jean-Michel Trivi    virtual audio_patch_handle_t getPatchHandle() const;
738c7cf3b7d0d7bccb9affbc34ae2ab2d6b332f972Jean-Michel Trivi
748c7cf3b7d0d7bccb9affbc34ae2ab2d6b332f972Jean-Michel Trivi    void setPatchHandle(audio_patch_handle_t handle);
758c7cf3b7d0d7bccb9affbc34ae2ab2d6b332f972Jean-Michel Trivi
76322b4d25387a04c9afebe998326d005bbdf17edeEric Laurentprivate:
778c7cf3b7d0d7bccb9affbc34ae2ab2d6b332f972Jean-Michel Trivi    audio_patch_handle_t          mPatchHandle;
78322b4d25387a04c9afebe998326d005bbdf17edeEric Laurent    audio_port_handle_t           mId;
79599c758b258cc5da0dba9b530425381facc37d77Eric Laurent    // audio sessions attached to this input
80599c758b258cc5da0dba9b530425381facc37d77Eric Laurent    AudioSessionCollection        mSessions;
812f4fe9f7df8f22c6bc8745407d19df73128810ecJean-Michel Trivi    // Because a preemptible capture session can preempt another one, we end up in an endless loop
8264265b2fb8f5be63b6c2ad4fcbec9acf74705bc4Eric Laurent    // situation were each session is allowed to restart after being preempted,
8364265b2fb8f5be63b6c2ad4fcbec9acf74705bc4Eric Laurent    // thus preempting the other one which restarts and so on.
8464265b2fb8f5be63b6c2ad4fcbec9acf74705bc4Eric Laurent    // To avoid this situation, we store which audio session was preempted when
8564265b2fb8f5be63b6c2ad4fcbec9acf74705bc4Eric Laurent    // a particular input started and prevent preemption of this active input by this session.
8664265b2fb8f5be63b6c2ad4fcbec9acf74705bc4Eric Laurent    // We also inherit sessions from the preempted input to avoid a 3 way preemption loop etc...
8764265b2fb8f5be63b6c2ad4fcbec9acf74705bc4Eric Laurent    SortedVector<audio_session_t> mPreemptedSessions;
8856ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi};
8956ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi
9053615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffieclass AudioInputCollection :
9153615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie        public DefaultKeyedVector< audio_io_handle_t, sp<AudioInputDescriptor> >
9253615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie{
9353615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffiepublic:
9453615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie    bool isSourceActive(audio_source_t source) const;
9553615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie
9653615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie    sp<AudioInputDescriptor> getInputFromId(audio_port_handle_t id) const;
9753615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie
98271a93e924f46ccaf3f76a8fc38685afea40d3eeEric Laurent    // count active capture sessions using one of the specified devices.
99271a93e924f46ccaf3f76a8fc38685afea40d3eeEric Laurent    // ignore devices if AUDIO_DEVICE_IN_DEFAULT is passed
100271a93e924f46ccaf3f76a8fc38685afea40d3eeEric Laurent    uint32_t activeInputsCountOnDevices(audio_devices_t devices = AUDIO_DEVICE_IN_DEFAULT) const;
10153615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie
10253615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie    /**
10353615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie     * return io handle of active input or 0 if no input is active
10453615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie     * Only considers inputs from physical devices (e.g. main mic, headset mic) when
10553615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie     * ignoreVirtualInputs is true.
10653615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie     */
107fb66dd9f95a1168698f072c4e5c2a2cf8c49a80fEric Laurent    Vector<sp <AudioInputDescriptor> > getActiveInputs(bool ignoreVirtualInputs = true);
10853615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie
10953615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie    audio_devices_t getSupportedDevices(audio_io_handle_t handle) const;
11053615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie
11153615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie    status_t dump(int fd) const;
11253615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie};
11353615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie
11453615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie
11556ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi}; // namespace android
116