From 3a05365a93afccc5bb7db3bdc9f5d2efef69c8d3 Mon Sep 17 00:00:00 2001 From: vivek mehta Date: Tue, 4 Dec 2012 11:46:08 -0800 Subject: Squashed commit of audio changes from CodeAurora libstagefright: Add QC specific media format - Add QC specific media extensions - Add QC specific media definitions Change-Id: I7dca90be3b977701d9537f5e017117790a030f1f audio: Compile AudioParameter as shared library - AudioParameter as shared lib is needed by BT support in WFD source. Change-Id: I464b428ace0cbb57ce6bf7bf3b57d51a7d56f032 libstagefright: Send flush on both i/p and o/p ports together - ANR occurs in music due to race condition in OMX component if flush is issued separately for i/p and o/p ports as DSP only handles simultaneous flush on i/p and o/p ports. Change-Id: I5b16cd5a9b57c857dc8bed489d2663b8f54769e3 libstagefright: Enable extended A\V format - Add new files to support extended A\V format Change-Id: I1e61d78d35b868d55fd8e99f95de8cab9c465db4 libstagefright: Framework to plug-in propritory parser - Extend the current framework to plug-in propritory parser Change-Id: Ia586a3048420ddf1515261f20035589447263b7b audio: add support for QCOM audio formats - Add support for EVRC, QCELP, and WMA formats. Change-Id: Iaf80f982fc8b08617132dbd7d524a1748866745c frameworks/av: Support Tunnel Playback - Implement DirectTrack and DirectTrackClient - DirectTrack exposes API to client so it can create a direct output. - DirectTrackClient allows notifications to be sent to the client from DirectTrack - DirectTrack is being used for Tunnel Audio Change-Id: I2fbb18a781d8e44b8d65da9a357f6e39375f063a frameworks/av: Support LPA Playback Add support to enable Playback in LPA mode Change-Id: I1b8ac4904f4735017d62f3757ede7bbb56e62fd3 audio: Send correct channel mask in voice call recording. -Using popCount function to get channel count gives incorrect value on voice call recording. -Only STEREO and MONO bits to be considered to count channels on input Change-Id: I04c2c802422e868bdba0538ff8623dbf9eb659fe libstagefright: Thumbnail mode initial commit - use sync frame decoding mode when kClientNeedsFrameBuffer is set for hardware decoders - hardware decoder will only expect I frames, OMXCodec will set EOS on first ETB to stop more frames from being pulled - skip EOS check on FTB so that the first frame will be handled Change-Id: I0e8974e088fdcc468e27764861c128cfe291499f audio: Add support for QCOM's VOIP solution Change-Id: I1150f536fa204b535ca4019fdaa84f33f4695d93 audio: define QCOM audio parameters - Define QCOM audio paramters for FM, VOIP, fluence, SSR, and A2DP Change-Id: I29d02e37685846f6d4f00dee02e2726b015eaae7 Add ifdefs for QCOM enhanced features Change-Id: Ic8e5fe6ecc058466ced71030883b1af6c2bc055c --- include/media/AudioParameter.h | 8 + include/media/AudioSystem.h | 7 + include/media/AudioTrack.h | 25 ++- include/media/IAudioFlinger.h | 23 +++ include/media/IDirectTrack.h | 93 +++++++++ include/media/IDirectTrackClient.h | 51 +++++ include/media/MediaPlayerInterface.h | 4 + include/media/MediaProfiles.h | 5 + include/media/mediarecorder.h | 12 ++ include/media/stagefright/AudioPlayer.h | 21 ++- include/media/stagefright/ExtendedWriter.h | 143 ++++++++++++++ include/media/stagefright/LPAPlayer.h | 290 +++++++++++++++++++++++++++++ include/media/stagefright/OMXCodec.h | 26 +++ include/media/stagefright/QCOMXCodec.h | 98 ++++++++++ include/media/stagefright/TunnelPlayer.h | 251 +++++++++++++++++++++++++ include/media/stagefright/WAVEWriter.h | 108 +++++++++++ 16 files changed, 1155 insertions(+), 10 deletions(-) create mode 100644 include/media/IDirectTrack.h create mode 100644 include/media/IDirectTrackClient.h create mode 100644 include/media/stagefright/ExtendedWriter.h create mode 100644 include/media/stagefright/LPAPlayer.h create mode 100644 include/media/stagefright/QCOMXCodec.h create mode 100644 include/media/stagefright/TunnelPlayer.h create mode 100644 include/media/stagefright/WAVEWriter.h (limited to 'include') diff --git a/include/media/AudioParameter.h b/include/media/AudioParameter.h index 891bc4b..d29c699 100644 --- a/include/media/AudioParameter.h +++ b/include/media/AudioParameter.h @@ -1,5 +1,6 @@ /* * Copyright (C) 2008-2011 The Android Open Source Project + * Copyright (c) 2012, The Linux Foundation. All rights reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -48,6 +49,13 @@ public: static const char * const keyFrameCount; static const char * const keyInputSource; static const char * const keyScreenState; +#ifdef QCOM_HARDWARE + static const char * const keyHandleFm; + static const char * const keyVoipCheck; + static const char * const keyFluenceType; + static const char * const keySSR; + static const char * const keyHandleA2dpDevice; +#endif String8 toString(); diff --git a/include/media/AudioSystem.h b/include/media/AudioSystem.h index 49e1afc..e66fc3a 100644 --- a/include/media/AudioSystem.h +++ b/include/media/AudioSystem.h @@ -1,4 +1,8 @@ /* + * Copyright (c) 2012, The Linux Foundation. All rights reserved. + * Not a Contribution, Apache license notifications and license are retained + * for attribution purposes only. + * * Copyright (C) 2008 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); @@ -144,6 +148,9 @@ public: INPUT_CLOSED, INPUT_CONFIG_CHANGED, STREAM_CONFIG_CHANGED, +#ifdef QCOM_HARDWARE + EFFECT_CONFIG_CHANGED, +#endif NUM_CONFIG_EVENTS }; diff --git a/include/media/AudioTrack.h b/include/media/AudioTrack.h index 34108b3..77a0b26 100644 --- a/include/media/AudioTrack.h +++ b/include/media/AudioTrack.h @@ -31,6 +31,10 @@ #include #include +#ifdef QCOM_HARDWARE +#include +#endif + namespace android { // ---------------------------------------------------------------------------- @@ -39,7 +43,11 @@ class audio_track_cblk_t; // ---------------------------------------------------------------------------- -class AudioTrack : virtual public RefBase +class AudioTrack : +#ifdef QCOM_HARDWARE + public BnDirectTrackClient, +#endif + virtual public RefBase { public: enum channel_index { @@ -451,6 +459,11 @@ public: */ status_t dump(int fd, const Vector& args) const; +#ifdef QCOM_HARDWARE + virtual void notify(int msg); + virtual status_t getTimeStamp(uint64_t *tstamp); +#endif + protected: /* copying audio tracks is not allowed */ AudioTrack(const AudioTrack& other); @@ -496,6 +509,9 @@ protected: status_t restoreTrack_l(audio_track_cblk_t*& cblk, bool fromStart); bool stopped_l() const { return !mActive; } +#ifdef QCOM_HARDWARE + sp mDirectTrack; +#endif sp mAudioTrack; sp mCblkMemory; sp mAudioTrackThread; @@ -529,10 +545,17 @@ protected: uint32_t mUpdatePeriod; bool mFlushed; // FIXME will be made obsolete by making flush() synchronous audio_output_flags_t mFlags; +#ifdef QCOM_HARDWARE + sp mAudioFlinger; + audio_io_handle_t mAudioDirectOutput; +#endif int mSessionId; int mAuxEffectId; mutable Mutex mLock; status_t mRestoreStatus; +#ifdef QCOM_HARDWARE + void* mObserver; +#endif bool mIsTimed; int mPreviousPriority; // before start() SchedPolicy mPreviousSchedulingGroup; diff --git a/include/media/IAudioFlinger.h b/include/media/IAudioFlinger.h index 5170a87..c895c13 100644 --- a/include/media/IAudioFlinger.h +++ b/include/media/IAudioFlinger.h @@ -1,4 +1,8 @@ /* + * Copyright (c) 2012, The Linux Foundation. All rights reserved. + * Not a Contribution, Apache license notifications and license are retained + * for attribution purposes only. + * * Copyright (C) 2007 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); @@ -24,6 +28,10 @@ #include #include #include +#ifdef QCOM_HARDWARE +#include +#include +#endif #include #include #include @@ -69,6 +77,21 @@ public: int *sessionId, status_t *status) = 0; +#ifdef QCOM_HARDWARE + /* create a direct audio track and registers it with AudioFlinger. + * return null if the track cannot be created. + */ + virtual sp createDirectTrack( + pid_t pid, + uint32_t sampleRate, + audio_channel_mask_t channelMask, + audio_io_handle_t output, + int *sessionId, + IDirectTrackClient* client, + audio_stream_type_t streamType, + status_t *status) = 0; +#endif + virtual sp openRecord( pid_t pid, audio_io_handle_t input, diff --git a/include/media/IDirectTrack.h b/include/media/IDirectTrack.h new file mode 100644 index 0000000..c1f4f09 --- /dev/null +++ b/include/media/IDirectTrack.h @@ -0,0 +1,93 @@ +/* + * Copyright (c) 2012, The Linux Foundation. All rights reserved. + * Not a Contribution, Apache license notifications and license are retained + * for attribution purposes only. + * + * Copyright (C) 2007 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef ANDROID_IDIRECTTRACK_H +#define ANDROID_IDIRECTTRACK_H + +#include +#include + +#include +#include +#include +#include + + +namespace android { + +// ---------------------------------------------------------------------------- + +class IDirectTrack : public IInterface +{ +public: + DECLARE_META_INTERFACE(DirectTrack); + + /* After it's created the track is not active. Call start() to + * make it active. If set, the callback will start being called. + */ + virtual status_t start() = 0; + + /* Stop a track. If set, the callback will cease being called and + * obtainBuffer will return an error. Buffers that are already released + * will be processed, unless flush() is called. + */ + virtual void stop() = 0; + + /* flush a stopped track. All pending buffers are discarded. + * This function has no effect if the track is not stoped. + */ + virtual void flush() = 0; + + /* mute or unmutes this track. + * While mutted, the callback, if set, is still called. + */ + virtual void mute(bool) = 0; + + /* Pause a track. If set, the callback will cease being called and + * obtainBuffer will return an error. Buffers that are already released + * will be processed, unless flush() is called. + */ + virtual void pause() = 0; + + /* set volume for both left and right channels. + */ + virtual void setVolume(float l, float r) = 0; + + virtual ssize_t write(const void*, size_t) = 0; + + virtual int64_t getTimeStamp() = 0; +}; + +// ---------------------------------------------------------------------------- + +class BnDirectTrack : public BnInterface +{ +public: + virtual status_t onTransact( uint32_t code, + const Parcel& data, + Parcel* reply, + uint32_t flags = 0); +}; + +// ---------------------------------------------------------------------------- + +}; // namespace android + +#endif // ANDROID_IAUDIOTRACK_H diff --git a/include/media/IDirectTrackClient.h b/include/media/IDirectTrackClient.h new file mode 100644 index 0000000..9383690 --- /dev/null +++ b/include/media/IDirectTrackClient.h @@ -0,0 +1,51 @@ +/* + * Copyright (c) 2012, The Linux Foundation. All rights reserved. + * Not a Contribution, Apache license notifications and license are retained + * for attribution purposes only. + * + * Copyright (C) 2007 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef ANDROID_IDIRECTTRACKCLIENT_H +#define ANDROID_IDIRECTTRACKCLIENT_H + +#include +#include +#include + +namespace android { + +class IDirectTrackClient: public IInterface +{ +public: + DECLARE_META_INTERFACE(DirectTrackClient); + + virtual void notify(int msg) = 0; +}; + +// ---------------------------------------------------------------------------- + +class BnDirectTrackClient: public BnInterface +{ +public: + virtual status_t onTransact( uint32_t code, + const Parcel& data, + Parcel* reply, + uint32_t flags = 0); +}; + +}; // namespace android + +#endif // ANDROID_IDIRECTTRACKCLIENT_H diff --git a/include/media/MediaPlayerInterface.h b/include/media/MediaPlayerInterface.h index b7bee3f..a7570d6 100644 --- a/include/media/MediaPlayerInterface.h +++ b/include/media/MediaPlayerInterface.h @@ -110,6 +110,10 @@ public: virtual status_t setPlaybackRatePermille(int32_t rate) { return INVALID_OPERATION; } virtual bool needsTrailingPadding() { return true; } +#ifdef QCOM_HARDWARE + virtual ssize_t sampleRate() const {return 0;}; + virtual status_t getTimeStamp(uint64_t *tstamp) {return 0;}; +#endif }; MediaPlayerBase() : mCookie(0), mNotify(0) {} diff --git a/include/media/MediaProfiles.h b/include/media/MediaProfiles.h index 60d6bef..0df9fd4 100644 --- a/include/media/MediaProfiles.h +++ b/include/media/MediaProfiles.h @@ -1,6 +1,7 @@ /* ** ** Copyright 2010, The Android Open Source Project. + ** Copyright (c) 2010 - 2012, The Linux Foundation. All rights reserved. ** ** Licensed under the Apache License, Version 2.0 (the "License"); ** you may not use this file except in compliance with the License. @@ -461,6 +462,10 @@ private: static VideoEncoderCap* createDefaultH263VideoEncoderCap(); static VideoEncoderCap* createDefaultM4vVideoEncoderCap(); static AudioEncoderCap* createDefaultAmrNBEncoderCap(); +#ifdef QCOM_HARDWARE + static AudioEncoderCap* createDefaultAacEncoderCap(); + static AudioEncoderCap* createDefaultLpcmEncoderCap(); +#endif static int findTagForName(const NameToTagMap *map, size_t nMappings, const char *name); diff --git a/include/media/mediarecorder.h b/include/media/mediarecorder.h index 3c2e700..6dfa5d9 100644 --- a/include/media/mediarecorder.h +++ b/include/media/mediarecorder.h @@ -1,5 +1,6 @@ /* ** Copyright (C) 2008 The Android Open Source Project + ** Copyright (c) 2010 - 2012, The Linux Foundation. All rights reserved. ** ** Licensed under the Apache License, Version 2.0 (the "License"); ** you may not use this file except in compliance with the License. @@ -67,6 +68,12 @@ enum output_format { /* H.264/AAC data encapsulated in MPEG2/TS */ OUTPUT_FORMAT_MPEG2TS = 8, +#ifdef QCOM_HARDWARE + OUTPUT_FORMAT_QCP = 9, // QCP file format + OUTPUT_FORMAT_THREE_GPP2 = 10, /*3GPP2*/ + OUTPUT_FORMAT_WAVE = 11, /*WAVE*/ +#endif + OUTPUT_FORMAT_LIST_END // must be last - used to validate format type }; @@ -77,6 +84,11 @@ enum audio_encoder { AUDIO_ENCODER_AAC = 3, AUDIO_ENCODER_HE_AAC = 4, AUDIO_ENCODER_AAC_ELD = 5, +#ifdef QCOM_HARDWARE + AUDIO_ENCODER_EVRC = 6, + AUDIO_ENCODER_QCELP = 7, + AUDIO_ENCODER_LPCM = 8, +#endif AUDIO_ENCODER_LIST_END // must be the last - used to validate the audio encoder type }; diff --git a/include/media/stagefright/AudioPlayer.h b/include/media/stagefright/AudioPlayer.h index 1dc408f..624fe3e 100644 --- a/include/media/stagefright/AudioPlayer.h +++ b/include/media/stagefright/AudioPlayer.h @@ -43,27 +43,27 @@ public: virtual ~AudioPlayer(); // Caller retains ownership of "source". - void setSource(const sp &source); + virtual void setSource(const sp &source); // Return time in us. virtual int64_t getRealTimeUs(); - status_t start(bool sourceAlreadyStarted = false); + virtual status_t start(bool sourceAlreadyStarted = false); - void pause(bool playPendingSamples = false); - void resume(); + virtual void pause(bool playPendingSamples = false); + virtual void resume(); // Returns the timestamp of the last buffer played (in us). - int64_t getMediaTimeUs(); + virtual int64_t getMediaTimeUs(); // Returns true iff a mapping is established, i.e. the AudioPlayer // has played at least one frame of audio. - bool getMediaTimeMapping(int64_t *realtime_us, int64_t *mediatime_us); + virtual bool getMediaTimeMapping(int64_t *realtime_us, int64_t *mediatime_us); - status_t seekTo(int64_t time_us); + virtual status_t seekTo(int64_t time_us); - bool isSeeking(); - bool reachedEOS(status_t *finalStatus); + virtual bool isSeeking(); + virtual bool reachedEOS(status_t *finalStatus); status_t setPlaybackRatePermille(int32_t ratePermille); @@ -91,6 +91,9 @@ private: int64_t mSeekTimeUs; bool mStarted; +#ifdef QCOM_HARDWARE + bool mSourcePaused; +#endif bool mIsFirstBuffer; status_t mFirstBufferResult; diff --git a/include/media/stagefright/ExtendedWriter.h b/include/media/stagefright/ExtendedWriter.h new file mode 100644 index 0000000..23944b0 --- /dev/null +++ b/include/media/stagefright/ExtendedWriter.h @@ -0,0 +1,143 @@ +/* + * Copyright (c) 2012, The Linux Foundation. All rights reserved. + * + * Not a Contribution, Apache license notifications and license are retained + * for attribution purposes only. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef EXTENDED_WRITER_H_ + +#define EXTENDED_WRITER_H_ + +#include + +#include +#include +#include + +#define LITERAL_TO_STRING_INTERNAL(x) #x +#define LITERAL_TO_STRING(x) LITERAL_TO_STRING_INTERNAL(x) + +#define CHECK_EQ(x,y) \ + LOG_ALWAYS_FATAL_IF( \ + (x) != (y), \ + __FILE__ ":" LITERAL_TO_STRING(__LINE__) " " #x " != " #y) + +#define CHECK(x) \ + LOG_ALWAYS_FATAL_IF( \ + !(x), \ + __FILE__ ":" LITERAL_TO_STRING(__LINE__) " " #x) + +namespace android { + +struct MediaSource; +struct MetaData; + +struct ExtendedWriter : public MediaWriter { + ExtendedWriter(const char *filename); + ExtendedWriter(int fd); + + status_t initCheck() const; + + virtual status_t addSource(const sp &source); + virtual bool reachedEOS(); + virtual status_t start(MetaData *params = NULL); + virtual status_t stop(); + virtual status_t pause(); + +protected: + virtual ~ExtendedWriter(); + +private: + FILE *mFile; + status_t mInitCheck; + sp mSource; + bool mStarted; + volatile bool mPaused; + volatile bool mResumed; + volatile bool mDone; + volatile bool mReachedEOS; + pthread_t mThread; + int64_t mEstimatedSizeBytes; + int64_t mEstimatedDurationUs; + + int32_t mFormat; + + //QCP/EVRC header + struct QCPEVRCHeader + { + /* RIFF Section */ + char riff[4]; + unsigned int s_riff; + char qlcm[4]; + + /* Format chunk */ + char fmt[4]; + unsigned int s_fmt; + char mjr; + char mnr; + unsigned int data1; + + /* UNIQUE ID of the codec */ + unsigned short data2; + unsigned short data3; + char data4[8]; + unsigned short ver; + + /* Codec Info */ + char name[80]; + unsigned short abps; + + /* average bits per sec of the codec */ + unsigned short bytes_per_pkt; + unsigned short samp_per_block; + unsigned short samp_per_sec; + unsigned short bits_per_samp; + unsigned char vr_num_of_rates; + + /* Rate Header fmt info */ + unsigned char rvd1[3]; + unsigned short vr_bytes_per_pkt[8]; + unsigned int rvd2[5]; + + /* Vrat chunk */ + unsigned char vrat[4]; + unsigned int s_vrat; + unsigned int v_rate; + unsigned int size_in_pkts; + + /* Data chunk */ + unsigned char data[4]; + unsigned int s_data; + } __attribute__ ((packed)); + + struct QCPEVRCHeader mHeader; + off_t mOffset; //note off_t + + static void *ThreadWrapper(void *); + status_t threadFunc(); + bool exceedsFileSizeLimit(); + bool exceedsFileDurationLimit(); + + ExtendedWriter(const ExtendedWriter &); + ExtendedWriter &operator=(const ExtendedWriter &); + + status_t writeQCPHeader( ); + status_t writeEVRCHeader( ); +}; + +} // namespace android + +#endif // AMR_WRITER_H_ diff --git a/include/media/stagefright/LPAPlayer.h b/include/media/stagefright/LPAPlayer.h new file mode 100644 index 0000000..c351211 --- /dev/null +++ b/include/media/stagefright/LPAPlayer.h @@ -0,0 +1,290 @@ +/* + * Copyright (C) 2009 The Android Open Source Project + * Copyright (c) 2009-2012, The Linux Foundation. All rights reserved. + * Not a Contribution, Apache license notifications and license are retained + * for attribution purposes only. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef LPA_PLAYER_H_ + +#define LPA_PLAYER_H_ + +#include "AudioPlayer.h" +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +// Pause timeout = 3sec +#define LPA_PAUSE_TIMEOUT_USEC 3000000 + +namespace android { + +class LPAPlayer : public AudioPlayer { +public: + enum { + REACHED_EOS, + SEEK_COMPLETE + }; + + enum { + TRACK_DIRECT, + TRACK_REGULAR, + TRACK_NONE + }; + + LPAPlayer(const sp &audioSink, bool &initCheck, + AwesomePlayer *audioObserver = NULL); + + virtual ~LPAPlayer(); + + // Caller retains ownership of "source". + virtual void setSource(const sp &source); + + // Return time in us. + virtual int64_t getRealTimeUs(); + + virtual status_t start(bool sourceAlreadyStarted = false); + + virtual void pause(bool playPendingSamples = false); + virtual void resume(); + + // Returns the timestamp of the last buffer played (in us). + virtual int64_t getMediaTimeUs(); + + // Returns true iff a mapping is established, i.e. the LPAPlayer + // has played at least one frame of audio. + virtual bool getMediaTimeMapping(int64_t *realtime_us, int64_t *mediatime_us); + + virtual status_t seekTo(int64_t time_us); + + virtual bool isSeeking(); + virtual bool reachedEOS(status_t *finalStatus); + + static int objectsAlive; +private: + int64_t mPositionTimeMediaUs; + int64_t mPositionTimeRealUs; + bool mInternalSeeking; + bool mIsAudioRouted; + bool mStarted; + bool mPaused; + bool mA2DPEnabled; + int32_t mChannelMask; + int32_t numChannels; + int32_t mSampleRate; + int64_t mLatencyUs; + size_t mFrameSize; + int64_t mTimeStarted; + int64_t mTimePlayed; + int64_t mNumFramesPlayed; + int64_t mNumFramesPlayedSysTimeUs; + int64_t mNumA2DPBytesPlayed; + + void clearPowerManager(); + + class PMDeathRecipient : public IBinder::DeathRecipient { + public: + PMDeathRecipient(void *obj){parentClass = (LPAPlayer *)obj;} + virtual ~PMDeathRecipient() {} + + // IBinder::DeathRecipient + virtual void binderDied(const wp& who); + + private: + LPAPlayer *parentClass; + PMDeathRecipient(const PMDeathRecipient&); + PMDeathRecipient& operator = (const PMDeathRecipient&); + + friend class LPAPlayer; + }; + + friend class PMDeathRecipient; + + void acquireWakeLock(); + void releaseWakeLock(); + + sp mPowerManager; + sp mWakeLockToken; + sp mDeathRecipient; + + pthread_t decoderThread; + + pthread_t A2DPNotificationThread; + + //Kill Thread boolean + bool killDecoderThread; + + + + bool killA2DPNotificationThread; + + //Thread alive boolean + bool decoderThreadAlive; + + + bool a2dpNotificationThreadAlive; + + //Declare the condition Variables and Mutex + + pthread_mutex_t decoder_mutex; + + pthread_mutex_t audio_sink_setup_mutex; + + pthread_mutex_t a2dp_notification_mutex; + + + + pthread_cond_t decoder_cv; + + + pthread_cond_t a2dp_notification_cv; + + + // make sure Decoder thread has exited + void requestAndWaitForDecoderThreadExit(); + + + // make sure the Effects thread also exited + void requestAndWaitForA2DPNotificationThreadExit(); + + static void *decoderThreadWrapper(void *me); + void decoderThreadEntry(); + static void *A2DPNotificationThreadWrapper(void *me); + void A2DPNotificationThreadEntry(); + + void createThreads(); + + volatile bool mIsA2DPEnabled; + + //Structure to recieve the BT notification from the flinger. + class AudioFlingerLPAdecodeClient: public IBinder::DeathRecipient, public BnAudioFlingerClient { + public: + AudioFlingerLPAdecodeClient(void *obj); + + LPAPlayer *pBaseClass; + // DeathRecipient + virtual void binderDied(const wp& who); + + // IAudioFlingerClient + + // indicate a change in the configuration of an output or input: keeps the cached + // values for output/input parameters upto date in client process + virtual void ioConfigChanged(int event, audio_io_handle_t ioHandle, const void *param2); + + friend class LPAPlayer; + }; + + sp mAudioFlinger; + + // helper function to obtain AudioFlinger service handle + void getAudioFlinger(); + + void handleA2DPSwitch(); + void onPauseTimeOut(); + + sp AudioFlingerClient; + friend class AudioFlingerLPAdecodeClient; + Mutex AudioFlingerLock; + sp mSource; + + MediaBuffer *mInputBuffer; + + Mutex mLock; + Mutex mResumeLock; + + bool mSeeking; + bool mReachedEOS; + bool mReachedOutputEOS; + status_t mFinalStatus; + int64_t mSeekTimeUs; + int64_t mPauseTime; + + + bool mIsFirstBuffer; + status_t mFirstBufferResult; + MediaBuffer *mFirstBuffer; + TimedEventQueue mQueue; + bool mQueueStarted; + sp mPauseEvent; + bool mPauseEventPending; + + sp mAudioSink; + AwesomePlayer *mObserver; + int mTrackType; + + static size_t AudioSinkCallback( + MediaPlayerBase::AudioSink *audioSink, + void *data, size_t size, void *me); + + enum A2DPState { + A2DP_ENABLED, + A2DP_DISABLED, + A2DP_CONNECT, + A2DP_DISCONNECT + }; + + int64_t getTimeStamp(A2DPState state); + + size_t fillBuffer(void *data, size_t size); + + int64_t getRealTimeUsLocked(); + + void reset(); + + status_t setupAudioSink(); + static size_t AudioCallback( + MediaPlayerBase::AudioSink *audioSink, + void *buffer, size_t size, void *cookie); + size_t AudioCallback(void *cookie, void *data, size_t size); + + LPAPlayer(const LPAPlayer &); + LPAPlayer &operator=(const LPAPlayer &); +}; + +struct TimedEvent : public TimedEventQueue::Event { + TimedEvent(LPAPlayer *player, + void (LPAPlayer::*method)()) + : mPlayer(player), + mMethod(method) { + } + +protected: + virtual ~TimedEvent() {} + + virtual void fire(TimedEventQueue *queue, int64_t /* now_us */) { + (mPlayer->*mMethod)(); + } + +private: + LPAPlayer *mPlayer; + void (LPAPlayer::*mMethod)(); + + TimedEvent(const TimedEvent &); + TimedEvent &operator=(const TimedEvent &); +}; + +} // namespace android + +#endif // LPA_PLAYER_H_ + diff --git a/include/media/stagefright/OMXCodec.h b/include/media/stagefright/OMXCodec.h index 2439be6..aad8844 100644 --- a/include/media/stagefright/OMXCodec.h +++ b/include/media/stagefright/OMXCodec.h @@ -1,5 +1,6 @@ /* * Copyright (C) 2009 The Android Open Source Project + * Copyright (c) 2010 - 2012, The Linux Foundation. All rights reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -22,6 +23,9 @@ #include #include #include +#ifdef QCOM_HARDWARE +#include +#endif #include #include @@ -100,6 +104,10 @@ struct OMXCodec : public MediaSource, kSupportsMultipleFramesPerInputBuffer = 1024, kRequiresLargerEncoderOutputBuffer = 2048, kOutputBuffersAreUnreadable = 4096, +#ifdef QCOM_HARDWARE + kRequiresGlobalFlush = 0x20000000, // 2^29 + kRequiresWMAProComponent = 0x40000000, //2^30 +#endif }; struct CodecNameAndQuirks { @@ -127,6 +135,11 @@ private: // Make sure mLock is accessible to OMXCodecObserver friend class OMXCodecObserver; +#ifdef QCOM_HARDWARE + // QCOMXCodec can access variables of OMXCodec + friend class QCOMXCodec; +#endif + // Call this with mLock hold void on_message(const omx_message &msg); @@ -143,6 +156,9 @@ private: }; enum { +#ifdef QCOM_HARDWARE + kPortIndexBoth = -1, +#endif kPortIndexInput = 0, kPortIndexOutput = 1 }; @@ -250,6 +266,11 @@ private: void setG711Format(int32_t numChannels); +#ifdef QCOM_HARDWARE + void setEVRCFormat( int32_t sampleRate, int32_t numChannels, int32_t bitRate); + void setQCELPFormat( int32_t sampleRate, int32_t numChannels, int32_t bitRate); +#endif + status_t setVideoPortFormatType( OMX_U32 portIndex, OMX_VIDEO_CODINGTYPE compressionFormat, @@ -361,6 +382,11 @@ private: OMXCodec(const OMXCodec &); OMXCodec &operator=(const OMXCodec &); + +#ifdef QCOM_HARDWARE + status_t setWMAFormat(const sp &inputFormat); + void setAC3Format(int32_t numChannels, int32_t sampleRate); +#endif }; struct CodecCapabilities { diff --git a/include/media/stagefright/QCOMXCodec.h b/include/media/stagefright/QCOMXCodec.h new file mode 100644 index 0000000..7259af9 --- /dev/null +++ b/include/media/stagefright/QCOMXCodec.h @@ -0,0 +1,98 @@ +/* + * Copyright (c) 2012, The Linux Foundation. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are + * met: + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of The Linux Foundation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR + * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, + * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN + * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef QC_OMX_CODEC_H_ + +#define QC_OMX_CODEC_H_ + +#include +#include +#include +#include +#include +#include + +#include + +namespace android { + +struct MediaCodecList; +struct OMXCodec; + +enum{ + kRequiresWMAProComponent = 0x40000000, +}; + + +struct QCOMXCodec { + + static uint32_t getQCComponentQuirks(const MediaCodecList *list, size_t index); + + static status_t configureDIVXCodec(const sp &meta, char* mime, + sp OMXhandle,IOMX::node_id nodeID, int port_index); + + static status_t setQCFormat(const sp &meta, char* mime, + sp OMXhandle,IOMX::node_id nodeID, + OMXCodec *handle, bool isEncoder); + + static status_t setWMAFormat(const sp &meta, sp OMXhandle, + IOMX::node_id nodeID, bool isEncoder ); + + static status_t setQCVideoInputFormat(const char *mime, + OMX_VIDEO_CODINGTYPE *compressionFormat); + + static status_t setQCVideoOutputFormat(const char *mime, + OMX_VIDEO_CODINGTYPE *compressionFormat); + + static status_t checkQCFormats(int format, AString* meta); + + static void setASFQuirks(uint32_t quirks, const sp &meta, + const char* componentName); + + static void checkAndAddRawFormat(OMXCodec *handle, const sp &meta); + + static void setEVRCFormat(int32_t numChannels, int32_t sampleRate, + sp OMXhandle, IOMX::node_id nodeID, + OMXCodec *handle, bool isEncoder ); + + static void setQCELPFormat(int32_t numChannels, int32_t sampleRate, + sp OMXhandle, IOMX::node_id nodeID, + OMXCodec *handle, bool isEncoder ); + + static void setAC3Format(int32_t numChannels, int32_t sampleRate, + sp OMXhandle, IOMX::node_id nodeID); + + static void checkQCRole(const sp &omx, IOMX::node_id node, + bool isEncoder,const char *mime); + +}; + +} +#endif /*QC_OMX_CODEC_H_ */ + diff --git a/include/media/stagefright/TunnelPlayer.h b/include/media/stagefright/TunnelPlayer.h new file mode 100644 index 0000000..71c4f10 --- /dev/null +++ b/include/media/stagefright/TunnelPlayer.h @@ -0,0 +1,251 @@ +/* + * Copyright (C) 2009 The Android Open Source Project + * + * Copyright (c) 2009-2012, The Linux Foundation. All rights reserved. + * Not a Contribution, Apache license notifications and license are retained + * for attribution purposes only. + * + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef TUNNEL_PLAYER_H_ + +#define TUNNEL_PLAYER_H_ + +#include "AudioPlayer.h" +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +// Pause timeout = 3sec +#define TUNNEL_PAUSE_TIMEOUT_USEC 3000000 +namespace android { + +class TunnelPlayer : public AudioPlayer { +public: + enum { + REACHED_EOS, + SEEK_COMPLETE + }; + + TunnelPlayer(const sp &audioSink, bool &initCheck, + AwesomePlayer *audioObserver = NULL, bool hasVideo = false); + + virtual ~TunnelPlayer(); + + // Caller retains ownership of "source". + virtual void setSource(const sp &source); + + // Return time in us. + virtual int64_t getRealTimeUs(); + + virtual status_t start(bool sourceAlreadyStarted = false); + + virtual void pause(bool playPendingSamples = false); + virtual void resume(); + + // Returns the timestamp of the last buffer played (in us). + virtual int64_t getMediaTimeUs(); + + // Returns true iff a mapping is established, i.e. the TunnelPlayer + // has played at least one frame of audio. + virtual bool getMediaTimeMapping(int64_t *realtime_us, int64_t *mediatime_us); + + virtual status_t seekTo(int64_t time_us); + + virtual bool isSeeking(); + virtual bool reachedEOS(status_t *finalStatus); + + + static int mTunnelObjectsAlive; +private: + int64_t mPositionTimeMediaUs; + int64_t mPositionTimeRealUs; + bool mInternalSeeking; + bool mIsAudioRouted; + bool mStarted; + bool mPaused; + bool mA2DPEnabled; + int32_t mChannelMask; + int32_t numChannels; + int32_t mSampleRate; + int64_t mLatencyUs; + size_t mFrameSize; + int64_t mNumFramesPlayed; + int64_t mNumFramesPlayedSysTimeUs; + audio_format_t mFormat; + bool mHasVideo; + void clearPowerManager(); + + class PMDeathRecipient : public IBinder::DeathRecipient { + public: + PMDeathRecipient(void *obj){parentClass = (TunnelPlayer *)obj;} + virtual ~PMDeathRecipient() {} + + // IBinder::DeathRecipient + virtual void binderDied(const wp& who); + + private: + TunnelPlayer *parentClass; + PMDeathRecipient(const PMDeathRecipient&); + PMDeathRecipient& operator = (const PMDeathRecipient&); + + friend class TunnelPlayer; + }; + + friend class PMDeathRecipient; + + void acquireWakeLock(); + void releaseWakeLock(); + + sp mPowerManager; + sp mWakeLockToken; + sp mDeathRecipient; + + pthread_t extractorThread; + + //Kill Thread boolean + bool killExtractorThread; + + //Thread alive boolean + bool extractorThreadAlive; + + + //Declare the condition Variables and Mutex + + pthread_mutex_t extractor_mutex; + pthread_cond_t extractor_cv; + + + // make sure Decoder thread has exited + void requestAndWaitForExtractorThreadExit(); + + + static void *extractorThreadWrapper(void *me); + void extractorThreadEntry(); + + void createThreads(); + + volatile bool mIsA2DPEnabled; + + //Structure to recieve the BT notification from the flinger. + class AudioFlingerTunneldecodeClient: public IBinder::DeathRecipient, public BnAudioFlingerClient { + public: + AudioFlingerTunneldecodeClient(void *obj); + + TunnelPlayer *pBaseClass; + // DeathRecipient + virtual void binderDied(const wp& who); + + // IAudioFlingerClient + + // indicate a change in the configuration of an output or input: keeps the cached + // values for output/input parameters upto date in client process + virtual void ioConfigChanged(int event, audio_io_handle_t ioHandle, const void *param2); + + friend class TunnelPlayer; + }; + + sp mAudioFlinger; + + // helper function to obtain AudioFlinger service handle + void getAudioFlinger(); + void onPauseTimeOut(); + + sp mAudioFlingerClient; + friend class AudioFlingerTunneldecodeClient; + Mutex mAudioFlingerLock; + sp mSource; + + MediaBuffer *mInputBuffer; + + Mutex pmLock; + Mutex mLock; + + bool mSeeking; + bool mReachedEOS; + bool mReachedOutputEOS; + status_t mFinalStatus; + int64_t mSeekTimeUs; + int64_t mPauseTime; + + + bool mIsFirstBuffer; + status_t mFirstBufferResult; + MediaBuffer *mFirstBuffer; + TimedEventQueue mQueue; + bool mQueueStarted; + sp mPauseEvent; + bool mPauseEventPending; + + sp mAudioSink; + AwesomePlayer *mObserver; + + static size_t AudioSinkCallback( + MediaPlayerBase::AudioSink *audioSink, + void *data, size_t size, void *me); + + enum A2DPState { + A2DP_ENABLED, + A2DP_DISABLED, + A2DP_CONNECT, + A2DP_DISCONNECT + }; + + int64_t getTimeStamp(A2DPState state); + + size_t fillBuffer(void *data, size_t size); + + int64_t getRealTimeUsLocked(); + + void reset(); + + TunnelPlayer(const TunnelPlayer &); + TunnelPlayer &operator=(const TunnelPlayer &); +}; + +struct TunnelEvent : public TimedEventQueue::Event { + TunnelEvent(TunnelPlayer *player, + void (TunnelPlayer::*method)()) + : mPlayer(player), + mMethod(method) { + } + +protected: + virtual ~TunnelEvent() {} + + virtual void fire(TimedEventQueue *queue, int64_t /* now_us */) { + (mPlayer->*mMethod)(); + } + +private: + TunnelPlayer *mPlayer; + void (TunnelPlayer::*mMethod)(); + + TunnelEvent(const TunnelEvent &); + TunnelEvent &operator=(const TunnelEvent &); +}; + +} // namespace android + +#endif // LPA_PLAYER_H_ diff --git a/include/media/stagefright/WAVEWriter.h b/include/media/stagefright/WAVEWriter.h new file mode 100644 index 0000000..766d8f4 --- /dev/null +++ b/include/media/stagefright/WAVEWriter.h @@ -0,0 +1,108 @@ +/* + * Copyright (c) 2012, The Linux Foundation. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are + * met: + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of The Linux Foundation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR + * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, + * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN + * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef WAVE_WRITER_H_ + +#define WAVE_WRITER_H_ + +#include + +#include +#include + +namespace android { + + +#define ID_RIFF 0x46464952 +#define ID_WAVE 0x45564157 +#define ID_FMT 0x20746d66 +#define ID_DATA 0x61746164 +#define FORMAT_PCM 1 + + +struct MediaSource; +struct MetaData; + +struct wav_header { + uint32_t riff_id; + uint32_t riff_sz; + uint32_t riff_fmt; + uint32_t fmt_id; + uint32_t fmt_sz; + uint16_t audio_format; + uint16_t num_channels; + uint32_t sample_rate; + uint32_t byte_rate; /* sample_rate * num_channels * bps / 8 */ + uint16_t block_align; /* num_channels * bps / 8 */ + uint16_t bits_per_sample; + uint32_t data_id; + uint32_t data_sz; +}; + + +struct WAVEWriter : public MediaWriter { + WAVEWriter(const char *filename); + WAVEWriter(int fd); + + status_t initCheck() const; + + virtual status_t addSource(const sp &source); + virtual bool reachedEOS(); + virtual status_t start(MetaData *params = NULL); + virtual status_t stop(); + virtual status_t pause(); + +protected: + virtual ~WAVEWriter(); + +private: + int mFd; + status_t mInitCheck; + sp mSource; + bool mStarted; + volatile bool mPaused; + volatile bool mResumed; + volatile bool mDone; + volatile bool mReachedEOS; + pthread_t mThread; + int64_t mEstimatedSizeBytes; + int64_t mEstimatedDurationUs; + + static void *ThreadWrapper(void *); + status_t threadFunc(); + bool exceedsFileSizeLimit(); + bool exceedsFileDurationLimit(); + + WAVEWriter(const WAVEWriter &); + WAVEWriter &operator=(const WAVEWriter &); +}; + +} // namespace android + +#endif // WAVE_WRITER_H_ -- cgit v1.1