mediametadataretriever.cpp revision 61a6d26aab95870279b274e565c1495748befde0
189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project/* 289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** 389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project** Copyright 2008, 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 "MediaMetadataRetriever" 2089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 217562408b2261d38415453378b6188f74fda99d88Mathias Agopian#include <binder/IServiceManager.h> 227562408b2261d38415453378b6188f74fda99d88Mathias Agopian#include <binder/IPCThreadState.h> 2389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project#include <media/mediametadataretriever.h> 2489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project#include <media/IMediaPlayerService.h> 2589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project#include <utils/Log.h> 2689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project#include <dlfcn.h> 2789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 2889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectnamespace android { 2989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 3089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project// client singleton for binder interface to service 3189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source ProjectMutex MediaMetadataRetriever::sServiceLock; 3289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectsp<IMediaPlayerService> MediaMetadataRetriever::sService; 3389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectsp<MediaMetadataRetriever::DeathNotifier> MediaMetadataRetriever::sDeathNotifier; 3489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 3561a6d26aab95870279b274e565c1495748befde0Marco Nelissenconst sp<IMediaPlayerService> MediaMetadataRetriever::getService() 3689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{ 3789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project Mutex::Autolock lock(sServiceLock); 387fc9a6fdf146ded90b51c52f4a05d797294dcb85Glenn Kasten if (sService == 0) { 3989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project sp<IServiceManager> sm = defaultServiceManager(); 4089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project sp<IBinder> binder; 4189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project do { 4289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project binder = sm->getService(String16("media.player")); 4389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (binder != 0) { 4489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project break; 4589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 465ff1dd576bb93c45b44088a51544a18fc43ebf58Steve Block ALOGW("MediaPlayerService not published, waiting..."); 4789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project usleep(500000); // 0.5 s 48e53b9ead781c36e96d6b6f012ddffc93a3d80f0dGlenn Kasten } while (true); 4989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (sDeathNotifier == NULL) { 5089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project sDeathNotifier = new DeathNotifier(); 5189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 5289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project binder->linkToDeath(sDeathNotifier); 5389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project sService = interface_cast<IMediaPlayerService>(binder); 5489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 5529357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE_IF(sService == 0, "no MediaPlayerService!?"); 5689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return sService; 5789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 5889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 5989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source ProjectMediaMetadataRetriever::MediaMetadataRetriever() 6089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{ 613856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("constructor"); 6261a6d26aab95870279b274e565c1495748befde0Marco Nelissen const sp<IMediaPlayerService> service(getService()); 6389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (service == 0) { 6429357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("failed to obtain MediaMetadataRetrieverService"); 6589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return; 6689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 678d6cc842e8d525405c68e57fdf3bc5da0b4d7e87Glenn Kasten sp<IMediaMetadataRetriever> retriever(service->createMetadataRetriever()); 6889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (retriever == 0) { 6929357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("failed to create IMediaMetadataRetriever object from server"); 7089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 7189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project mRetriever = retriever; 7289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 7389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 7489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source ProjectMediaMetadataRetriever::~MediaMetadataRetriever() 7589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{ 763856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("destructor"); 7789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project disconnect(); 7889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project IPCThreadState::self()->flushCommands(); 7989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 8089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 8189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectvoid MediaMetadataRetriever::disconnect() 8289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{ 833856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("disconnect"); 8489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project sp<IMediaMetadataRetriever> retriever; 8589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project { 8689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project Mutex::Autolock _l(mLock); 8789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project retriever = mRetriever; 8889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project mRetriever.clear(); 8989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 9089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (retriever != 0) { 9189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project retriever->disconnect(); 9289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 9389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 9489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 95af8791e112c8072452bd14ef3c43a47511d19542Andreas Huberstatus_t MediaMetadataRetriever::setDataSource( 96af8791e112c8072452bd14ef3c43a47511d19542Andreas Huber const char *srcUrl, const KeyedVector<String8, String8> *headers) 9789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{ 983856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("setDataSource"); 99a17a1347ffe281fc70633ba8dc98f6cf49ac06ffDave Sparks Mutex::Autolock _l(mLock); 10089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (mRetriever == 0) { 10129357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("retriever is not initialized"); 10289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return INVALID_OPERATION; 10389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 10489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (srcUrl == NULL) { 10529357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("data source is a null pointer"); 10689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return UNKNOWN_ERROR; 10789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 1083856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("data source (%s)", srcUrl); 109af8791e112c8072452bd14ef3c43a47511d19542Andreas Huber return mRetriever->setDataSource(srcUrl, headers); 11089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 11189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 11289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectstatus_t MediaMetadataRetriever::setDataSource(int fd, int64_t offset, int64_t length) 11389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{ 1143856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("setDataSource(%d, %lld, %lld)", fd, offset, length); 115a17a1347ffe281fc70633ba8dc98f6cf49ac06ffDave Sparks Mutex::Autolock _l(mLock); 11689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (mRetriever == 0) { 11729357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("retriever is not initialized"); 11889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return INVALID_OPERATION; 11989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 12089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (fd < 0 || offset < 0 || length < 0) { 12129357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("Invalid negative argument"); 12289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return UNKNOWN_ERROR; 12389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 12489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return mRetriever->setDataSource(fd, offset, length); 12589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 12689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 12716afe2fb439cab6125bb46a07a8078d4ce1c1ea5James Dongsp<IMemory> MediaMetadataRetriever::getFrameAtTime(int64_t timeUs, int option) 12889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{ 1293856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("getFrameAtTime: time(%lld us) option(%d)", timeUs, option); 130a17a1347ffe281fc70633ba8dc98f6cf49ac06ffDave Sparks Mutex::Autolock _l(mLock); 13189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (mRetriever == 0) { 13229357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("retriever is not initialized"); 13389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return NULL; 13489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 13516afe2fb439cab6125bb46a07a8078d4ce1c1ea5James Dong return mRetriever->getFrameAtTime(timeUs, option); 13689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 13789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 13889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectconst char* MediaMetadataRetriever::extractMetadata(int keyCode) 13989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{ 1403856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("extractMetadata(%d)", keyCode); 141a17a1347ffe281fc70633ba8dc98f6cf49ac06ffDave Sparks Mutex::Autolock _l(mLock); 14289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (mRetriever == 0) { 14329357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("retriever is not initialized"); 14489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return NULL; 14589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 14689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return mRetriever->extractMetadata(keyCode); 14789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 14889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 14989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectsp<IMemory> MediaMetadataRetriever::extractAlbumArt() 15089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{ 1513856b090cd04ba5dd4a59a12430ed724d5995909Steve Block ALOGV("extractAlbumArt"); 152a17a1347ffe281fc70633ba8dc98f6cf49ac06ffDave Sparks Mutex::Autolock _l(mLock); 15389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (mRetriever == 0) { 15429357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block ALOGE("retriever is not initialized"); 15589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return NULL; 15689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 15789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project return mRetriever->extractAlbumArt(); 15889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 15989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 16089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Projectvoid MediaMetadataRetriever::DeathNotifier::binderDied(const wp<IBinder>& who) { 16189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project Mutex::Autolock lock(MediaMetadataRetriever::sServiceLock); 16289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project MediaMetadataRetriever::sService.clear(); 1635ff1dd576bb93c45b44088a51544a18fc43ebf58Steve Block ALOGW("MediaMetadataRetriever server died!"); 16489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 16589fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 16689fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source ProjectMediaMetadataRetriever::DeathNotifier::~DeathNotifier() 16789fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project{ 16889fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project Mutex::Autolock lock(sServiceLock); 16989fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project if (sService != 0) { 17089fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project sService->asBinder()->unlinkToDeath(this); 17189fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project } 17289fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project} 17389fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project 17489fa4ad53f2f4d57adbc97ae1149fc00c9b6f3c5The Android Open Source Project}; // namespace android 175