199e53b86eebb605b70dd7591b89bf61a9414ed0eGlenn Kasten/*
289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project**
389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** Copyright 2006, The Android Open Source Project
489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project**
589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** Licensed under the Apache License, Version 2.0 (the "License");
689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** you may not use this file except in compliance with the License.
789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** You may obtain a copy of the License at
889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project**
989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project**     http://www.apache.org/licenses/LICENSE-2.0
1089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project**
1189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** Unless required by applicable law or agreed to in writing, software
1289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** distributed under the License is distributed on an "AS IS" BASIS,
1389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** See the License for the specific language governing permissions and
1589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** limitations under the License.
1689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project*/
1789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
1889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project//#define LOG_NDEBUG 0
1989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project#define LOG_TAG "MediaPlayer"
2089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
2134fb29696b0f3abf61b10f8d053b1f33d501de0aMark Salyzyn#include <fcntl.h>
2234fb29696b0f3abf61b10f8d053b1f33d501de0aMark Salyzyn#include <inttypes.h>
2389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project#include <sys/stat.h>
2434fb29696b0f3abf61b10f8d053b1f33d501de0aMark Salyzyn#include <sys/types.h>
2589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project#include <unistd.h>
2634fb29696b0f3abf61b10f8d053b1f33d501de0aMark Salyzyn
2734fb29696b0f3abf61b10f8d053b1f33d501de0aMark Salyzyn#include <utils/Log.h>
2889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
297562408b2261d38415453378b6188f74fda99d88Mathias Agopian#include <binder/IServiceManager.h>
307562408b2261d38415453378b6188f74fda99d88Mathias Agopian#include <binder/IPCThreadState.h>
3189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
32b1e7cd156ca3e1747374e0d20cdd1ce467210453Mathias Agopian#include <gui/Surface.h>
3361c7ef5bde2c7ed94a078396aa65da67b47e5402Jamie Gennis
3489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project#include <media/mediaplayer.h>
353a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar#include <media/AudioResamplerPublic.h>
36a3f1fa308728976fc9ca1b4f37d26e633b32b9acGlenn Kasten#include <media/AudioSystem.h>
373a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar#include <media/AVSyncSettings.h>
3899f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins#include <media/IDataSource.h>
3989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
407562408b2261d38415453378b6188f74fda99d88Mathias Agopian#include <binder/MemoryBase.h>
4189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
422db8455d8f4468a637109d31f319ce02d9d743ecAndreas Huber#include <utils/KeyedVector.h>
432db8455d8f4468a637109d31f319ce02d9d743ecAndreas Huber#include <utils/String8.h>
442db8455d8f4468a637109d31f319ce02d9d743ecAndreas Huber
4564760240f931714858a59c1579f07264d7182ba2Dima Zavin#include <system/audio.h>
4661c7ef5bde2c7ed94a078396aa65da67b47e5402Jamie Gennis#include <system/window.h>
47fce7a473248381cc83a01855f92581077d3c9ee2Dima Zavin
4889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectnamespace android {
4989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
5089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source ProjectMediaPlayer::MediaPlayer()
5189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
523856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("constructor");
5389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mListener = NULL;
5489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mCookie = NULL;
55fce7a473248381cc83a01855f92581077d3c9ee2Dima Zavin    mStreamType = AUDIO_STREAM_MUSIC;
56640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi    mAudioAttributesParcel = NULL;
5789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mCurrentPosition = -1;
5889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mSeekPosition = -1;
5989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mCurrentState = MEDIA_PLAYER_IDLE;
6089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mPrepareSync = false;
6189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mPrepareStatus = NO_ERROR;
6289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mLoop = false;
6389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mLeftVolume = mRightVolume = 1.0;
6489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mVideoWidth = mVideoHeight = 0;
651af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams    mLockThreadId = 0;
66d848eb48c121c119e8ba7583efc75415fe102570Glenn Kasten    mAudioSessionId = (audio_session_t) AudioSystem::newAudioUniqueId(AUDIO_UNIQUE_ID_USE_SESSION);
67d457c970c8d08519cd77280a90b61ae1e342cfe3Marco Nelissen    AudioSystem::acquireAudioSessionId(mAudioSessionId, -1);
688c563ed9ca8a863a66965330b5d14bb4b4ab59d4Eric Laurent    mSendLevel = 0;
69c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    mRetransmitEndpointValid = false;
7089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
7189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
7289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source ProjectMediaPlayer::~MediaPlayer()
7389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
743856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("destructor");
75640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi    if (mAudioAttributesParcel != NULL) {
76640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi        delete mAudioAttributesParcel;
77640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi        mAudioAttributesParcel = NULL;
78640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi    }
79d457c970c8d08519cd77280a90b61ae1e342cfe3Marco Nelissen    AudioSystem::releaseAudioSessionId(mAudioSessionId, -1);
8089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    disconnect();
8189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    IPCThreadState::self()->flushCommands();
8289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
8389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
8489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectvoid MediaPlayer::disconnect()
8589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
863856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("disconnect");
8789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    sp<IMediaPlayer> p;
8889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    {
8989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        Mutex::Autolock _l(mLock);
9089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        p = mPlayer;
9189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mPlayer.clear();
9289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
9389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
9489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (p != 0) {
9589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        p->disconnect();
9689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
9789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
9889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
9989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project// always call with lock held
10089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectvoid MediaPlayer::clear_l()
10189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
10289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mCurrentPosition = -1;
10389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mSeekPosition = -1;
10489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mVideoWidth = mVideoHeight = 0;
105c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    mRetransmitEndpointValid = false;
10689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
10789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
10889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::setListener(const sp<MediaPlayerListener>& listener)
10989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
1103856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("setListener");
11189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
11289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mListener = listener;
11389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return NO_ERROR;
11489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
11589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
11689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
117d681bbb1767bed09415e050ba78975df214bcd68Dave Burkestatus_t MediaPlayer::attachNewPlayer(const sp<IMediaPlayer>& player)
11889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
11989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    status_t err = UNKNOWN_ERROR;
12089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    sp<IMediaPlayer> p;
12189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    { // scope for the lock
12289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        Mutex::Autolock _l(mLock);
12389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
12483ff1438d2d1d5dbf39ca5e6f2e4fa1799e7ba80Marco Nelissen        if ( !( (mCurrentState & MEDIA_PLAYER_IDLE) ||
12583ff1438d2d1d5dbf39ca5e6f2e4fa1799e7ba80Marco Nelissen                (mCurrentState == MEDIA_PLAYER_STATE_ERROR ) ) ) {
12629357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block            ALOGE("attachNewPlayer called in state %d", mCurrentState);
12789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            return INVALID_OPERATION;
12889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
12989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
13089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        clear_l();
13189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        p = mPlayer;
13289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mPlayer = player;
13389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (player != 0) {
13489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentState = MEDIA_PLAYER_INITIALIZED;
13589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            err = NO_ERROR;
13689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        } else {
137f65fa170b28f97503df3c309ecdaab377a042ba6Masaki Muranaka            ALOGE("Unable to create media player");
13889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
13989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
14089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
14189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (p != 0) {
14289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        p->disconnect();
14389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
14489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
14589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return err;
14689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
14789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
1482db8455d8f4468a637109d31f319ce02d9d743ecAndreas Huberstatus_t MediaPlayer::setDataSource(
1491b86fe063badb5f28c467ade39be0f4008688947Andreas Huber        const sp<IMediaHTTPService> &httpService,
1502db8455d8f4468a637109d31f319ce02d9d743ecAndreas Huber        const char *url, const KeyedVector<String8, String8> *headers)
15189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
1523856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("setDataSource(%s)", url);
15389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    status_t err = BAD_VALUE;
15489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (url != NULL) {
155fc908d010b32bbb850a6306893ce7db166a932f6Marco Nelissen        const sp<IMediaPlayerService> service(getMediaPlayerService());
15689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (service != 0) {
157f37971f624164c3ed185d3f976404a6f60f49b9aGlenn Kasten            sp<IMediaPlayer> player(service->create(this, mAudioSessionId));
158c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman            if ((NO_ERROR != doSetRetransmitEndpoint(player)) ||
1591b86fe063badb5f28c467ade39be0f4008688947Andreas Huber                (NO_ERROR != player->setDataSource(httpService, url, headers))) {
1600662067b06658a4a56a8416c676f6cce8ccddb53Dave Burke                player.clear();
161d681bbb1767bed09415e050ba78975df214bcd68Dave Burke            }
1620662067b06658a4a56a8416c676f6cce8ccddb53Dave Burke            err = attachNewPlayer(player);
16389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
16489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
16589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return err;
16689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
16789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
16889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::setDataSource(int fd, int64_t offset, int64_t length)
16989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
17034fb29696b0f3abf61b10f8d053b1f33d501de0aMark Salyzyn    ALOGV("setDataSource(%d, %" PRId64 ", %" PRId64 ")", fd, offset, length);
17189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    status_t err = UNKNOWN_ERROR;
172fc908d010b32bbb850a6306893ce7db166a932f6Marco Nelissen    const sp<IMediaPlayerService> service(getMediaPlayerService());
17389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (service != 0) {
174f37971f624164c3ed185d3f976404a6f60f49b9aGlenn Kasten        sp<IMediaPlayer> player(service->create(this, mAudioSessionId));
175c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman        if ((NO_ERROR != doSetRetransmitEndpoint(player)) ||
176c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman            (NO_ERROR != player->setDataSource(fd, offset, length))) {
1770662067b06658a4a56a8416c676f6cce8ccddb53Dave Burke            player.clear();
178d681bbb1767bed09415e050ba78975df214bcd68Dave Burke        }
1790662067b06658a4a56a8416c676f6cce8ccddb53Dave Burke        err = attachNewPlayer(player);
180d681bbb1767bed09415e050ba78975df214bcd68Dave Burke    }
181d681bbb1767bed09415e050ba78975df214bcd68Dave Burke    return err;
182d681bbb1767bed09415e050ba78975df214bcd68Dave Burke}
183d681bbb1767bed09415e050ba78975df214bcd68Dave Burke
18499f31604136d66ae10e20669fb6b5716f342bde0Chris Watkinsstatus_t MediaPlayer::setDataSource(const sp<IDataSource> &source)
18599f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins{
18699f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins    ALOGV("setDataSource(IDataSource)");
18799f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins    status_t err = UNKNOWN_ERROR;
188fc908d010b32bbb850a6306893ce7db166a932f6Marco Nelissen    const sp<IMediaPlayerService> service(getMediaPlayerService());
18999f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins    if (service != 0) {
19099f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins        sp<IMediaPlayer> player(service->create(this, mAudioSessionId));
19199f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins        if ((NO_ERROR != doSetRetransmitEndpoint(player)) ||
19299f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins            (NO_ERROR != player->setDataSource(source))) {
19399f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins            player.clear();
19499f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins        }
19599f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins        err = attachNewPlayer(player);
19699f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins    }
19799f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins    return err;
19899f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins}
19999f31604136d66ae10e20669fb6b5716f342bde0Chris Watkins
2001d187f1a86855f5f0694d7ec30efc9833bf7c589Nicolas Cataniastatus_t MediaPlayer::invoke(const Parcel& request, Parcel *reply)
2011d187f1a86855f5f0694d7ec30efc9833bf7c589Nicolas Catania{
2021d187f1a86855f5f0694d7ec30efc9833bf7c589Nicolas Catania    Mutex::Autolock _l(mLock);
2034023493a827bc9751d8e40795516d0d536a53348Nicolas Catania    const bool hasBeenInitialized =
2044023493a827bc9751d8e40795516d0d536a53348Nicolas Catania            (mCurrentState != MEDIA_PLAYER_STATE_ERROR) &&
2054023493a827bc9751d8e40795516d0d536a53348Nicolas Catania            ((mCurrentState & MEDIA_PLAYER_IDLE) != MEDIA_PLAYER_IDLE);
2064023493a827bc9751d8e40795516d0d536a53348Nicolas Catania    if ((mPlayer != NULL) && hasBeenInitialized) {
20734fb29696b0f3abf61b10f8d053b1f33d501de0aMark Salyzyn        ALOGV("invoke %zu", request.dataSize());
208e53b9ead781c36e96d6b6f012ddffc93a3d80f0dGlenn Kasten        return  mPlayer->invoke(request, reply);
2091d187f1a86855f5f0694d7ec30efc9833bf7c589Nicolas Catania    }
210848ebc644a1a7ef93a051186fb5f0aef826ad67eWei Jia    ALOGE("invoke failed: wrong state %X, mPlayer(%p)", mCurrentState, mPlayer.get());
2111d187f1a86855f5f0694d7ec30efc9833bf7c589Nicolas Catania    return INVALID_OPERATION;
2121d187f1a86855f5f0694d7ec30efc9833bf7c589Nicolas Catania}
2131d187f1a86855f5f0694d7ec30efc9833bf7c589Nicolas Catania
214a7e0e8b4c429fc68eb1bd5b5a30f5b91352288f9Nicolas Cataniastatus_t MediaPlayer::setMetadataFilter(const Parcel& filter)
215a7e0e8b4c429fc68eb1bd5b5a30f5b91352288f9Nicolas Catania{
216b8a805261bf0282e992d3608035e47d05a898710Steve Block    ALOGD("setMetadataFilter");
2178e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Catania    Mutex::Autolock lock(mLock);
2188e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Catania    if (mPlayer == NULL) {
219a7e0e8b4c429fc68eb1bd5b5a30f5b91352288f9Nicolas Catania        return NO_INIT;
220a7e0e8b4c429fc68eb1bd5b5a30f5b91352288f9Nicolas Catania    }
221a7e0e8b4c429fc68eb1bd5b5a30f5b91352288f9Nicolas Catania    return mPlayer->setMetadataFilter(filter);
222a7e0e8b4c429fc68eb1bd5b5a30f5b91352288f9Nicolas Catania}
2231d187f1a86855f5f0694d7ec30efc9833bf7c589Nicolas Catania
2248e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Cataniastatus_t MediaPlayer::getMetadata(bool update_only, bool apply_filter, Parcel *metadata)
2258e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Catania{
226b8a805261bf0282e992d3608035e47d05a898710Steve Block    ALOGD("getMetadata");
2278e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Catania    Mutex::Autolock lock(mLock);
2288e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Catania    if (mPlayer == NULL) {
2298e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Catania        return NO_INIT;
2308e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Catania    }
2318e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Catania    return mPlayer->getMetadata(update_only, apply_filter, metadata);
2328e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Catania}
2338e1b6cce24574b9ecd5b0300155776bd0b4ef756Nicolas Catania
2341173118eace0e9e347cb007f0da817cee87579edGlenn Kastenstatus_t MediaPlayer::setVideoSurfaceTexture(
235484566c410afdfbc4b6bc5aa1732aef37428a5b8Andy McFadden        const sp<IGraphicBufferProducer>& bufferProducer)
2361173118eace0e9e347cb007f0da817cee87579edGlenn Kasten{
2373856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("setVideoSurfaceTexture");
2381173118eace0e9e347cb007f0da817cee87579edGlenn Kasten    Mutex::Autolock _l(mLock);
2391173118eace0e9e347cb007f0da817cee87579edGlenn Kasten    if (mPlayer == 0) return NO_INIT;
240484566c410afdfbc4b6bc5aa1732aef37428a5b8Andy McFadden    return mPlayer->setVideoSurfaceTexture(bufferProducer);
2411173118eace0e9e347cb007f0da817cee87579edGlenn Kasten}
2421173118eace0e9e347cb007f0da817cee87579edGlenn Kasten
24389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project// must call with lock held
24489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::prepareAsync_l()
24589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
246b187de1ada34a9023c05d020a4592686ba761278Glenn Kasten    if ( (mPlayer != 0) && ( mCurrentState & (MEDIA_PLAYER_INITIALIZED | MEDIA_PLAYER_STOPPED) ) ) {
247640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi        if (mAudioAttributesParcel != NULL) {
248640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi            mPlayer->setParameter(KEY_PARAMETER_AUDIO_ATTRIBUTES, *mAudioAttributesParcel);
2494356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent        } else {
2504356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent            mPlayer->setAudioStreamType(mStreamType);
251640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi        }
25289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mCurrentState = MEDIA_PLAYER_PREPARING;
25389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return mPlayer->prepareAsync();
25489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
255848ebc644a1a7ef93a051186fb5f0aef826ad67eWei Jia    ALOGE("prepareAsync called in state %d, mPlayer(%p)", mCurrentState, mPlayer.get());
25689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return INVALID_OPERATION;
25789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
25889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
25965e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project// TODO: In case of error, prepareAsync provides the caller with 2 error codes,
26065e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project// one defined in the Android framework and one provided by the implementation
26165e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project// that generated the error. The sync version of prepare returns only 1 error
26265e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project// code.
26389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::prepare()
26489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
2653856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("prepare");
26689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
2671af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams    mLockThreadId = getThreadId();
2681af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams    if (mPrepareSync) {
2691af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams        mLockThreadId = 0;
2701af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams        return -EALREADY;
2711af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams    }
27289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mPrepareSync = true;
27389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    status_t ret = prepareAsync_l();
2741af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams    if (ret != NO_ERROR) {
2751af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams        mLockThreadId = 0;
2761af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams        return ret;
2771af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams    }
27889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
27989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mPrepareSync) {
28089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mSignal.wait(mLock);  // wait for prepare done
28189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mPrepareSync = false;
28289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
2833856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("prepare complete - status=%d", mPrepareStatus);
2841af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams    mLockThreadId = 0;
28589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return mPrepareStatus;
28689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
28789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
28889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::prepareAsync()
28989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
2903856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("prepareAsync");
29189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
29289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return prepareAsync_l();
29389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
29489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
29589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::start()
29689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
2973856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("start");
298d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang
299d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang    status_t ret = NO_ERROR;
30089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
301d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang
302d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang    mLockThreadId = getThreadId();
303d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang
304d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang    if (mCurrentState & MEDIA_PLAYER_STARTED) {
305d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang        ret = NO_ERROR;
306d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang    } else if ( (mPlayer != 0) && ( mCurrentState & ( MEDIA_PLAYER_PREPARED |
30789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project                    MEDIA_PLAYER_PLAYBACK_COMPLETE | MEDIA_PLAYER_PAUSED ) ) ) {
30889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mPlayer->setLooping(mLoop);
30989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mPlayer->setVolume(mLeftVolume, mRightVolume);
3102beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent        mPlayer->setAuxEffectSendLevel(mSendLevel);
31189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mCurrentState = MEDIA_PLAYER_STARTED;
312d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang        ret = mPlayer->start();
31389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (ret != NO_ERROR) {
31489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentState = MEDIA_PLAYER_STATE_ERROR;
31589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        } else {
31689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            if (mCurrentState == MEDIA_PLAYER_PLAYBACK_COMPLETE) {
3173856b090cd04ba5dd4a59a12430ed724d5995909Steve Block                ALOGV("playback completed immediately following start()");
31889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            }
31989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
320d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang    } else {
321848ebc644a1a7ef93a051186fb5f0aef826ad67eWei Jia        ALOGE("start called in state %d, mPlayer(%p)", mCurrentState, mPlayer.get());
322d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang        ret = INVALID_OPERATION;
32389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
324d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang
325d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang    mLockThreadId = 0;
326d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang
327d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang    return ret;
32889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
32989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
33089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::stop()
33189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
3323856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("stop");
33389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
33489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mCurrentState & MEDIA_PLAYER_STOPPED) return NO_ERROR;
33589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if ( (mPlayer != 0) && ( mCurrentState & ( MEDIA_PLAYER_STARTED | MEDIA_PLAYER_PREPARED |
33689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project                    MEDIA_PLAYER_PAUSED | MEDIA_PLAYER_PLAYBACK_COMPLETE ) ) ) {
33789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        status_t ret = mPlayer->stop();
33889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (ret != NO_ERROR) {
33989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentState = MEDIA_PLAYER_STATE_ERROR;
34089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        } else {
34189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentState = MEDIA_PLAYER_STOPPED;
34289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
34389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return ret;
34489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
345848ebc644a1a7ef93a051186fb5f0aef826ad67eWei Jia    ALOGE("stop called in state %d, mPlayer(%p)", mCurrentState, mPlayer.get());
34689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return INVALID_OPERATION;
34789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
34889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
34989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::pause()
35089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
3513856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("pause");
35289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
353698f476590bc9e38d4d1d4155da9efdbedd357c4Marco Nelissen    if (mCurrentState & (MEDIA_PLAYER_PAUSED|MEDIA_PLAYER_PLAYBACK_COMPLETE))
35489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return NO_ERROR;
35589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if ((mPlayer != 0) && (mCurrentState & MEDIA_PLAYER_STARTED)) {
35689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        status_t ret = mPlayer->pause();
35789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (ret != NO_ERROR) {
35889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentState = MEDIA_PLAYER_STATE_ERROR;
35989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        } else {
36089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentState = MEDIA_PLAYER_PAUSED;
36189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
36289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return ret;
36389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
364848ebc644a1a7ef93a051186fb5f0aef826ad67eWei Jia    ALOGE("pause called in state %d, mPlayer(%p)", mCurrentState, mPlayer.get());
36589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return INVALID_OPERATION;
36689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
36789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
36889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectbool MediaPlayer::isPlaying()
36989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
37089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
37189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mPlayer != 0) {
37289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        bool temp = false;
37389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mPlayer->isPlaying(&temp);
3743856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("isPlaying: %d", temp);
37589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if ((mCurrentState & MEDIA_PLAYER_STARTED) && ! temp) {
37629357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block            ALOGE("internal/external state mismatch corrected");
37789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentState = MEDIA_PLAYER_PAUSED;
3783a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar        } else if ((mCurrentState & MEDIA_PLAYER_PAUSED) && temp) {
3793a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar            ALOGE("internal/external state mismatch corrected");
3803a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar            mCurrentState = MEDIA_PLAYER_STARTED;
38189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
38289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return temp;
38389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
3843856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("isPlaying: no active player");
38589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return false;
38689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
38789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
3883a474aa67fc31505740526dd249d96204c08bf79Lajos Molnarstatus_t MediaPlayer::setPlaybackSettings(const AudioPlaybackRate& rate)
3899816016afb2a13c6a866cd047d57020566a8b9a9Wei Jia{
3903a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    ALOGV("setPlaybackSettings: %f %f %d %d",
3913a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar            rate.mSpeed, rate.mPitch, rate.mFallbackMode, rate.mStretchMode);
3923a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    // Negative speed and pitch does not make sense. Further validation will
3933a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    // be done by the respective mediaplayers.
3943a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    if (rate.mSpeed < 0.f || rate.mPitch < 0.f) {
3959816016afb2a13c6a866cd047d57020566a8b9a9Wei Jia        return BAD_VALUE;
3969816016afb2a13c6a866cd047d57020566a8b9a9Wei Jia    }
3979816016afb2a13c6a866cd047d57020566a8b9a9Wei Jia    Mutex::Autolock _l(mLock);
3983a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    if (mPlayer == 0) return INVALID_OPERATION;
3995be109faadfc08b561221bd801082873b614b93dWei Jia
4005be109faadfc08b561221bd801082873b614b93dWei Jia    if (rate.mSpeed != 0.f && !(mCurrentState & MEDIA_PLAYER_STARTED)
4015be109faadfc08b561221bd801082873b614b93dWei Jia            && (mCurrentState & (MEDIA_PLAYER_PREPARED | MEDIA_PLAYER_PAUSED
4025be109faadfc08b561221bd801082873b614b93dWei Jia                    | MEDIA_PLAYER_PLAYBACK_COMPLETE))) {
4035be109faadfc08b561221bd801082873b614b93dWei Jia        mPlayer->setLooping(mLoop);
4045be109faadfc08b561221bd801082873b614b93dWei Jia        mPlayer->setVolume(mLeftVolume, mRightVolume);
4055be109faadfc08b561221bd801082873b614b93dWei Jia        mPlayer->setAuxEffectSendLevel(mSendLevel);
4065be109faadfc08b561221bd801082873b614b93dWei Jia    }
4075be109faadfc08b561221bd801082873b614b93dWei Jia
4083a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    status_t err = mPlayer->setPlaybackSettings(rate);
4093a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    if (err == OK) {
4103a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar        if (rate.mSpeed == 0.f && mCurrentState == MEDIA_PLAYER_STARTED) {
4113a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar            mCurrentState = MEDIA_PLAYER_PAUSED;
4125be109faadfc08b561221bd801082873b614b93dWei Jia        } else if (rate.mSpeed != 0.f
4135be109faadfc08b561221bd801082873b614b93dWei Jia                && (mCurrentState & (MEDIA_PLAYER_PREPARED | MEDIA_PLAYER_PAUSED
4145be109faadfc08b561221bd801082873b614b93dWei Jia                    | MEDIA_PLAYER_PLAYBACK_COMPLETE))) {
4153a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar            mCurrentState = MEDIA_PLAYER_STARTED;
4169816016afb2a13c6a866cd047d57020566a8b9a9Wei Jia        }
4179816016afb2a13c6a866cd047d57020566a8b9a9Wei Jia    }
4183a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    return err;
4193a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar}
4203a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar
4213a474aa67fc31505740526dd249d96204c08bf79Lajos Molnarstatus_t MediaPlayer::getPlaybackSettings(AudioPlaybackRate* rate /* nonnull */)
4223a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar{
4233a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    Mutex::Autolock _l(mLock);
4243a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    if (mPlayer == 0) return INVALID_OPERATION;
4253a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    return mPlayer->getPlaybackSettings(rate);
4263a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar}
4273a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar
4283a474aa67fc31505740526dd249d96204c08bf79Lajos Molnarstatus_t MediaPlayer::setSyncSettings(const AVSyncSettings& sync, float videoFpsHint)
4293a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar{
4303a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    ALOGV("setSyncSettings: %u %u %f %f",
4313a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar            sync.mSource, sync.mAudioAdjustMode, sync.mTolerance, videoFpsHint);
4323a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    Mutex::Autolock _l(mLock);
4333a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    if (mPlayer == 0) return INVALID_OPERATION;
4343a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    return mPlayer->setSyncSettings(sync, videoFpsHint);
4353a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar}
4363a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar
4373a474aa67fc31505740526dd249d96204c08bf79Lajos Molnarstatus_t MediaPlayer::getSyncSettings(
4383a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar        AVSyncSettings* sync /* nonnull */, float* videoFps /* nonnull */)
4393a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar{
4403a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    Mutex::Autolock _l(mLock);
4413a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    if (mPlayer == 0) return INVALID_OPERATION;
4423a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar    return mPlayer->getSyncSettings(sync, videoFps);
4439816016afb2a13c6a866cd047d57020566a8b9a9Wei Jia}
4449816016afb2a13c6a866cd047d57020566a8b9a9Wei Jia
44589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::getVideoWidth(int *w)
44689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
4473856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("getVideoWidth");
44889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
44989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mPlayer == 0) return INVALID_OPERATION;
45089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    *w = mVideoWidth;
45189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return NO_ERROR;
45289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
45389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
45489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::getVideoHeight(int *h)
45589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
4563856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("getVideoHeight");
45789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
45889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mPlayer == 0) return INVALID_OPERATION;
45989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    *h = mVideoHeight;
46089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return NO_ERROR;
46189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
46289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
46389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::getCurrentPosition(int *msec)
46489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
4653856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("getCurrentPosition");
46689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
46789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mPlayer != 0) {
46889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (mCurrentPosition >= 0) {
4693856b090cd04ba5dd4a59a12430ed724d5995909Steve Block            ALOGV("Using cached seek position: %d", mCurrentPosition);
47089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            *msec = mCurrentPosition;
47189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            return NO_ERROR;
47289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
47389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return mPlayer->getCurrentPosition(msec);
47489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
47589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return INVALID_OPERATION;
47689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
47789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
47889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::getDuration_l(int *msec)
47989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
480a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber    ALOGV("getDuration_l");
481b187de1ada34a9023c05d020a4592686ba761278Glenn Kasten    bool isValidState = (mCurrentState & (MEDIA_PLAYER_PREPARED | MEDIA_PLAYER_STARTED |
482b187de1ada34a9023c05d020a4592686ba761278Glenn Kasten            MEDIA_PLAYER_PAUSED | MEDIA_PLAYER_STOPPED | MEDIA_PLAYER_PLAYBACK_COMPLETE));
48389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mPlayer != 0 && isValidState) {
484a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber        int durationMs;
485a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber        status_t ret = mPlayer->getDuration(&durationMs);
4862070254f241f52cadb69bc2323f56df72704f1caAndreas Huber
4872070254f241f52cadb69bc2323f56df72704f1caAndreas Huber        if (ret != OK) {
4882070254f241f52cadb69bc2323f56df72704f1caAndreas Huber            // Do not enter error state just because no duration was available.
4892070254f241f52cadb69bc2323f56df72704f1caAndreas Huber            durationMs = -1;
4902070254f241f52cadb69bc2323f56df72704f1caAndreas Huber            ret = OK;
4912070254f241f52cadb69bc2323f56df72704f1caAndreas Huber        }
4922070254f241f52cadb69bc2323f56df72704f1caAndreas Huber
493a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber        if (msec) {
494a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber            *msec = durationMs;
495a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber        }
49689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return ret;
49789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
498848ebc644a1a7ef93a051186fb5f0aef826ad67eWei Jia    ALOGE("Attempt to call getDuration in wrong state: mPlayer=%p, mCurrentState=%u",
499848ebc644a1a7ef93a051186fb5f0aef826ad67eWei Jia            mPlayer.get(), mCurrentState);
50089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return INVALID_OPERATION;
50189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
50289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
50389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::getDuration(int *msec)
50489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
50589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
50689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return getDuration_l(msec);
50789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
50889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
50989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::seekTo_l(int msec)
51089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
5113856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("seekTo %d", msec);
512b187de1ada34a9023c05d020a4592686ba761278Glenn Kasten    if ((mPlayer != 0) && ( mCurrentState & ( MEDIA_PLAYER_STARTED | MEDIA_PLAYER_PREPARED |
513b187de1ada34a9023c05d020a4592686ba761278Glenn Kasten            MEDIA_PLAYER_PAUSED |  MEDIA_PLAYER_PLAYBACK_COMPLETE) ) ) {
51489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if ( msec < 0 ) {
5155ff1dd576bb93c45b44088a51544a18fc43ebf58Steve Block            ALOGW("Attempt to seek to invalid position: %d", msec);
51689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            msec = 0;
51789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
518a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber
519a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber        int durationMs;
520a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber        status_t err = mPlayer->getDuration(&durationMs);
521a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber
522a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber        if (err != OK) {
523a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber            ALOGW("Stream has no duration and is therefore not seekable.");
524a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber            return err;
525a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber        }
526a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber
527a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber        if (msec > durationMs) {
528a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber            ALOGW("Attempt to seek to past end of file: request = %d, "
529a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber                  "durationMs = %d",
530a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber                  msec,
531a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber                  durationMs);
532a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber
533a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber            msec = durationMs;
534a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber        }
535a4c5bc0f18fe272146426ab2eccad6215279c9f3Andreas Huber
53689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        // cache duration
53789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mCurrentPosition = msec;
53889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (mSeekPosition < 0) {
53989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mSeekPosition = msec;
54089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            return mPlayer->seekTo(msec);
54189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
54289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        else {
5433856b090cd04ba5dd4a59a12430ed724d5995909Steve Block            ALOGV("Seek in progress - queue up seekTo[%d]", msec);
54489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            return NO_ERROR;
54589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
54689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
547b187de1ada34a9023c05d020a4592686ba761278Glenn Kasten    ALOGE("Attempt to perform seekTo in wrong state: mPlayer=%p, mCurrentState=%u", mPlayer.get(),
548b187de1ada34a9023c05d020a4592686ba761278Glenn Kasten            mCurrentState);
54989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return INVALID_OPERATION;
55089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
55189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
55289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::seekTo(int msec)
55389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
5545cb07aa071b43a214e4c880b3b7852714e06451bAndreas Huber    mLockThreadId = getThreadId();
55589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
5565cb07aa071b43a214e4c880b3b7852714e06451bAndreas Huber    status_t result = seekTo_l(msec);
5575cb07aa071b43a214e4c880b3b7852714e06451bAndreas Huber    mLockThreadId = 0;
5585cb07aa071b43a214e4c880b3b7852714e06451bAndreas Huber
5595cb07aa071b43a214e4c880b3b7852714e06451bAndreas Huber    return result;
56089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
56189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
56261c7ef5bde2c7ed94a078396aa65da67b47e5402Jamie Gennisstatus_t MediaPlayer::reset_l()
56389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
56489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mLoop = false;
56589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mCurrentState == MEDIA_PLAYER_IDLE) return NO_ERROR;
56689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mPrepareSync = false;
56789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mPlayer != 0) {
56889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        status_t ret = mPlayer->reset();
56989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (ret != NO_ERROR) {
57029357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block            ALOGE("reset() failed with return code (%d)", ret);
57189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentState = MEDIA_PLAYER_STATE_ERROR;
57289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        } else {
5732b95bda111444f2834e64221e3a3eb1a87d43c38Robert Shih            mPlayer->disconnect();
57489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentState = MEDIA_PLAYER_IDLE;
57589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
576a1680bce73ea1b051cc92e0df651a53944b104eeJames Dong        // setDataSource has to be called again to create a
577a1680bce73ea1b051cc92e0df651a53944b104eeJames Dong        // new mediaplayer.
578a1680bce73ea1b051cc92e0df651a53944b104eeJames Dong        mPlayer = 0;
57989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return ret;
58089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
58189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    clear_l();
58289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return NO_ERROR;
58389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
58489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
585c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossmanstatus_t MediaPlayer::doSetRetransmitEndpoint(const sp<IMediaPlayer>& player) {
586c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    Mutex::Autolock _l(mLock);
587c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman
588c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    if (player == NULL) {
589c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman        return UNKNOWN_ERROR;
590c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    }
591c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman
592c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    if (mRetransmitEndpointValid) {
593c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman        return player->setRetransmitEndpoint(&mRetransmitEndpoint);
594c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    }
595c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman
596c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    return OK;
597c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman}
598c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman
59961c7ef5bde2c7ed94a078396aa65da67b47e5402Jamie Gennisstatus_t MediaPlayer::reset()
60061c7ef5bde2c7ed94a078396aa65da67b47e5402Jamie Gennis{
6013856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("reset");
60261c7ef5bde2c7ed94a078396aa65da67b47e5402Jamie Gennis    Mutex::Autolock _l(mLock);
60361c7ef5bde2c7ed94a078396aa65da67b47e5402Jamie Gennis    return reset_l();
60461c7ef5bde2c7ed94a078396aa65da67b47e5402Jamie Gennis}
60561c7ef5bde2c7ed94a078396aa65da67b47e5402Jamie Gennis
606fff6d715a8db0daf08a50634f242c40268de3d49Glenn Kastenstatus_t MediaPlayer::setAudioStreamType(audio_stream_type_t type)
60789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
6083856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("MediaPlayer::setAudioStreamType");
60989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
61089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mStreamType == type) return NO_ERROR;
61189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mCurrentState & ( MEDIA_PLAYER_PREPARED | MEDIA_PLAYER_STARTED |
61289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project                MEDIA_PLAYER_PAUSED | MEDIA_PLAYER_PLAYBACK_COMPLETE ) ) {
61389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        // Can't change the stream type after prepare
61429357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block        ALOGE("setAudioStream called in state %d", mCurrentState);
61589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return INVALID_OPERATION;
61689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
61789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    // cache
61889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mStreamType = type;
61989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return OK;
62089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
62189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
622de9453fb5cbc9cd69fd1ea45d577851e3aa3b8c9John Spurlockstatus_t MediaPlayer::getAudioStreamType(audio_stream_type_t *type)
623de9453fb5cbc9cd69fd1ea45d577851e3aa3b8c9John Spurlock{
624de9453fb5cbc9cd69fd1ea45d577851e3aa3b8c9John Spurlock    ALOGV("getAudioStreamType");
625de9453fb5cbc9cd69fd1ea45d577851e3aa3b8c9John Spurlock    Mutex::Autolock _l(mLock);
626de9453fb5cbc9cd69fd1ea45d577851e3aa3b8c9John Spurlock    *type = mStreamType;
627de9453fb5cbc9cd69fd1ea45d577851e3aa3b8c9John Spurlock    return OK;
628de9453fb5cbc9cd69fd1ea45d577851e3aa3b8c9John Spurlock}
629de9453fb5cbc9cd69fd1ea45d577851e3aa3b8c9John Spurlock
63089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::setLooping(int loop)
63189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
6323856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("MediaPlayer::setLooping");
63389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
63489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mLoop = (loop != 0);
63589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mPlayer != 0) {
63689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return mPlayer->setLooping(loop);
63789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
63889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return OK;
63989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
64089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
64189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectbool MediaPlayer::isLooping() {
6423856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("isLooping");
64389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
64489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mPlayer != 0) {
64589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return mLoop;
64689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
6473856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("isLooping: no active player");
64889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return false;
64989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
65089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
65189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaPlayer::setVolume(float leftVolume, float rightVolume)
65289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
6533856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("MediaPlayer::setVolume(%f, %f)", leftVolume, rightVolume);
65489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    Mutex::Autolock _l(mLock);
65589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mLeftVolume = leftVolume;
65689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    mRightVolume = rightVolume;
65789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if (mPlayer != 0) {
65889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return mPlayer->setVolume(leftVolume, rightVolume);
65989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
66089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    return OK;
66189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
66289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
663d848eb48c121c119e8ba7583efc75415fe102570Glenn Kastenstatus_t MediaPlayer::setAudioSessionId(audio_session_t sessionId)
664a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent{
6653856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("MediaPlayer::setAudioSessionId(%d)", sessionId);
666a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent    Mutex::Autolock _l(mLock);
667a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent    if (!(mCurrentState & MEDIA_PLAYER_IDLE)) {
66829357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block        ALOGE("setAudioSessionId called in state %d", mCurrentState);
669a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent        return INVALID_OPERATION;
670a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent    }
671a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent    if (sessionId < 0) {
672a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent        return BAD_VALUE;
673a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent    }
6743a34befc6fb04a4945a849e8bda8b84e4bf973feMarco Nelissen    if (sessionId != mAudioSessionId) {
675d457c970c8d08519cd77280a90b61ae1e342cfe3Marco Nelissen        AudioSystem::acquireAudioSessionId(sessionId, -1);
676d457c970c8d08519cd77280a90b61ae1e342cfe3Marco Nelissen        AudioSystem::releaseAudioSessionId(mAudioSessionId, -1);
677e53b9ead781c36e96d6b6f012ddffc93a3d80f0dGlenn Kasten        mAudioSessionId = sessionId;
6783a34befc6fb04a4945a849e8bda8b84e4bf973feMarco Nelissen    }
679a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent    return NO_ERROR;
680a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent}
681a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent
682d848eb48c121c119e8ba7583efc75415fe102570Glenn Kastenaudio_session_t MediaPlayer::getAudioSessionId()
683a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent{
684a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent    Mutex::Autolock _l(mLock);
685a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent    return mAudioSessionId;
686a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent}
687a514bdb58b5de4986679f72b7204b4764f7a2778Eric Laurent
6882beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurentstatus_t MediaPlayer::setAuxEffectSendLevel(float level)
6892beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent{
6903856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("MediaPlayer::setAuxEffectSendLevel(%f)", level);
6912beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent    Mutex::Autolock _l(mLock);
6922beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent    mSendLevel = level;
6932beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent    if (mPlayer != 0) {
6942beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent        return mPlayer->setAuxEffectSendLevel(level);
6952beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent    }
6962beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent    return OK;
6972beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent}
6982beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent
6992beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurentstatus_t MediaPlayer::attachAuxEffect(int effectId)
7002beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent{
7013856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("MediaPlayer::attachAuxEffect(%d)", effectId);
7022beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent    Mutex::Autolock _l(mLock);
7032beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent    if (mPlayer == 0 ||
7042beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent        (mCurrentState & MEDIA_PLAYER_IDLE) ||
7052beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent        (mCurrentState == MEDIA_PLAYER_STATE_ERROR )) {
706848ebc644a1a7ef93a051186fb5f0aef826ad67eWei Jia        ALOGE("attachAuxEffect called in state %d, mPlayer(%p)", mCurrentState, mPlayer.get());
7072beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent        return INVALID_OPERATION;
7082beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent    }
7092beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent
7102beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent    return mPlayer->attachAuxEffect(effectId);
7112beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent}
7122beeb50b1bba9e92f6cacfeca37fe9fa9d36ead1Eric Laurent
713d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi// always call with lock held
714d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivistatus_t MediaPlayer::checkStateForKeySet_l(int key)
715d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi{
716d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi    switch(key) {
717d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi    case KEY_PARAMETER_AUDIO_ATTRIBUTES:
718d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi        if (mCurrentState & ( MEDIA_PLAYER_PREPARED | MEDIA_PLAYER_STARTED |
719d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi                MEDIA_PLAYER_PAUSED | MEDIA_PLAYER_PLAYBACK_COMPLETE) ) {
720d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi            // Can't change the audio attributes after prepare
721d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi            ALOGE("trying to set audio attributes called in state %d", mCurrentState);
722d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi            return INVALID_OPERATION;
723d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi        }
724d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi        break;
725d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi    default:
726d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi        // parameter doesn't require player state check
727d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi        break;
728d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi    }
729d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi    return OK;
730d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi}
731d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi
7324f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wangstatus_t MediaPlayer::setParameter(int key, const Parcel& request)
7334f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang{
7343856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("MediaPlayer::setParameter(%d)", key);
7354356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent    status_t status = INVALID_OPERATION;
7364f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang    Mutex::Autolock _l(mLock);
737d9d7fa0873796ac661c44a7fcd6ad5ff697ff01fJean-Michel Trivi    if (checkStateForKeySet_l(key) != OK) {
7384356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent        return status;
7394f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang    }
740640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi    switch (key) {
741640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi    case KEY_PARAMETER_AUDIO_ATTRIBUTES:
7424356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent        // save the marshalled audio attributes
743640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi        if (mAudioAttributesParcel != NULL) { delete mAudioAttributesParcel; };
744640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi        mAudioAttributesParcel = new Parcel();
745640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi        mAudioAttributesParcel->appendFrom(&request, 0, request.dataSize());
7464356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent        status = OK;
7474356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent        break;
748640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi    default:
7494356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent        ALOGV_IF(mPlayer == NULL, "setParameter: no active player");
7504356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent        break;
7514356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent    }
7524356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent
7534356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent    if (mPlayer != NULL) {
7544356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent        status = mPlayer->setParameter(key, request);
755640adb3cf89cc9b826372009fad8c9b3d120482eJean-Michel Trivi    }
7564356269be6d2b62bbb945364e8fc4beb99e1aadaEric Laurent    return status;
7574f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang}
7584f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang
7594f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wangstatus_t MediaPlayer::getParameter(int key, Parcel *reply)
7604f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang{
7613856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("MediaPlayer::getParameter(%d)", key);
7624f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang    Mutex::Autolock _l(mLock);
7634f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang    if (mPlayer != NULL) {
764e53b9ead781c36e96d6b6f012ddffc93a3d80f0dGlenn Kasten        return  mPlayer->getParameter(key, reply);
7654f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang    }
7663856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("getParameter: no active player");
7674f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang    return INVALID_OPERATION;
7684f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang}
7694f9e47f2c03ce36261c4717cd7e131d7940bb068Gloria Wang
770c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossmanstatus_t MediaPlayer::setRetransmitEndpoint(const char* addrString,
771c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman                                            uint16_t port) {
772c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    ALOGV("MediaPlayer::setRetransmitEndpoint(%s:%hu)",
773c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman            addrString ? addrString : "(null)", port);
774c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman
775c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    Mutex::Autolock _l(mLock);
776c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    if ((mPlayer != NULL) || (mCurrentState != MEDIA_PLAYER_IDLE))
777c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman        return INVALID_OPERATION;
778c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman
779c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    if (NULL == addrString) {
780c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman        mRetransmitEndpointValid = false;
781c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman        return OK;
782c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    }
783c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman
784c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    struct in_addr saddr;
785c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    if(!inet_aton(addrString, &saddr)) {
786c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman        return BAD_VALUE;
787c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    }
788c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman
789be08f6a6688f3b1ae6914fbe800953c9bfb13c45Glenn Kasten    memset(&mRetransmitEndpoint, 0, sizeof(mRetransmitEndpoint));
790c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    mRetransmitEndpoint.sin_family = AF_INET;
791c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    mRetransmitEndpoint.sin_addr   = saddr;
792c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    mRetransmitEndpoint.sin_port   = htons(port);
793c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    mRetransmitEndpointValid       = true;
794c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman
795c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman    return OK;
796c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman}
797c795b64060c3af9d7961fc1371e4ccfa8ee3e450John Grossman
798b483c4724846c0b8d4e82afcbb7c17f671bae81cGloria Wangvoid MediaPlayer::notify(int msg, int ext1, int ext2, const Parcel *obj)
79989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{
8003856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("message received msg=%d, ext1=%d, ext2=%d", msg, ext1, ext2);
80189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    bool send = true;
8021af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams    bool locked = false;
80389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
80489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    // TODO: In the future, we might be on the same thread if the app is
80589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    // running in the same process as the media server. In that case,
80689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    // this will deadlock.
807660951867e959ebe98612742ef1f72d33ea7e9a3Nicolas Catania    //
808d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang    // The threadId hack below works around this for the care of prepare,
809d88adb96ec867ed1b629c434f87514d2fabaf5e9Chong Zhang    // seekTo and start within the same process.
8105cb07aa071b43a214e4c880b3b7852714e06451bAndreas Huber    // FIXME: Remember, this is a hack, it's not even a hack that is applied
8115cb07aa071b43a214e4c880b3b7852714e06451bAndreas Huber    // consistently for all use-cases, this needs to be revisited.
812e53b9ead781c36e96d6b6f012ddffc93a3d80f0dGlenn Kasten    if (mLockThreadId != getThreadId()) {
8131af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams        mLock.lock();
8141af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams        locked = true;
815660951867e959ebe98612742ef1f72d33ea7e9a3Nicolas Catania    }
8161af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams
8173b26844e60f8487388e7e62709faf0dada86e7e1Eric Laurent    // Allows calls from JNI in idle state to notify errors
8183b26844e60f8487388e7e62709faf0dada86e7e1Eric Laurent    if (!(msg == MEDIA_ERROR && mCurrentState == MEDIA_PLAYER_IDLE) && mPlayer == 0) {
8193856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("notify(%d, %d, %d) callback on disconnected mediaplayer", msg, ext1, ext2);
8201af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams        if (locked) mLock.unlock();   // release the lock when done.
82189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        return;
82289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
82389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
82489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    switch (msg) {
82589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    case MEDIA_NOP: // interface test message
82689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        break;
82789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    case MEDIA_PREPARED:
8283856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("prepared");
82989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mCurrentState = MEDIA_PLAYER_PREPARED;
83089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (mPrepareSync) {
8313856b090cd04ba5dd4a59a12430ed724d5995909Steve Block            ALOGV("signal application thread");
83289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mPrepareSync = false;
83389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mPrepareStatus = NO_ERROR;
83489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mSignal.signal();
83589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
83689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        break;
83789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    case MEDIA_PLAYBACK_COMPLETE:
8383856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("playback complete");
8391c1503cf47c0a37a30e7acac2c5d29140fc61a5fMarco Nelissen        if (mCurrentState == MEDIA_PLAYER_IDLE) {
84029357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block            ALOGE("playback complete in idle state");
8411c1503cf47c0a37a30e7acac2c5d29140fc61a5fMarco Nelissen        }
84289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (!mLoop) {
84389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentState = MEDIA_PLAYER_PLAYBACK_COMPLETE;
84489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
84589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        break;
84689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    case MEDIA_ERROR:
84765e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project        // Always log errors.
84865e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project        // ext1: Media framework error code.
84965e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project        // ext2: Implementation dependant error code.
85029357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block        ALOGE("error (%d, %d)", ext1, ext2);
85189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mCurrentState = MEDIA_PLAYER_STATE_ERROR;
85289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (mPrepareSync)
85389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        {
8543856b090cd04ba5dd4a59a12430ed724d5995909Steve Block            ALOGV("signal application thread");
85589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mPrepareSync = false;
85689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mPrepareStatus = ext1;
85789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mSignal.signal();
85889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            send = false;
85989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
86089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        break;
86165e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project    case MEDIA_INFO:
86265e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project        // ext1: Media framework error code.
86365e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project        // ext2: Implementation dependant error code.
864145e68fc778275963189b02a1adcbe27cce4d769Andreas Huber        if (ext1 != MEDIA_INFO_VIDEO_TRACK_LAGGING) {
8655ff1dd576bb93c45b44088a51544a18fc43ebf58Steve Block            ALOGW("info/warning (%d, %d)", ext1, ext2);
866145e68fc778275963189b02a1adcbe27cce4d769Andreas Huber        }
86765e731f393f704eedab6fbe0af7f8a580c8d4617The Android Open Source Project        break;
86889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    case MEDIA_SEEK_COMPLETE:
8693856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("Received seek complete");
87089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        if (mSeekPosition != mCurrentPosition) {
8713856b090cd04ba5dd4a59a12430ed724d5995909Steve Block            ALOGV("Executing queued seekTo(%d)", mSeekPosition);
87289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mSeekPosition = -1;
87389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            seekTo_l(mCurrentPosition);
87489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
87589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        else {
8763856b090cd04ba5dd4a59a12430ed724d5995909Steve Block            ALOGV("All seeks complete - return to regularly scheduled program");
87789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project            mCurrentPosition = mSeekPosition = -1;
87889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        }
87989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        break;
88089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    case MEDIA_BUFFERING_UPDATE:
8813856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("buffering %d", ext1);
88289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        break;
88389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    case MEDIA_SET_VIDEO_SIZE:
8843856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("New video size %d x %d", ext1, ext2);
88589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mVideoWidth = ext1;
88689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        mVideoHeight = ext2;
88789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        break;
888b483c4724846c0b8d4e82afcbb7c17f671bae81cGloria Wang    case MEDIA_TIMED_TEXT:
8893856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("Received timed text message");
890b483c4724846c0b8d4e82afcbb7c17f671bae81cGloria Wang        break;
891dcb89b3b505522efde173c105a851c412f947178Chong Zhang    case MEDIA_SUBTITLE_DATA:
892dcb89b3b505522efde173c105a851c412f947178Chong Zhang        ALOGV("Received subtitle data message");
893dcb89b3b505522efde173c105a851c412f947178Chong Zhang        break;
8940852843d304006e3ab333081fddda13b07193de8Robert Shih    case MEDIA_META_DATA:
8950852843d304006e3ab333081fddda13b07193de8Robert Shih        ALOGV("Received timed metadata message");
8960852843d304006e3ab333081fddda13b07193de8Robert Shih        break;
89789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    default:
8983856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("unrecognized message: (%d, %d, %d)", msg, ext1, ext2);
89989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        break;
90089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
90189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
90289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    sp<MediaPlayerListener> listener = mListener;
9031af452f333664e8b0a61d96a9b3bb682d8b9a00fJason Sams    if (locked) mLock.unlock();
90489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
90589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    // this prevents re-entrant calls into client code
90689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    if ((listener != 0) && send) {
90789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project        Mutex::Autolock _l(mNotifyLock);
9083856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("callback application");
909b483c4724846c0b8d4e82afcbb7c17f671bae81cGloria Wang        listener->notify(msg, ext1, ext2, obj);
9103856b090cd04ba5dd4a59a12430ed724d5995909Steve Block        ALOGV("back from callback");
91189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project    }
91289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}
91389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project
914dd172fce75b2a1c3cb3a5d3b3bbb5020b1ae8675James Dongvoid MediaPlayer::died()
915dd172fce75b2a1c3cb3a5d3b3bbb5020b1ae8675James Dong{
9163856b090cd04ba5dd4a59a12430ed724d5995909Steve Block    ALOGV("died");
917dd172fce75b2a1c3cb3a5d3b3bbb5020b1ae8675James Dong    notify(MEDIA_ERROR, MEDIA_ERROR_SERVER_DIED, 0);
918dd172fce75b2a1c3cb3a5d3b3bbb5020b1ae8675James Dong}
919dd172fce75b2a1c3cb3a5d3b3bbb5020b1ae8675James Dong
9206b74d671a1321a6ecc4a40b6c87beedfecc1ec44Marco Nelissenstatus_t MediaPlayer::setNextMediaPlayer(const sp<MediaPlayer>& next) {
9211243869fb29ee580fa5c179443420c06a779dbfdWei Jia    Mutex::Autolock _l(mLock);
9226b74d671a1321a6ecc4a40b6c87beedfecc1ec44Marco Nelissen    if (mPlayer == NULL) {
9236b74d671a1321a6ecc4a40b6c87beedfecc1ec44Marco Nelissen        return NO_INIT;
9246b74d671a1321a6ecc4a40b6c87beedfecc1ec44Marco Nelissen    }
925b13820ffafcb6bcdd33b6272676535afb4dff479Marco Nelissen
926b13820ffafcb6bcdd33b6272676535afb4dff479Marco Nelissen    if (next != NULL && !(next->mCurrentState &
927b13820ffafcb6bcdd33b6272676535afb4dff479Marco Nelissen            (MEDIA_PLAYER_PREPARED | MEDIA_PLAYER_PAUSED | MEDIA_PLAYER_PLAYBACK_COMPLETE))) {
928b13820ffafcb6bcdd33b6272676535afb4dff479Marco Nelissen        ALOGE("next player is not prepared");
929b13820ffafcb6bcdd33b6272676535afb4dff479Marco Nelissen        return INVALID_OPERATION;
930b13820ffafcb6bcdd33b6272676535afb4dff479Marco Nelissen    }
931b13820ffafcb6bcdd33b6272676535afb4dff479Marco Nelissen
9326b74d671a1321a6ecc4a40b6c87beedfecc1ec44Marco Nelissen    return mPlayer->setNextPlayer(next == NULL ? NULL : next->mPlayer);
9336b74d671a1321a6ecc4a40b6c87beedfecc1ec44Marco Nelissen}
9346b74d671a1321a6ecc4a40b6c87beedfecc1ec44Marco Nelissen
93540bc906252974d0b389ae4a147232d0c9a97193fGlenn Kasten} // namespace android
936