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 19cbb3044d6bfa9ab30c83b67874f40344e29805e1François Gaffie#include "AudioCollections.h" 20112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie#include "AudioProfile.h" 21ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie#include <utils/String8.h> 22ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie#include <utils/Vector.h> 23ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie#include <utils/RefBase.h> 24ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie#include <utils/Errors.h> 25ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie#include <system/audio.h> 26ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie#include <cutils/config_utils.h> 27ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie 2856ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivinamespace android { 2956ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 3056ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Triviclass HwModule; 31ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffieclass AudioGain; 32cbb3044d6bfa9ab30c83b67874f40344e29805e1François Gaffieclass AudioRoute; 33a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffietypedef Vector<sp<AudioGain> > AudioGainCollection; 3456ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 3553615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffieclass AudioPort : public virtual RefBase 3656ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi{ 3756ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivipublic: 38a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie AudioPort(const String8& name, audio_port_type_t type, audio_port_role_t role) : 39a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie mName(name), mType(type), mRole(role), mFlags(AUDIO_OUTPUT_FLAG_NONE) {} 40a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie 4156ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi virtual ~AudioPort() {} 4256ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 431d4481fb9cb1ea149f79f2a5d22110af84fbc90bFrançois Gaffie void setName(const String8 &name) { mName = name; } 44a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie const String8 &getName() const { return mName; } 45a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie 46a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie audio_port_type_t getType() const { return mType; } 47a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie audio_port_role_t getRole() const { return mRole; } 48a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie 49cbb3044d6bfa9ab30c83b67874f40344e29805e1François Gaffie virtual const String8 getTagName() const = 0; 50cbb3044d6bfa9ab30c83b67874f40344e29805e1François Gaffie 51a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie void setGains(const AudioGainCollection &gains) { mGains = gains; } 52a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie const AudioGainCollection &getGains() const { return mGains; } 53a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie 54f4ad6e5637b6deccdac4b60615383f290b3806cfFrançois Gaffie void setFlags(uint32_t flags) 55f4ad6e5637b6deccdac4b60615383f290b3806cfFrançois Gaffie { 56f4ad6e5637b6deccdac4b60615383f290b3806cfFrançois Gaffie //force direct flag if offload flag is set: offloading implies a direct output stream 57f4ad6e5637b6deccdac4b60615383f290b3806cfFrançois Gaffie // and all common behaviors are driven by checking only the direct flag 58f4ad6e5637b6deccdac4b60615383f290b3806cfFrançois Gaffie // this should normally be set appropriately in the policy configuration file 59f4ad6e5637b6deccdac4b60615383f290b3806cfFrançois Gaffie if (mRole == AUDIO_PORT_ROLE_SOURCE && (flags & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) != 0) { 60f4ad6e5637b6deccdac4b60615383f290b3806cfFrançois Gaffie flags |= AUDIO_OUTPUT_FLAG_DIRECT; 61f4ad6e5637b6deccdac4b60615383f290b3806cfFrançois Gaffie } 62f4ad6e5637b6deccdac4b60615383f290b3806cfFrançois Gaffie mFlags = flags; 63f4ad6e5637b6deccdac4b60615383f290b3806cfFrançois Gaffie } 64a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie uint32_t getFlags() const { return mFlags; } 65a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie 66322b4d25387a04c9afebe998326d005bbdf17edeEric Laurent virtual void attach(const sp<HwModule>& module); 67322b4d25387a04c9afebe998326d005bbdf17edeEric Laurent bool isAttached() { return mModule != 0; } 6856ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 69f0c6d7d940314dbec47c9b53cb99da79eb022787Glenn Kasten // Audio port IDs are in a different namespace than AudioFlinger unique IDs 7098cc191247388132b6fd8a4ecd07abd6e4c5a0edFrançois Gaffie static audio_port_handle_t getNextUniqueId(); 7198cc191247388132b6fd8a4ecd07abd6e4c5a0edFrançois Gaffie 7256ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi virtual void toAudioPort(struct audio_port *port) const; 7356ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 74e964d4e421e2d1ca937227a580c0c837091a11e3Chih-Hung Hsieh virtual void importAudioPort(const sp<AudioPort>& port); 7556ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 76112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie void addAudioProfile(const sp<AudioProfile> &profile) { mProfiles.add(profile); } 77112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie 78112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie void setAudioProfiles(const AudioProfileVector &profiles) { mProfiles = profiles; } 79112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie AudioProfileVector &getAudioProfiles() { return mProfiles; } 80112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie 81112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie bool hasValidAudioProfile() const { return mProfiles.hasValidProfile(); } 82112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie 83112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie bool hasDynamicAudioProfile() const { return mProfiles.hasDynamicProfile(); } 84112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie 85112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie // searches for an exact match 86112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie status_t checkExactAudioProfile(uint32_t samplingRate, 87112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie audio_channel_mask_t channelMask, 88112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie audio_format_t format) const 89a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie { 90112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie return mProfiles.checkExactProfile(samplingRate, channelMask, format); 91a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie } 92112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie 93112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie // searches for a compatible match, currently implemented for input 94112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie // parameters are input|output, returned value is the best match. 95112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie status_t checkCompatibleAudioProfile(uint32_t &samplingRate, 96112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie audio_channel_mask_t &channelMask, 97112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie audio_format_t &format) const 98a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie { 99112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie return mProfiles.checkCompatibleProfile(samplingRate, channelMask, format, mType, mRole); 100a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie } 10156ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 102112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie void clearAudioProfiles() { return mProfiles.clearProfiles(); } 103112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie 10456ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi status_t checkGain(const struct audio_gain_config *gainConfig, int index) const; 10556ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 106112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie void pickAudioProfile(uint32_t &samplingRate, 107112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie audio_channel_mask_t &channelMask, 108112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie audio_format_t &format) const; 10956ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 11056ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi static const audio_format_t sPcmFormatCompareTable[]; 111112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie 11256ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi static int compareFormats(audio_format_t format1, audio_format_t format2); 11356ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 114e693002b0fb25099540588245892ed98103749baEric Laurent // Used to select an audio HAL output stream with a sample format providing the 115e693002b0fb25099540588245892ed98103749baEric Laurent // less degradation for a given AudioTrack sample format. 116e693002b0fb25099540588245892ed98103749baEric Laurent static bool isBetterFormatMatch(audio_format_t newFormat, 117e693002b0fb25099540588245892ed98103749baEric Laurent audio_format_t currentFormat, 118e693002b0fb25099540588245892ed98103749baEric Laurent audio_format_t targetFormat); 119e693002b0fb25099540588245892ed98103749baEric Laurent 12053615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie audio_module_handle_t getModuleHandle() const; 1219ee0540d3a61bff03d561ca431a371c3d9335d2bMikhail Naganov uint32_t getModuleVersionMajor() const; 122322b4d25387a04c9afebe998326d005bbdf17edeEric Laurent const char *getModuleName() const; 12353615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffie 124a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie bool useInputChannelMask() const 125a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie { 126a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie return ((mType == AUDIO_PORT_TYPE_DEVICE) && (mRole == AUDIO_PORT_ROLE_SOURCE)) || 127a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie ((mType == AUDIO_PORT_TYPE_MIX) && (mRole == AUDIO_PORT_ROLE_SINK)); 128a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie } 129a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie 130112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie inline bool isDirectOutput() const 131112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie { 132112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie return (mType == AUDIO_PORT_TYPE_MIX) && (mRole == AUDIO_PORT_ROLE_SOURCE) && 133112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie (mFlags & (AUDIO_OUTPUT_FLAG_DIRECT | AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD)); 134112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie } 135112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie 136cbb3044d6bfa9ab30c83b67874f40344e29805e1François Gaffie void addRoute(const sp<AudioRoute> &route) { mRoutes.add(route); } 137cbb3044d6bfa9ab30c83b67874f40344e29805e1François Gaffie const AudioRouteVector &getRoutes() const { return mRoutes; } 138cbb3044d6bfa9ab30c83b67874f40344e29805e1François Gaffie 139112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie void dump(int fd, int spaces, bool verbose = true) const; 140aa9811945f575614b3482d09e4d969792701cebbPaul McLean void log(const char* indent) const; 14156ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 142a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie AudioGainCollection mGains; // gain controllers 14356ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi sp<HwModule> mModule; // audio HW module exposing this I/O stream 14456ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 145ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffieprivate: 146112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie void pickChannelMask(audio_channel_mask_t &channelMask, const ChannelsVector &channelMasks) const; 147112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie void pickSamplingRate(uint32_t &rate,const SampleRateVector &samplingRates) const; 148112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie 149cbb3044d6bfa9ab30c83b67874f40344e29805e1François Gaffie String8 mName; 150a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie audio_port_type_t mType; 151a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie audio_port_role_t mRole; 152a8ecc2c72ca26389bd6b0162181d60aaeaca8149François Gaffie uint32_t mFlags; // attribute flags mask (e.g primary output, direct output...). 153112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie AudioProfileVector mProfiles; // AudioProfiles supported by this port (format, Rates, Channels) 154cbb3044d6bfa9ab30c83b67874f40344e29805e1François Gaffie AudioRouteVector mRoutes; // Routes involving this port 155ad3183e2d4cecd02f6261270a7ea1c68be0efa0fFrançois Gaffie static volatile int32_t mNextUniqueId; 15656ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi}; 15756ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 15853615e29c99c5e9d2ca77aaefd7bf5c770513120François Gaffieclass AudioPortConfig : public virtual RefBase 15956ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi{ 16056ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivipublic: 16156ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi AudioPortConfig(); 16256ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi virtual ~AudioPortConfig() {} 16356ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 16456ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi status_t applyAudioPortConfig(const struct audio_port_config *config, 165112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie struct audio_port_config *backupConfig = NULL); 16656ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi virtual void toAudioPortConfig(struct audio_port_config *dstConfig, 167112b0af826aeca45855690b9c105b2cdf9938bbeFrançois Gaffie const struct audio_port_config *srcConfig = NULL) const = 0; 16856ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi virtual sp<AudioPort> getAudioPort() const = 0; 169fb66dd9f95a1168698f072c4e5c2a2cf8c49a80fEric Laurent virtual bool hasSameHwModuleAs(const sp<AudioPortConfig>& other) const { 170fb66dd9f95a1168698f072c4e5c2a2cf8c49a80fEric Laurent return (other != 0) && 171fb66dd9f95a1168698f072c4e5c2a2cf8c49a80fEric Laurent (other->getAudioPort()->getModuleHandle() == getAudioPort()->getModuleHandle()); 172fb66dd9f95a1168698f072c4e5c2a2cf8c49a80fEric Laurent } 17356ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi uint32_t mSamplingRate; 17456ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi audio_format_t mFormat; 17556ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi audio_channel_mask_t mChannelMask; 17656ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi struct audio_gain_config mGain; 17756ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi}; 17856ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi 17956ec4ffcbae8aeac6c5245fc7b825d02e2e6cefdJean-Michel Trivi}; // namespace android 180