• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2 **
3 ** Copyright 2008, The Android Open Source Project
4 **
5 ** Licensed under the Apache License, Version 2.0 (the "License");
6 ** you may not use this file except in compliance with the License.
7 ** You may obtain a copy of the License at
8 **
9 **     http://www.apache.org/licenses/LICENSE-2.0
10 **
11 ** Unless required by applicable law or agreed to in writing, software
12 ** distributed under the License is distributed on an "AS IS" BASIS,
13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 ** See the License for the specific language governing permissions and
15 ** limitations under the License.
16 */
17 
18 // Proxy for media player implementations
19 
20 //#define LOG_NDEBUG 0
21 #define LOG_TAG "MediaPlayerService"
22 #include <utils/Log.h>
23 
24 #include <sys/types.h>
25 #include <sys/stat.h>
26 #include <dirent.h>
27 #include <unistd.h>
28 
29 #include <string.h>
30 
31 #include <cutils/atomic.h>
32 #include <cutils/properties.h> // for property_get
33 
34 #include <utils/misc.h>
35 
36 #include <android_runtime/ActivityManager.h>
37 
38 #include <binder/IPCThreadState.h>
39 #include <binder/IServiceManager.h>
40 #include <binder/MemoryHeapBase.h>
41 #include <binder/MemoryBase.h>
42 #include <utils/Errors.h>  // for status_t
43 #include <utils/String8.h>
44 #include <utils/SystemClock.h>
45 #include <utils/Vector.h>
46 #include <cutils/properties.h>
47 
48 #include <media/MediaPlayerInterface.h>
49 #include <media/mediarecorder.h>
50 #include <media/MediaMetadataRetrieverInterface.h>
51 #include <media/Metadata.h>
52 #include <media/AudioTrack.h>
53 
54 #include "MediaRecorderClient.h"
55 #include "MediaPlayerService.h"
56 #include "MetadataRetrieverClient.h"
57 
58 #include "MidiFile.h"
59 #include <media/PVPlayer.h>
60 #include "TestPlayerStub.h"
61 #include "StagefrightPlayer.h"
62 
63 #include <OMX.h>
64 
65 /* desktop Linux needs a little help with gettid() */
66 #if defined(HAVE_GETTID) && !defined(HAVE_ANDROID_OS)
67 #define __KERNEL__
68 # include <linux/unistd.h>
69 #ifdef _syscall0
70 _syscall0(pid_t,gettid)
71 #else
72 pid_t gettid() { return syscall(__NR_gettid);}
73 #endif
74 #undef __KERNEL__
75 #endif
76 
77 namespace {
78 using android::media::Metadata;
79 using android::status_t;
80 using android::OK;
81 using android::BAD_VALUE;
82 using android::NOT_ENOUGH_DATA;
83 using android::Parcel;
84 
85 // Max number of entries in the filter.
86 const int kMaxFilterSize = 64;  // I pulled that out of thin air.
87 
88 // FIXME: Move all the metadata related function in the Metadata.cpp
89 
90 
91 // Unmarshall a filter from a Parcel.
92 // Filter format in a parcel:
93 //
94 //  0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
95 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
96 // |                       number of entries (n)                   |
97 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
98 // |                       metadata type 1                         |
99 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
100 // |                       metadata type 2                         |
101 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
102 //  ....
103 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
104 // |                       metadata type n                         |
105 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
106 //
107 // @param p Parcel that should start with a filter.
108 // @param[out] filter On exit contains the list of metadata type to be
109 //                    filtered.
110 // @param[out] status On exit contains the status code to be returned.
111 // @return true if the parcel starts with a valid filter.
unmarshallFilter(const Parcel & p,Metadata::Filter * filter,status_t * status)112 bool unmarshallFilter(const Parcel& p,
113                       Metadata::Filter *filter,
114                       status_t *status)
115 {
116     int32_t val;
117     if (p.readInt32(&val) != OK)
118     {
119         LOGE("Failed to read filter's length");
120         *status = NOT_ENOUGH_DATA;
121         return false;
122     }
123 
124     if( val > kMaxFilterSize || val < 0)
125     {
126         LOGE("Invalid filter len %d", val);
127         *status = BAD_VALUE;
128         return false;
129     }
130 
131     const size_t num = val;
132 
133     filter->clear();
134     filter->setCapacity(num);
135 
136     size_t size = num * sizeof(Metadata::Type);
137 
138 
139     if (p.dataAvail() < size)
140     {
141         LOGE("Filter too short expected %d but got %d", size, p.dataAvail());
142         *status = NOT_ENOUGH_DATA;
143         return false;
144     }
145 
146     const Metadata::Type *data =
147             static_cast<const Metadata::Type*>(p.readInplace(size));
148 
149     if (NULL == data)
150     {
151         LOGE("Filter had no data");
152         *status = BAD_VALUE;
153         return false;
154     }
155 
156     // TODO: The stl impl of vector would be more efficient here
157     // because it degenerates into a memcpy on pod types. Try to
158     // replace later or use stl::set.
159     for (size_t i = 0; i < num; ++i)
160     {
161         filter->add(*data);
162         ++data;
163     }
164     *status = OK;
165     return true;
166 }
167 
168 // @param filter Of metadata type.
169 // @param val To be searched.
170 // @return true if a match was found.
findMetadata(const Metadata::Filter & filter,const int32_t val)171 bool findMetadata(const Metadata::Filter& filter, const int32_t val)
172 {
173     // Deal with empty and ANY right away
174     if (filter.isEmpty()) return false;
175     if (filter[0] == Metadata::kAny) return true;
176 
177     return filter.indexOf(val) >= 0;
178 }
179 
180 }  // anonymous namespace
181 
182 
183 namespace android {
184 
185 // TODO: Temp hack until we can register players
186 typedef struct {
187     const char *extension;
188     const player_type playertype;
189 } extmap;
190 extmap FILE_EXTS [] =  {
191         {".mid", SONIVOX_PLAYER},
192         {".midi", SONIVOX_PLAYER},
193         {".smf", SONIVOX_PLAYER},
194         {".xmf", SONIVOX_PLAYER},
195         {".imy", SONIVOX_PLAYER},
196         {".rtttl", SONIVOX_PLAYER},
197         {".rtx", SONIVOX_PLAYER},
198         {".ota", SONIVOX_PLAYER},
199 #ifndef NO_OPENCORE
200         {".wma", PV_PLAYER},
201         {".wmv", PV_PLAYER},
202         {".asf", PV_PLAYER},
203 #endif
204 };
205 
206 // TODO: Find real cause of Audio/Video delay in PV framework and remove this workaround
207 /* static */ int MediaPlayerService::AudioOutput::mMinBufferCount = 4;
208 /* static */ bool MediaPlayerService::AudioOutput::mIsOnEmulator = false;
209 
instantiate()210 void MediaPlayerService::instantiate() {
211     defaultServiceManager()->addService(
212             String16("media.player"), new MediaPlayerService());
213 }
214 
MediaPlayerService()215 MediaPlayerService::MediaPlayerService()
216 {
217     LOGV("MediaPlayerService created");
218     mNextConnId = 1;
219 }
220 
~MediaPlayerService()221 MediaPlayerService::~MediaPlayerService()
222 {
223     LOGV("MediaPlayerService destroyed");
224 }
225 
createMediaRecorder(pid_t pid)226 sp<IMediaRecorder> MediaPlayerService::createMediaRecorder(pid_t pid)
227 {
228     sp<MediaRecorderClient> recorder = new MediaRecorderClient(this, pid);
229     wp<MediaRecorderClient> w = recorder;
230     Mutex::Autolock lock(mLock);
231     mMediaRecorderClients.add(w);
232     LOGV("Create new media recorder client from pid %d", pid);
233     return recorder;
234 }
235 
removeMediaRecorderClient(wp<MediaRecorderClient> client)236 void MediaPlayerService::removeMediaRecorderClient(wp<MediaRecorderClient> client)
237 {
238     Mutex::Autolock lock(mLock);
239     mMediaRecorderClients.remove(client);
240     LOGV("Delete media recorder client");
241 }
242 
createMetadataRetriever(pid_t pid)243 sp<IMediaMetadataRetriever> MediaPlayerService::createMetadataRetriever(pid_t pid)
244 {
245     sp<MetadataRetrieverClient> retriever = new MetadataRetrieverClient(pid);
246     LOGV("Create new media retriever from pid %d", pid);
247     return retriever;
248 }
249 
create(pid_t pid,const sp<IMediaPlayerClient> & client,const char * url,const KeyedVector<String8,String8> * headers,int audioSessionId)250 sp<IMediaPlayer> MediaPlayerService::create(
251         pid_t pid, const sp<IMediaPlayerClient>& client, const char* url,
252         const KeyedVector<String8, String8> *headers, int audioSessionId)
253 {
254     int32_t connId = android_atomic_inc(&mNextConnId);
255     sp<Client> c = new Client(this, pid, connId, client, audioSessionId);
256     LOGV("Create new client(%d) from pid %d, url=%s, connId=%d, audioSessionId=%d",
257             connId, pid, url, connId, audioSessionId);
258     if (NO_ERROR != c->setDataSource(url, headers))
259     {
260         c.clear();
261         return c;
262     }
263     wp<Client> w = c;
264     Mutex::Autolock lock(mLock);
265     mClients.add(w);
266     return c;
267 }
268 
create(pid_t pid,const sp<IMediaPlayerClient> & client,int fd,int64_t offset,int64_t length,int audioSessionId)269 sp<IMediaPlayer> MediaPlayerService::create(pid_t pid, const sp<IMediaPlayerClient>& client,
270         int fd, int64_t offset, int64_t length, int audioSessionId)
271 {
272     int32_t connId = android_atomic_inc(&mNextConnId);
273     sp<Client> c = new Client(this, pid, connId, client, audioSessionId);
274     LOGV("Create new client(%d) from pid %d, fd=%d, offset=%lld, length=%lld, audioSessionId=%d",
275             connId, pid, fd, offset, length, audioSessionId);
276     if (NO_ERROR != c->setDataSource(fd, offset, length)) {
277         c.clear();
278     } else {
279         wp<Client> w = c;
280         Mutex::Autolock lock(mLock);
281         mClients.add(w);
282     }
283     ::close(fd);
284     return c;
285 }
286 
getOMX()287 sp<IOMX> MediaPlayerService::getOMX() {
288     Mutex::Autolock autoLock(mLock);
289 
290     if (mOMX.get() == NULL) {
291         mOMX = new OMX;
292     }
293 
294     return mOMX;
295 }
296 
dump(int fd,const Vector<String16> & args) const297 status_t MediaPlayerService::AudioCache::dump(int fd, const Vector<String16>& args) const
298 {
299     const size_t SIZE = 256;
300     char buffer[SIZE];
301     String8 result;
302 
303     result.append(" AudioCache\n");
304     if (mHeap != 0) {
305         snprintf(buffer, 255, "  heap base(%p), size(%d), flags(%d), device(%s)\n",
306                 mHeap->getBase(), mHeap->getSize(), mHeap->getFlags(), mHeap->getDevice());
307         result.append(buffer);
308     }
309     snprintf(buffer, 255, "  msec per frame(%f), channel count(%d), format(%d), frame count(%ld)\n",
310             mMsecsPerFrame, mChannelCount, mFormat, mFrameCount);
311     result.append(buffer);
312     snprintf(buffer, 255, "  sample rate(%d), size(%d), error(%d), command complete(%s)\n",
313             mSampleRate, mSize, mError, mCommandComplete?"true":"false");
314     result.append(buffer);
315     ::write(fd, result.string(), result.size());
316     return NO_ERROR;
317 }
318 
dump(int fd,const Vector<String16> & args) const319 status_t MediaPlayerService::AudioOutput::dump(int fd, const Vector<String16>& args) const
320 {
321     const size_t SIZE = 256;
322     char buffer[SIZE];
323     String8 result;
324 
325     result.append(" AudioOutput\n");
326     snprintf(buffer, 255, "  stream type(%d), left - right volume(%f, %f)\n",
327             mStreamType, mLeftVolume, mRightVolume);
328     result.append(buffer);
329     snprintf(buffer, 255, "  msec per frame(%f), latency (%d)\n",
330             mMsecsPerFrame, mLatency);
331     result.append(buffer);
332     snprintf(buffer, 255, "  aux effect id(%d), send level (%f)\n",
333             mAuxEffectId, mSendLevel);
334     result.append(buffer);
335 
336     ::write(fd, result.string(), result.size());
337     if (mTrack != 0) {
338         mTrack->dump(fd, args);
339     }
340     return NO_ERROR;
341 }
342 
dump(int fd,const Vector<String16> & args) const343 status_t MediaPlayerService::Client::dump(int fd, const Vector<String16>& args) const
344 {
345     const size_t SIZE = 256;
346     char buffer[SIZE];
347     String8 result;
348     result.append(" Client\n");
349     snprintf(buffer, 255, "  pid(%d), connId(%d), status(%d), looping(%s)\n",
350             mPid, mConnId, mStatus, mLoop?"true": "false");
351     result.append(buffer);
352     write(fd, result.string(), result.size());
353     if (mAudioOutput != 0) {
354         mAudioOutput->dump(fd, args);
355     }
356     write(fd, "\n", 1);
357     return NO_ERROR;
358 }
359 
myTid()360 static int myTid() {
361 #ifdef HAVE_GETTID
362     return gettid();
363 #else
364     return getpid();
365 #endif
366 }
367 
368 #if defined(__arm__)
369 extern "C" void get_malloc_leak_info(uint8_t** info, size_t* overallSize,
370         size_t* infoSize, size_t* totalMemory, size_t* backtraceSize);
371 extern "C" void free_malloc_leak_info(uint8_t* info);
372 
373 // Use the String-class below instead of String8 to allocate all memory
374 // beforehand and not reenter the heap while we are examining it...
375 struct MyString8 {
376     static const size_t MAX_SIZE = 256 * 1024;
377 
MyString8android::MyString8378     MyString8()
379         : mPtr((char *)malloc(MAX_SIZE)) {
380         *mPtr = '\0';
381     }
382 
~MyString8android::MyString8383     ~MyString8() {
384         free(mPtr);
385     }
386 
appendandroid::MyString8387     void append(const char *s) {
388         strcat(mPtr, s);
389     }
390 
stringandroid::MyString8391     const char *string() const {
392         return mPtr;
393     }
394 
sizeandroid::MyString8395     size_t size() const {
396         return strlen(mPtr);
397     }
398 
399 private:
400     char *mPtr;
401 
402     MyString8(const MyString8 &);
403     MyString8 &operator=(const MyString8 &);
404 };
405 
memStatus(int fd,const Vector<String16> & args)406 void memStatus(int fd, const Vector<String16>& args)
407 {
408     const size_t SIZE = 256;
409     char buffer[SIZE];
410     MyString8 result;
411 
412     typedef struct {
413         size_t size;
414         size_t dups;
415         intptr_t * backtrace;
416     } AllocEntry;
417 
418     uint8_t *info = NULL;
419     size_t overallSize = 0;
420     size_t infoSize = 0;
421     size_t totalMemory = 0;
422     size_t backtraceSize = 0;
423 
424     get_malloc_leak_info(&info, &overallSize, &infoSize, &totalMemory, &backtraceSize);
425     if (info) {
426         uint8_t *ptr = info;
427         size_t count = overallSize / infoSize;
428 
429         snprintf(buffer, SIZE, " Allocation count %i\n", count);
430         result.append(buffer);
431         snprintf(buffer, SIZE, " Total memory %i\n", totalMemory);
432         result.append(buffer);
433 
434         AllocEntry * entries = new AllocEntry[count];
435 
436         for (size_t i = 0; i < count; i++) {
437             // Each entry should be size_t, size_t, intptr_t[backtraceSize]
438             AllocEntry *e = &entries[i];
439 
440             e->size = *reinterpret_cast<size_t *>(ptr);
441             ptr += sizeof(size_t);
442 
443             e->dups = *reinterpret_cast<size_t *>(ptr);
444             ptr += sizeof(size_t);
445 
446             e->backtrace = reinterpret_cast<intptr_t *>(ptr);
447             ptr += sizeof(intptr_t) * backtraceSize;
448         }
449 
450         // Now we need to sort the entries.  They come sorted by size but
451         // not by stack trace which causes problems using diff.
452         bool moved;
453         do {
454             moved = false;
455             for (size_t i = 0; i < (count - 1); i++) {
456                 AllocEntry *e1 = &entries[i];
457                 AllocEntry *e2 = &entries[i+1];
458 
459                 bool swap = e1->size < e2->size;
460                 if (e1->size == e2->size) {
461                     for(size_t j = 0; j < backtraceSize; j++) {
462                         if (e1->backtrace[j] == e2->backtrace[j]) {
463                             continue;
464                         }
465                         swap = e1->backtrace[j] < e2->backtrace[j];
466                         break;
467                     }
468                 }
469                 if (swap) {
470                     AllocEntry t = entries[i];
471                     entries[i] = entries[i+1];
472                     entries[i+1] = t;
473                     moved = true;
474                 }
475             }
476         } while (moved);
477 
478         for (size_t i = 0; i < count; i++) {
479             AllocEntry *e = &entries[i];
480 
481             snprintf(buffer, SIZE, "size %8i, dup %4i, ", e->size, e->dups);
482             result.append(buffer);
483             for (size_t ct = 0; (ct < backtraceSize) && e->backtrace[ct]; ct++) {
484                 if (ct) {
485                     result.append(", ");
486                 }
487                 snprintf(buffer, SIZE, "0x%08x", e->backtrace[ct]);
488                 result.append(buffer);
489             }
490             result.append("\n");
491         }
492 
493         delete[] entries;
494         free_malloc_leak_info(info);
495     }
496 
497     write(fd, result.string(), result.size());
498 }
499 #endif
500 
dump(int fd,const Vector<String16> & args)501 status_t MediaPlayerService::dump(int fd, const Vector<String16>& args)
502 {
503     const size_t SIZE = 256;
504     char buffer[SIZE];
505     String8 result;
506     if (checkCallingPermission(String16("android.permission.DUMP")) == false) {
507         snprintf(buffer, SIZE, "Permission Denial: "
508                 "can't dump MediaPlayerService from pid=%d, uid=%d\n",
509                 IPCThreadState::self()->getCallingPid(),
510                 IPCThreadState::self()->getCallingUid());
511         result.append(buffer);
512     } else {
513         Mutex::Autolock lock(mLock);
514         for (int i = 0, n = mClients.size(); i < n; ++i) {
515             sp<Client> c = mClients[i].promote();
516             if (c != 0) c->dump(fd, args);
517         }
518         if (mMediaRecorderClients.size() == 0) {
519                 result.append(" No media recorder client\n\n");
520         } else {
521             for (int i = 0, n = mMediaRecorderClients.size(); i < n; ++i) {
522                 sp<MediaRecorderClient> c = mMediaRecorderClients[i].promote();
523                 snprintf(buffer, 255, " MediaRecorderClient pid(%d)\n", c->mPid);
524                 result.append(buffer);
525                 write(fd, result.string(), result.size());
526                 result = "\n";
527                 c->dump(fd, args);
528             }
529         }
530 
531         result.append(" Files opened and/or mapped:\n");
532         snprintf(buffer, SIZE, "/proc/%d/maps", myTid());
533         FILE *f = fopen(buffer, "r");
534         if (f) {
535             while (!feof(f)) {
536                 fgets(buffer, SIZE, f);
537                 if (strstr(buffer, " /mnt/sdcard/") ||
538                     strstr(buffer, " /system/sounds/") ||
539                     strstr(buffer, " /data/") ||
540                     strstr(buffer, " /system/media/")) {
541                     result.append("  ");
542                     result.append(buffer);
543                 }
544             }
545             fclose(f);
546         } else {
547             result.append("couldn't open ");
548             result.append(buffer);
549             result.append("\n");
550         }
551 
552         snprintf(buffer, SIZE, "/proc/%d/fd", myTid());
553         DIR *d = opendir(buffer);
554         if (d) {
555             struct dirent *ent;
556             while((ent = readdir(d)) != NULL) {
557                 if (strcmp(ent->d_name,".") && strcmp(ent->d_name,"..")) {
558                     snprintf(buffer, SIZE, "/proc/%d/fd/%s", myTid(), ent->d_name);
559                     struct stat s;
560                     if (lstat(buffer, &s) == 0) {
561                         if ((s.st_mode & S_IFMT) == S_IFLNK) {
562                             char linkto[256];
563                             int len = readlink(buffer, linkto, sizeof(linkto));
564                             if(len > 0) {
565                                 if(len > 255) {
566                                     linkto[252] = '.';
567                                     linkto[253] = '.';
568                                     linkto[254] = '.';
569                                     linkto[255] = 0;
570                                 } else {
571                                     linkto[len] = 0;
572                                 }
573                                 if (strstr(linkto, "/mnt/sdcard/") == linkto ||
574                                     strstr(linkto, "/system/sounds/") == linkto ||
575                                     strstr(linkto, "/data/") == linkto ||
576                                     strstr(linkto, "/system/media/") == linkto) {
577                                     result.append("  ");
578                                     result.append(buffer);
579                                     result.append(" -> ");
580                                     result.append(linkto);
581                                     result.append("\n");
582                                 }
583                             }
584                         } else {
585                             result.append("  unexpected type for ");
586                             result.append(buffer);
587                             result.append("\n");
588                         }
589                     }
590                 }
591             }
592             closedir(d);
593         } else {
594             result.append("couldn't open ");
595             result.append(buffer);
596             result.append("\n");
597         }
598 
599 #if defined(__arm__)
600         bool dumpMem = false;
601         for (size_t i = 0; i < args.size(); i++) {
602             if (args[i] == String16("-m")) {
603                 dumpMem = true;
604             }
605         }
606         if (dumpMem) {
607             memStatus(fd, args);
608         }
609 #endif
610     }
611     write(fd, result.string(), result.size());
612     return NO_ERROR;
613 }
614 
removeClient(wp<Client> client)615 void MediaPlayerService::removeClient(wp<Client> client)
616 {
617     Mutex::Autolock lock(mLock);
618     mClients.remove(client);
619 }
620 
Client(const sp<MediaPlayerService> & service,pid_t pid,int32_t connId,const sp<IMediaPlayerClient> & client,int audioSessionId)621 MediaPlayerService::Client::Client(const sp<MediaPlayerService>& service, pid_t pid,
622         int32_t connId, const sp<IMediaPlayerClient>& client, int audioSessionId)
623 {
624     LOGV("Client(%d) constructor", connId);
625     mPid = pid;
626     mConnId = connId;
627     mService = service;
628     mClient = client;
629     mLoop = false;
630     mStatus = NO_INIT;
631     mAudioSessionId = audioSessionId;
632 
633 #if CALLBACK_ANTAGONIZER
634     LOGD("create Antagonizer");
635     mAntagonizer = new Antagonizer(notify, this);
636 #endif
637 }
638 
~Client()639 MediaPlayerService::Client::~Client()
640 {
641     LOGV("Client(%d) destructor pid = %d", mConnId, mPid);
642     mAudioOutput.clear();
643     wp<Client> client(this);
644     disconnect();
645     mService->removeClient(client);
646 }
647 
disconnect()648 void MediaPlayerService::Client::disconnect()
649 {
650     LOGV("disconnect(%d) from pid %d", mConnId, mPid);
651     // grab local reference and clear main reference to prevent future
652     // access to object
653     sp<MediaPlayerBase> p;
654     {
655         Mutex::Autolock l(mLock);
656         p = mPlayer;
657     }
658     mClient.clear();
659 
660     mPlayer.clear();
661 
662     // clear the notification to prevent callbacks to dead client
663     // and reset the player. We assume the player will serialize
664     // access to itself if necessary.
665     if (p != 0) {
666         p->setNotifyCallback(0, 0);
667 #if CALLBACK_ANTAGONIZER
668         LOGD("kill Antagonizer");
669         mAntagonizer->kill();
670 #endif
671         p->reset();
672     }
673 
674     IPCThreadState::self()->flushCommands();
675 }
676 
getDefaultPlayerType()677 static player_type getDefaultPlayerType() {
678     return STAGEFRIGHT_PLAYER;
679 }
680 
getPlayerType(int fd,int64_t offset,int64_t length)681 player_type getPlayerType(int fd, int64_t offset, int64_t length)
682 {
683     char buf[20];
684     lseek(fd, offset, SEEK_SET);
685     read(fd, buf, sizeof(buf));
686     lseek(fd, offset, SEEK_SET);
687 
688     long ident = *((long*)buf);
689 
690     // Ogg vorbis?
691     if (ident == 0x5367674f) // 'OggS'
692         return STAGEFRIGHT_PLAYER;
693 
694 #ifndef NO_OPENCORE
695     if (ident == 0x75b22630) {
696         // The magic number for .asf files, i.e. wmv and wma content.
697         // These are not currently supported through stagefright.
698         return PV_PLAYER;
699     }
700 #endif
701 
702     // Some kind of MIDI?
703     EAS_DATA_HANDLE easdata;
704     if (EAS_Init(&easdata) == EAS_SUCCESS) {
705         EAS_FILE locator;
706         locator.path = NULL;
707         locator.fd = fd;
708         locator.offset = offset;
709         locator.length = length;
710         EAS_HANDLE  eashandle;
711         if (EAS_OpenFile(easdata, &locator, &eashandle) == EAS_SUCCESS) {
712             EAS_CloseFile(easdata, eashandle);
713             EAS_Shutdown(easdata);
714             return SONIVOX_PLAYER;
715         }
716         EAS_Shutdown(easdata);
717     }
718 
719     return getDefaultPlayerType();
720 }
721 
getPlayerType(const char * url)722 player_type getPlayerType(const char* url)
723 {
724     if (TestPlayerStub::canBeUsed(url)) {
725         return TEST_PLAYER;
726     }
727 
728     // use MidiFile for MIDI extensions
729     int lenURL = strlen(url);
730     for (int i = 0; i < NELEM(FILE_EXTS); ++i) {
731         int len = strlen(FILE_EXTS[i].extension);
732         int start = lenURL - len;
733         if (start > 0) {
734             if (!strncasecmp(url + start, FILE_EXTS[i].extension, len)) {
735                 return FILE_EXTS[i].playertype;
736             }
737         }
738     }
739 
740     if (!strncasecmp(url, "rtsp://", 7)) {
741         char value[PROPERTY_VALUE_MAX];
742         if (property_get("media.stagefright.enable-rtsp", value, NULL)
743             && (strcmp(value, "1") && strcasecmp(value, "true"))) {
744             // For now, we're going to use PV for rtsp-based playback
745             // by default until we can clear up a few more issues.
746             return PV_PLAYER;
747         }
748     }
749 
750     return getDefaultPlayerType();
751 }
752 
createPlayer(player_type playerType,void * cookie,notify_callback_f notifyFunc)753 static sp<MediaPlayerBase> createPlayer(player_type playerType, void* cookie,
754         notify_callback_f notifyFunc)
755 {
756     sp<MediaPlayerBase> p;
757     switch (playerType) {
758 #ifndef NO_OPENCORE
759         case PV_PLAYER:
760             LOGV(" create PVPlayer");
761             p = new PVPlayer();
762             break;
763 #endif
764         case SONIVOX_PLAYER:
765             LOGV(" create MidiFile");
766             p = new MidiFile();
767             break;
768         case STAGEFRIGHT_PLAYER:
769             LOGV(" create StagefrightPlayer");
770             p = new StagefrightPlayer;
771             break;
772         case TEST_PLAYER:
773             LOGV("Create Test Player stub");
774             p = new TestPlayerStub();
775             break;
776     }
777     if (p != NULL) {
778         if (p->initCheck() == NO_ERROR) {
779             p->setNotifyCallback(cookie, notifyFunc);
780         } else {
781             p.clear();
782         }
783     }
784     if (p == NULL) {
785         LOGE("Failed to create player object");
786     }
787     return p;
788 }
789 
createPlayer(player_type playerType)790 sp<MediaPlayerBase> MediaPlayerService::Client::createPlayer(player_type playerType)
791 {
792     // determine if we have the right player type
793     sp<MediaPlayerBase> p = mPlayer;
794     if ((p != NULL) && (p->playerType() != playerType)) {
795         LOGV("delete player");
796         p.clear();
797     }
798     if (p == NULL) {
799         p = android::createPlayer(playerType, this, notify);
800     }
801     return p;
802 }
803 
setDataSource(const char * url,const KeyedVector<String8,String8> * headers)804 status_t MediaPlayerService::Client::setDataSource(
805         const char *url, const KeyedVector<String8, String8> *headers)
806 {
807     LOGV("setDataSource(%s)", url);
808     if (url == NULL)
809         return UNKNOWN_ERROR;
810 
811     if (strncmp(url, "content://", 10) == 0) {
812         // get a filedescriptor for the content Uri and
813         // pass it to the setDataSource(fd) method
814 
815         String16 url16(url);
816         int fd = android::openContentProviderFile(url16);
817         if (fd < 0)
818         {
819             LOGE("Couldn't open fd for %s", url);
820             return UNKNOWN_ERROR;
821         }
822         setDataSource(fd, 0, 0x7fffffffffLL); // this sets mStatus
823         close(fd);
824         return mStatus;
825     } else {
826         player_type playerType = getPlayerType(url);
827         LOGV("player type = %d", playerType);
828 
829         // create the right type of player
830         sp<MediaPlayerBase> p = createPlayer(playerType);
831         if (p == NULL) return NO_INIT;
832 
833         if (!p->hardwareOutput()) {
834             mAudioOutput = new AudioOutput(mAudioSessionId);
835             static_cast<MediaPlayerInterface*>(p.get())->setAudioSink(mAudioOutput);
836         }
837 
838         // now set data source
839         LOGV(" setDataSource");
840         mStatus = p->setDataSource(url, headers);
841         if (mStatus == NO_ERROR) {
842             mPlayer = p;
843         } else {
844             LOGE("  error: %d", mStatus);
845         }
846         return mStatus;
847     }
848 }
849 
setDataSource(int fd,int64_t offset,int64_t length)850 status_t MediaPlayerService::Client::setDataSource(int fd, int64_t offset, int64_t length)
851 {
852     LOGV("setDataSource fd=%d, offset=%lld, length=%lld", fd, offset, length);
853     struct stat sb;
854     int ret = fstat(fd, &sb);
855     if (ret != 0) {
856         LOGE("fstat(%d) failed: %d, %s", fd, ret, strerror(errno));
857         return UNKNOWN_ERROR;
858     }
859 
860     LOGV("st_dev  = %llu", sb.st_dev);
861     LOGV("st_mode = %u", sb.st_mode);
862     LOGV("st_uid  = %lu", sb.st_uid);
863     LOGV("st_gid  = %lu", sb.st_gid);
864     LOGV("st_size = %llu", sb.st_size);
865 
866     if (offset >= sb.st_size) {
867         LOGE("offset error");
868         ::close(fd);
869         return UNKNOWN_ERROR;
870     }
871     if (offset + length > sb.st_size) {
872         length = sb.st_size - offset;
873         LOGV("calculated length = %lld", length);
874     }
875 
876     player_type playerType = getPlayerType(fd, offset, length);
877     LOGV("player type = %d", playerType);
878 
879     // create the right type of player
880     sp<MediaPlayerBase> p = createPlayer(playerType);
881     if (p == NULL) return NO_INIT;
882 
883     if (!p->hardwareOutput()) {
884         mAudioOutput = new AudioOutput(mAudioSessionId);
885         static_cast<MediaPlayerInterface*>(p.get())->setAudioSink(mAudioOutput);
886     }
887 
888     // now set data source
889     mStatus = p->setDataSource(fd, offset, length);
890     if (mStatus == NO_ERROR) mPlayer = p;
891     return mStatus;
892 }
893 
setVideoSurface(const sp<ISurface> & surface)894 status_t MediaPlayerService::Client::setVideoSurface(const sp<ISurface>& surface)
895 {
896     LOGV("[%d] setVideoSurface(%p)", mConnId, surface.get());
897     sp<MediaPlayerBase> p = getPlayer();
898     if (p == 0) return UNKNOWN_ERROR;
899     return p->setVideoSurface(surface);
900 }
901 
invoke(const Parcel & request,Parcel * reply)902 status_t MediaPlayerService::Client::invoke(const Parcel& request,
903                                             Parcel *reply)
904 {
905     sp<MediaPlayerBase> p = getPlayer();
906     if (p == NULL) return UNKNOWN_ERROR;
907     return p->invoke(request, reply);
908 }
909 
910 // This call doesn't need to access the native player.
setMetadataFilter(const Parcel & filter)911 status_t MediaPlayerService::Client::setMetadataFilter(const Parcel& filter)
912 {
913     status_t status;
914     media::Metadata::Filter allow, drop;
915 
916     if (unmarshallFilter(filter, &allow, &status) &&
917         unmarshallFilter(filter, &drop, &status)) {
918         Mutex::Autolock lock(mLock);
919 
920         mMetadataAllow = allow;
921         mMetadataDrop = drop;
922     }
923     return status;
924 }
925 
getMetadata(bool update_only,bool apply_filter,Parcel * reply)926 status_t MediaPlayerService::Client::getMetadata(
927         bool update_only, bool apply_filter, Parcel *reply)
928 {
929     sp<MediaPlayerBase> player = getPlayer();
930     if (player == 0) return UNKNOWN_ERROR;
931 
932     status_t status;
933     // Placeholder for the return code, updated by the caller.
934     reply->writeInt32(-1);
935 
936     media::Metadata::Filter ids;
937 
938     // We don't block notifications while we fetch the data. We clear
939     // mMetadataUpdated first so we don't lose notifications happening
940     // during the rest of this call.
941     {
942         Mutex::Autolock lock(mLock);
943         if (update_only) {
944             ids = mMetadataUpdated;
945         }
946         mMetadataUpdated.clear();
947     }
948 
949     media::Metadata metadata(reply);
950 
951     metadata.appendHeader();
952     status = player->getMetadata(ids, reply);
953 
954     if (status != OK) {
955         metadata.resetParcel();
956         LOGE("getMetadata failed %d", status);
957         return status;
958     }
959 
960     // FIXME: Implement filtering on the result. Not critical since
961     // filtering takes place on the update notifications already. This
962     // would be when all the metadata are fetch and a filter is set.
963 
964     // Everything is fine, update the metadata length.
965     metadata.updateLength();
966     return OK;
967 }
968 
suspend()969 status_t MediaPlayerService::Client::suspend() {
970     sp<MediaPlayerBase> p = getPlayer();
971     if (p == 0) return UNKNOWN_ERROR;
972 
973     return p->suspend();
974 }
975 
resume()976 status_t MediaPlayerService::Client::resume() {
977     sp<MediaPlayerBase> p = getPlayer();
978     if (p == 0) return UNKNOWN_ERROR;
979 
980     return p->resume();
981 }
982 
prepareAsync()983 status_t MediaPlayerService::Client::prepareAsync()
984 {
985     LOGV("[%d] prepareAsync", mConnId);
986     sp<MediaPlayerBase> p = getPlayer();
987     if (p == 0) return UNKNOWN_ERROR;
988     status_t ret = p->prepareAsync();
989 #if CALLBACK_ANTAGONIZER
990     LOGD("start Antagonizer");
991     if (ret == NO_ERROR) mAntagonizer->start();
992 #endif
993     return ret;
994 }
995 
start()996 status_t MediaPlayerService::Client::start()
997 {
998     LOGV("[%d] start", mConnId);
999     sp<MediaPlayerBase> p = getPlayer();
1000     if (p == 0) return UNKNOWN_ERROR;
1001     p->setLooping(mLoop);
1002     return p->start();
1003 }
1004 
stop()1005 status_t MediaPlayerService::Client::stop()
1006 {
1007     LOGV("[%d] stop", mConnId);
1008     sp<MediaPlayerBase> p = getPlayer();
1009     if (p == 0) return UNKNOWN_ERROR;
1010     return p->stop();
1011 }
1012 
pause()1013 status_t MediaPlayerService::Client::pause()
1014 {
1015     LOGV("[%d] pause", mConnId);
1016     sp<MediaPlayerBase> p = getPlayer();
1017     if (p == 0) return UNKNOWN_ERROR;
1018     return p->pause();
1019 }
1020 
isPlaying(bool * state)1021 status_t MediaPlayerService::Client::isPlaying(bool* state)
1022 {
1023     *state = false;
1024     sp<MediaPlayerBase> p = getPlayer();
1025     if (p == 0) return UNKNOWN_ERROR;
1026     *state = p->isPlaying();
1027     LOGV("[%d] isPlaying: %d", mConnId, *state);
1028     return NO_ERROR;
1029 }
1030 
getCurrentPosition(int * msec)1031 status_t MediaPlayerService::Client::getCurrentPosition(int *msec)
1032 {
1033     LOGV("getCurrentPosition");
1034     sp<MediaPlayerBase> p = getPlayer();
1035     if (p == 0) return UNKNOWN_ERROR;
1036     status_t ret = p->getCurrentPosition(msec);
1037     if (ret == NO_ERROR) {
1038         LOGV("[%d] getCurrentPosition = %d", mConnId, *msec);
1039     } else {
1040         LOGE("getCurrentPosition returned %d", ret);
1041     }
1042     return ret;
1043 }
1044 
getDuration(int * msec)1045 status_t MediaPlayerService::Client::getDuration(int *msec)
1046 {
1047     LOGV("getDuration");
1048     sp<MediaPlayerBase> p = getPlayer();
1049     if (p == 0) return UNKNOWN_ERROR;
1050     status_t ret = p->getDuration(msec);
1051     if (ret == NO_ERROR) {
1052         LOGV("[%d] getDuration = %d", mConnId, *msec);
1053     } else {
1054         LOGE("getDuration returned %d", ret);
1055     }
1056     return ret;
1057 }
1058 
seekTo(int msec)1059 status_t MediaPlayerService::Client::seekTo(int msec)
1060 {
1061     LOGV("[%d] seekTo(%d)", mConnId, msec);
1062     sp<MediaPlayerBase> p = getPlayer();
1063     if (p == 0) return UNKNOWN_ERROR;
1064     return p->seekTo(msec);
1065 }
1066 
reset()1067 status_t MediaPlayerService::Client::reset()
1068 {
1069     LOGV("[%d] reset", mConnId);
1070     sp<MediaPlayerBase> p = getPlayer();
1071     if (p == 0) return UNKNOWN_ERROR;
1072     return p->reset();
1073 }
1074 
setAudioStreamType(int type)1075 status_t MediaPlayerService::Client::setAudioStreamType(int type)
1076 {
1077     LOGV("[%d] setAudioStreamType(%d)", mConnId, type);
1078     // TODO: for hardware output, call player instead
1079     Mutex::Autolock l(mLock);
1080     if (mAudioOutput != 0) mAudioOutput->setAudioStreamType(type);
1081     return NO_ERROR;
1082 }
1083 
setLooping(int loop)1084 status_t MediaPlayerService::Client::setLooping(int loop)
1085 {
1086     LOGV("[%d] setLooping(%d)", mConnId, loop);
1087     mLoop = loop;
1088     sp<MediaPlayerBase> p = getPlayer();
1089     if (p != 0) return p->setLooping(loop);
1090     return NO_ERROR;
1091 }
1092 
setVolume(float leftVolume,float rightVolume)1093 status_t MediaPlayerService::Client::setVolume(float leftVolume, float rightVolume)
1094 {
1095     LOGV("[%d] setVolume(%f, %f)", mConnId, leftVolume, rightVolume);
1096     // TODO: for hardware output, call player instead
1097     Mutex::Autolock l(mLock);
1098     if (mAudioOutput != 0) mAudioOutput->setVolume(leftVolume, rightVolume);
1099     return NO_ERROR;
1100 }
1101 
setAuxEffectSendLevel(float level)1102 status_t MediaPlayerService::Client::setAuxEffectSendLevel(float level)
1103 {
1104     LOGV("[%d] setAuxEffectSendLevel(%f)", mConnId, level);
1105     Mutex::Autolock l(mLock);
1106     if (mAudioOutput != 0) return mAudioOutput->setAuxEffectSendLevel(level);
1107     return NO_ERROR;
1108 }
1109 
attachAuxEffect(int effectId)1110 status_t MediaPlayerService::Client::attachAuxEffect(int effectId)
1111 {
1112     LOGV("[%d] attachAuxEffect(%d)", mConnId, effectId);
1113     Mutex::Autolock l(mLock);
1114     if (mAudioOutput != 0) return mAudioOutput->attachAuxEffect(effectId);
1115     return NO_ERROR;
1116 }
1117 
notify(void * cookie,int msg,int ext1,int ext2)1118 void MediaPlayerService::Client::notify(void* cookie, int msg, int ext1, int ext2)
1119 {
1120     Client* client = static_cast<Client*>(cookie);
1121 
1122     if (MEDIA_INFO == msg &&
1123         MEDIA_INFO_METADATA_UPDATE == ext1) {
1124         const media::Metadata::Type metadata_type = ext2;
1125 
1126         if(client->shouldDropMetadata(metadata_type)) {
1127             return;
1128         }
1129 
1130         // Update the list of metadata that have changed. getMetadata
1131         // also access mMetadataUpdated and clears it.
1132         client->addNewMetadataUpdate(metadata_type);
1133     }
1134     LOGV("[%d] notify (%p, %d, %d, %d)", client->mConnId, cookie, msg, ext1, ext2);
1135     client->mClient->notify(msg, ext1, ext2);
1136 }
1137 
1138 
shouldDropMetadata(media::Metadata::Type code) const1139 bool MediaPlayerService::Client::shouldDropMetadata(media::Metadata::Type code) const
1140 {
1141     Mutex::Autolock lock(mLock);
1142 
1143     if (findMetadata(mMetadataDrop, code)) {
1144         return true;
1145     }
1146 
1147     if (mMetadataAllow.isEmpty() || findMetadata(mMetadataAllow, code)) {
1148         return false;
1149     } else {
1150         return true;
1151     }
1152 }
1153 
1154 
addNewMetadataUpdate(media::Metadata::Type metadata_type)1155 void MediaPlayerService::Client::addNewMetadataUpdate(media::Metadata::Type metadata_type) {
1156     Mutex::Autolock lock(mLock);
1157     if (mMetadataUpdated.indexOf(metadata_type) < 0) {
1158         mMetadataUpdated.add(metadata_type);
1159     }
1160 }
1161 
1162 #if CALLBACK_ANTAGONIZER
1163 const int Antagonizer::interval = 10000; // 10 msecs
1164 
Antagonizer(notify_callback_f cb,void * client)1165 Antagonizer::Antagonizer(notify_callback_f cb, void* client) :
1166     mExit(false), mActive(false), mClient(client), mCb(cb)
1167 {
1168     createThread(callbackThread, this);
1169 }
1170 
kill()1171 void Antagonizer::kill()
1172 {
1173     Mutex::Autolock _l(mLock);
1174     mActive = false;
1175     mExit = true;
1176     mCondition.wait(mLock);
1177 }
1178 
callbackThread(void * user)1179 int Antagonizer::callbackThread(void* user)
1180 {
1181     LOGD("Antagonizer started");
1182     Antagonizer* p = reinterpret_cast<Antagonizer*>(user);
1183     while (!p->mExit) {
1184         if (p->mActive) {
1185             LOGV("send event");
1186             p->mCb(p->mClient, 0, 0, 0);
1187         }
1188         usleep(interval);
1189     }
1190     Mutex::Autolock _l(p->mLock);
1191     p->mCondition.signal();
1192     LOGD("Antagonizer stopped");
1193     return 0;
1194 }
1195 #endif
1196 
1197 static size_t kDefaultHeapSize = 1024 * 1024; // 1MB
1198 
decode(const char * url,uint32_t * pSampleRate,int * pNumChannels,int * pFormat)1199 sp<IMemory> MediaPlayerService::decode(const char* url, uint32_t *pSampleRate, int* pNumChannels, int* pFormat)
1200 {
1201     LOGV("decode(%s)", url);
1202     sp<MemoryBase> mem;
1203     sp<MediaPlayerBase> player;
1204 
1205     // Protect our precious, precious DRMd ringtones by only allowing
1206     // decoding of http, but not filesystem paths or content Uris.
1207     // If the application wants to decode those, it should open a
1208     // filedescriptor for them and use that.
1209     if (url != NULL && strncmp(url, "http://", 7) != 0) {
1210         LOGD("Can't decode %s by path, use filedescriptor instead", url);
1211         return mem;
1212     }
1213 
1214     player_type playerType = getPlayerType(url);
1215     LOGV("player type = %d", playerType);
1216 
1217     // create the right type of player
1218     sp<AudioCache> cache = new AudioCache(url);
1219     player = android::createPlayer(playerType, cache.get(), cache->notify);
1220     if (player == NULL) goto Exit;
1221     if (player->hardwareOutput()) goto Exit;
1222 
1223     static_cast<MediaPlayerInterface*>(player.get())->setAudioSink(cache);
1224 
1225     // set data source
1226     if (player->setDataSource(url) != NO_ERROR) goto Exit;
1227 
1228     LOGV("prepare");
1229     player->prepareAsync();
1230 
1231     LOGV("wait for prepare");
1232     if (cache->wait() != NO_ERROR) goto Exit;
1233 
1234     LOGV("start");
1235     player->start();
1236 
1237     LOGV("wait for playback complete");
1238     if (cache->wait() != NO_ERROR) goto Exit;
1239 
1240     mem = new MemoryBase(cache->getHeap(), 0, cache->size());
1241     *pSampleRate = cache->sampleRate();
1242     *pNumChannels = cache->channelCount();
1243     *pFormat = cache->format();
1244     LOGV("return memory @ %p, sampleRate=%u, channelCount = %d, format = %d", mem->pointer(), *pSampleRate, *pNumChannels, *pFormat);
1245 
1246 Exit:
1247     if (player != 0) player->reset();
1248     return mem;
1249 }
1250 
decode(int fd,int64_t offset,int64_t length,uint32_t * pSampleRate,int * pNumChannels,int * pFormat)1251 sp<IMemory> MediaPlayerService::decode(int fd, int64_t offset, int64_t length, uint32_t *pSampleRate, int* pNumChannels, int* pFormat)
1252 {
1253     LOGV("decode(%d, %lld, %lld)", fd, offset, length);
1254     sp<MemoryBase> mem;
1255     sp<MediaPlayerBase> player;
1256 
1257     player_type playerType = getPlayerType(fd, offset, length);
1258     LOGV("player type = %d", playerType);
1259 
1260     // create the right type of player
1261     sp<AudioCache> cache = new AudioCache("decode_fd");
1262     player = android::createPlayer(playerType, cache.get(), cache->notify);
1263     if (player == NULL) goto Exit;
1264     if (player->hardwareOutput()) goto Exit;
1265 
1266     static_cast<MediaPlayerInterface*>(player.get())->setAudioSink(cache);
1267 
1268     // set data source
1269     if (player->setDataSource(fd, offset, length) != NO_ERROR) goto Exit;
1270 
1271     LOGV("prepare");
1272     player->prepareAsync();
1273 
1274     LOGV("wait for prepare");
1275     if (cache->wait() != NO_ERROR) goto Exit;
1276 
1277     LOGV("start");
1278     player->start();
1279 
1280     LOGV("wait for playback complete");
1281     if (cache->wait() != NO_ERROR) goto Exit;
1282 
1283     mem = new MemoryBase(cache->getHeap(), 0, cache->size());
1284     *pSampleRate = cache->sampleRate();
1285     *pNumChannels = cache->channelCount();
1286     *pFormat = cache->format();
1287     LOGV("return memory @ %p, sampleRate=%u, channelCount = %d, format = %d", mem->pointer(), *pSampleRate, *pNumChannels, *pFormat);
1288 
1289 Exit:
1290     if (player != 0) player->reset();
1291     ::close(fd);
1292     return mem;
1293 }
1294 
1295 
1296 #undef LOG_TAG
1297 #define LOG_TAG "AudioSink"
AudioOutput(int sessionId)1298 MediaPlayerService::AudioOutput::AudioOutput(int sessionId)
1299     : mCallback(NULL),
1300       mCallbackCookie(NULL),
1301       mSessionId(sessionId) {
1302     LOGV("AudioOutput(%d)", sessionId);
1303     mTrack = 0;
1304     mStreamType = AudioSystem::MUSIC;
1305     mLeftVolume = 1.0;
1306     mRightVolume = 1.0;
1307     mLatency = 0;
1308     mMsecsPerFrame = 0;
1309     mAuxEffectId = 0;
1310     mSendLevel = 0.0;
1311     setMinBufferCount();
1312 }
1313 
~AudioOutput()1314 MediaPlayerService::AudioOutput::~AudioOutput()
1315 {
1316     close();
1317 }
1318 
setMinBufferCount()1319 void MediaPlayerService::AudioOutput::setMinBufferCount()
1320 {
1321     char value[PROPERTY_VALUE_MAX];
1322     if (property_get("ro.kernel.qemu", value, 0)) {
1323         mIsOnEmulator = true;
1324         mMinBufferCount = 12;  // to prevent systematic buffer underrun for emulator
1325     }
1326 }
1327 
isOnEmulator()1328 bool MediaPlayerService::AudioOutput::isOnEmulator()
1329 {
1330     setMinBufferCount();
1331     return mIsOnEmulator;
1332 }
1333 
getMinBufferCount()1334 int MediaPlayerService::AudioOutput::getMinBufferCount()
1335 {
1336     setMinBufferCount();
1337     return mMinBufferCount;
1338 }
1339 
bufferSize() const1340 ssize_t MediaPlayerService::AudioOutput::bufferSize() const
1341 {
1342     if (mTrack == 0) return NO_INIT;
1343     return mTrack->frameCount() * frameSize();
1344 }
1345 
frameCount() const1346 ssize_t MediaPlayerService::AudioOutput::frameCount() const
1347 {
1348     if (mTrack == 0) return NO_INIT;
1349     return mTrack->frameCount();
1350 }
1351 
channelCount() const1352 ssize_t MediaPlayerService::AudioOutput::channelCount() const
1353 {
1354     if (mTrack == 0) return NO_INIT;
1355     return mTrack->channelCount();
1356 }
1357 
frameSize() const1358 ssize_t MediaPlayerService::AudioOutput::frameSize() const
1359 {
1360     if (mTrack == 0) return NO_INIT;
1361     return mTrack->frameSize();
1362 }
1363 
latency() const1364 uint32_t MediaPlayerService::AudioOutput::latency () const
1365 {
1366     return mLatency;
1367 }
1368 
msecsPerFrame() const1369 float MediaPlayerService::AudioOutput::msecsPerFrame() const
1370 {
1371     return mMsecsPerFrame;
1372 }
1373 
getPosition(uint32_t * position)1374 status_t MediaPlayerService::AudioOutput::getPosition(uint32_t *position)
1375 {
1376     if (mTrack == 0) return NO_INIT;
1377     return mTrack->getPosition(position);
1378 }
1379 
open(uint32_t sampleRate,int channelCount,int format,int bufferCount,AudioCallback cb,void * cookie)1380 status_t MediaPlayerService::AudioOutput::open(
1381         uint32_t sampleRate, int channelCount, int format, int bufferCount,
1382         AudioCallback cb, void *cookie)
1383 {
1384     mCallback = cb;
1385     mCallbackCookie = cookie;
1386 
1387     // Check argument "bufferCount" against the mininum buffer count
1388     if (bufferCount < mMinBufferCount) {
1389         LOGD("bufferCount (%d) is too small and increased to %d", bufferCount, mMinBufferCount);
1390         bufferCount = mMinBufferCount;
1391 
1392     }
1393     LOGV("open(%u, %d, %d, %d, %d)", sampleRate, channelCount, format, bufferCount,mSessionId);
1394     if (mTrack) close();
1395     int afSampleRate;
1396     int afFrameCount;
1397     int frameCount;
1398 
1399     if (AudioSystem::getOutputFrameCount(&afFrameCount, mStreamType) != NO_ERROR) {
1400         return NO_INIT;
1401     }
1402     if (AudioSystem::getOutputSamplingRate(&afSampleRate, mStreamType) != NO_ERROR) {
1403         return NO_INIT;
1404     }
1405 
1406     frameCount = (sampleRate*afFrameCount*bufferCount)/afSampleRate;
1407 
1408     AudioTrack *t;
1409     if (mCallback != NULL) {
1410         t = new AudioTrack(
1411                 mStreamType,
1412                 sampleRate,
1413                 format,
1414                 (channelCount == 2) ? AudioSystem::CHANNEL_OUT_STEREO : AudioSystem::CHANNEL_OUT_MONO,
1415                 frameCount,
1416                 0 /* flags */,
1417                 CallbackWrapper,
1418                 this,
1419                 0,
1420                 mSessionId);
1421     } else {
1422         t = new AudioTrack(
1423                 mStreamType,
1424                 sampleRate,
1425                 format,
1426                 (channelCount == 2) ? AudioSystem::CHANNEL_OUT_STEREO : AudioSystem::CHANNEL_OUT_MONO,
1427                 frameCount,
1428                 0,
1429                 NULL,
1430                 NULL,
1431                 0,
1432                 mSessionId);
1433     }
1434 
1435     if ((t == 0) || (t->initCheck() != NO_ERROR)) {
1436         LOGE("Unable to create audio track");
1437         delete t;
1438         return NO_INIT;
1439     }
1440 
1441     LOGV("setVolume");
1442     t->setVolume(mLeftVolume, mRightVolume);
1443 
1444     mMsecsPerFrame = 1.e3 / (float) sampleRate;
1445     mLatency = t->latency();
1446     mTrack = t;
1447 
1448     t->setAuxEffectSendLevel(mSendLevel);
1449     return t->attachAuxEffect(mAuxEffectId);;
1450 }
1451 
start()1452 void MediaPlayerService::AudioOutput::start()
1453 {
1454     LOGV("start");
1455     if (mTrack) {
1456         mTrack->setVolume(mLeftVolume, mRightVolume);
1457         mTrack->setAuxEffectSendLevel(mSendLevel);
1458         mTrack->start();
1459     }
1460 }
1461 
1462 
1463 
write(const void * buffer,size_t size)1464 ssize_t MediaPlayerService::AudioOutput::write(const void* buffer, size_t size)
1465 {
1466     LOG_FATAL_IF(mCallback != NULL, "Don't call write if supplying a callback.");
1467 
1468     //LOGV("write(%p, %u)", buffer, size);
1469     if (mTrack) {
1470         ssize_t ret = mTrack->write(buffer, size);
1471         return ret;
1472     }
1473     return NO_INIT;
1474 }
1475 
stop()1476 void MediaPlayerService::AudioOutput::stop()
1477 {
1478     LOGV("stop");
1479     if (mTrack) mTrack->stop();
1480 }
1481 
flush()1482 void MediaPlayerService::AudioOutput::flush()
1483 {
1484     LOGV("flush");
1485     if (mTrack) mTrack->flush();
1486 }
1487 
pause()1488 void MediaPlayerService::AudioOutput::pause()
1489 {
1490     LOGV("pause");
1491     if (mTrack) mTrack->pause();
1492 }
1493 
close()1494 void MediaPlayerService::AudioOutput::close()
1495 {
1496     LOGV("close");
1497     delete mTrack;
1498     mTrack = 0;
1499 }
1500 
setVolume(float left,float right)1501 void MediaPlayerService::AudioOutput::setVolume(float left, float right)
1502 {
1503     LOGV("setVolume(%f, %f)", left, right);
1504     mLeftVolume = left;
1505     mRightVolume = right;
1506     if (mTrack) {
1507         mTrack->setVolume(left, right);
1508     }
1509 }
1510 
setAuxEffectSendLevel(float level)1511 status_t MediaPlayerService::AudioOutput::setAuxEffectSendLevel(float level)
1512 {
1513     LOGV("setAuxEffectSendLevel(%f)", level);
1514     mSendLevel = level;
1515     if (mTrack) {
1516         return mTrack->setAuxEffectSendLevel(level);
1517     }
1518     return NO_ERROR;
1519 }
1520 
attachAuxEffect(int effectId)1521 status_t MediaPlayerService::AudioOutput::attachAuxEffect(int effectId)
1522 {
1523     LOGV("attachAuxEffect(%d)", effectId);
1524     mAuxEffectId = effectId;
1525     if (mTrack) {
1526         return mTrack->attachAuxEffect(effectId);
1527     }
1528     return NO_ERROR;
1529 }
1530 
1531 // static
CallbackWrapper(int event,void * cookie,void * info)1532 void MediaPlayerService::AudioOutput::CallbackWrapper(
1533         int event, void *cookie, void *info) {
1534     //LOGV("callbackwrapper");
1535     if (event != AudioTrack::EVENT_MORE_DATA) {
1536         return;
1537     }
1538 
1539     AudioOutput *me = (AudioOutput *)cookie;
1540     AudioTrack::Buffer *buffer = (AudioTrack::Buffer *)info;
1541 
1542     size_t actualSize = (*me->mCallback)(
1543             me, buffer->raw, buffer->size, me->mCallbackCookie);
1544 
1545     buffer->size = actualSize;
1546 
1547 }
1548 
getSessionId()1549 int MediaPlayerService::AudioOutput::getSessionId()
1550 {
1551     return mSessionId;
1552 }
1553 
1554 #undef LOG_TAG
1555 #define LOG_TAG "AudioCache"
AudioCache(const char * name)1556 MediaPlayerService::AudioCache::AudioCache(const char* name) :
1557     mChannelCount(0), mFrameCount(1024), mSampleRate(0), mSize(0),
1558     mError(NO_ERROR), mCommandComplete(false)
1559 {
1560     // create ashmem heap
1561     mHeap = new MemoryHeapBase(kDefaultHeapSize, 0, name);
1562 }
1563 
latency() const1564 uint32_t MediaPlayerService::AudioCache::latency () const
1565 {
1566     return 0;
1567 }
1568 
msecsPerFrame() const1569 float MediaPlayerService::AudioCache::msecsPerFrame() const
1570 {
1571     return mMsecsPerFrame;
1572 }
1573 
getPosition(uint32_t * position)1574 status_t MediaPlayerService::AudioCache::getPosition(uint32_t *position)
1575 {
1576     if (position == 0) return BAD_VALUE;
1577     *position = mSize;
1578     return NO_ERROR;
1579 }
1580 
1581 ////////////////////////////////////////////////////////////////////////////////
1582 
1583 struct CallbackThread : public Thread {
1584     CallbackThread(const wp<MediaPlayerBase::AudioSink> &sink,
1585                    MediaPlayerBase::AudioSink::AudioCallback cb,
1586                    void *cookie);
1587 
1588 protected:
1589     virtual ~CallbackThread();
1590 
1591     virtual bool threadLoop();
1592 
1593 private:
1594     wp<MediaPlayerBase::AudioSink> mSink;
1595     MediaPlayerBase::AudioSink::AudioCallback mCallback;
1596     void *mCookie;
1597     void *mBuffer;
1598     size_t mBufferSize;
1599 
1600     CallbackThread(const CallbackThread &);
1601     CallbackThread &operator=(const CallbackThread &);
1602 };
1603 
CallbackThread(const wp<MediaPlayerBase::AudioSink> & sink,MediaPlayerBase::AudioSink::AudioCallback cb,void * cookie)1604 CallbackThread::CallbackThread(
1605         const wp<MediaPlayerBase::AudioSink> &sink,
1606         MediaPlayerBase::AudioSink::AudioCallback cb,
1607         void *cookie)
1608     : mSink(sink),
1609       mCallback(cb),
1610       mCookie(cookie),
1611       mBuffer(NULL),
1612       mBufferSize(0) {
1613 }
1614 
~CallbackThread()1615 CallbackThread::~CallbackThread() {
1616     if (mBuffer) {
1617         free(mBuffer);
1618         mBuffer = NULL;
1619     }
1620 }
1621 
threadLoop()1622 bool CallbackThread::threadLoop() {
1623     sp<MediaPlayerBase::AudioSink> sink = mSink.promote();
1624     if (sink == NULL) {
1625         return false;
1626     }
1627 
1628     if (mBuffer == NULL) {
1629         mBufferSize = sink->bufferSize();
1630         mBuffer = malloc(mBufferSize);
1631     }
1632 
1633     size_t actualSize =
1634         (*mCallback)(sink.get(), mBuffer, mBufferSize, mCookie);
1635 
1636     if (actualSize > 0) {
1637         sink->write(mBuffer, actualSize);
1638     }
1639 
1640     return true;
1641 }
1642 
1643 ////////////////////////////////////////////////////////////////////////////////
1644 
open(uint32_t sampleRate,int channelCount,int format,int bufferCount,AudioCallback cb,void * cookie)1645 status_t MediaPlayerService::AudioCache::open(
1646         uint32_t sampleRate, int channelCount, int format, int bufferCount,
1647         AudioCallback cb, void *cookie)
1648 {
1649     LOGV("open(%u, %d, %d, %d)", sampleRate, channelCount, format, bufferCount);
1650     if (mHeap->getHeapID() < 0) {
1651         return NO_INIT;
1652     }
1653 
1654     mSampleRate = sampleRate;
1655     mChannelCount = (uint16_t)channelCount;
1656     mFormat = (uint16_t)format;
1657     mMsecsPerFrame = 1.e3 / (float) sampleRate;
1658 
1659     if (cb != NULL) {
1660         mCallbackThread = new CallbackThread(this, cb, cookie);
1661     }
1662     return NO_ERROR;
1663 }
1664 
start()1665 void MediaPlayerService::AudioCache::start() {
1666     if (mCallbackThread != NULL) {
1667         mCallbackThread->run("AudioCache callback");
1668     }
1669 }
1670 
stop()1671 void MediaPlayerService::AudioCache::stop() {
1672     if (mCallbackThread != NULL) {
1673         mCallbackThread->requestExitAndWait();
1674     }
1675 }
1676 
write(const void * buffer,size_t size)1677 ssize_t MediaPlayerService::AudioCache::write(const void* buffer, size_t size)
1678 {
1679     LOGV("write(%p, %u)", buffer, size);
1680     if ((buffer == 0) || (size == 0)) return size;
1681 
1682     uint8_t* p = static_cast<uint8_t*>(mHeap->getBase());
1683     if (p == NULL) return NO_INIT;
1684     p += mSize;
1685     LOGV("memcpy(%p, %p, %u)", p, buffer, size);
1686     if (mSize + size > mHeap->getSize()) {
1687         LOGE("Heap size overflow! req size: %d, max size: %d", (mSize + size), mHeap->getSize());
1688         size = mHeap->getSize() - mSize;
1689     }
1690     memcpy(p, buffer, size);
1691     mSize += size;
1692     return size;
1693 }
1694 
1695 // call with lock held
wait()1696 status_t MediaPlayerService::AudioCache::wait()
1697 {
1698     Mutex::Autolock lock(mLock);
1699     while (!mCommandComplete) {
1700         mSignal.wait(mLock);
1701     }
1702     mCommandComplete = false;
1703 
1704     if (mError == NO_ERROR) {
1705         LOGV("wait - success");
1706     } else {
1707         LOGV("wait - error");
1708     }
1709     return mError;
1710 }
1711 
notify(void * cookie,int msg,int ext1,int ext2)1712 void MediaPlayerService::AudioCache::notify(void* cookie, int msg, int ext1, int ext2)
1713 {
1714     LOGV("notify(%p, %d, %d, %d)", cookie, msg, ext1, ext2);
1715     AudioCache* p = static_cast<AudioCache*>(cookie);
1716 
1717     // ignore buffering messages
1718     switch (msg)
1719     {
1720     case MEDIA_ERROR:
1721         LOGE("Error %d, %d occurred", ext1, ext2);
1722         p->mError = ext1;
1723         break;
1724     case MEDIA_PREPARED:
1725         LOGV("prepared");
1726         break;
1727     case MEDIA_PLAYBACK_COMPLETE:
1728         LOGV("playback complete");
1729         break;
1730     default:
1731         LOGV("ignored");
1732         return;
1733     }
1734 
1735     // wake up thread
1736     Mutex::Autolock lock(p->mLock);
1737     p->mCommandComplete = true;
1738     p->mSignal.signal();
1739 }
1740 
getSessionId()1741 int MediaPlayerService::AudioCache::getSessionId()
1742 {
1743     return 0;
1744 }
1745 
1746 } // namespace android
1747