Adds tests for Variable Speed code.

The test changes:
- Adds many, many test cases against a MediaPlayerProxy, checking that
  it behaves to the contract of a MediaPlayer.
- Adds the RealMediaPlayer class to check a real MediaPlayer.
- Adds the VariableSpeed class, to check a VariableSpeed instance
  against the same contract as the MediaPlayer.
- Adds an Android.mk for the unit tests.
- Adds also an AndroidManifest.xml for the unit tests.
- Adds some test asset media files (3gpp file and mp3 file).

Required for the test changes:
- Adds a DynamicProxy class to adapt a MediaPlayer as a
  MediaPlayerProxy class, i.e. to test the implementation of
  MediaPlayerProxy, required to avoid writing an adapter.
- Adds a couple of listeners, OnErrorListener and
  OnCompletionListener, that can be waited for synchronously in unit
  tests.

Improvements as a result of the tests:
- During the testing, fixes the case where we weren't throwing
  IllegalStateException if asked for the duration on released player.
- Refactored the create engine, create and realize output mix, create
  and realize audio player, get play interfaces and callbacks, all
  separated into their own static methods.
- This allows me to create the audio player during the main while loop
  actually after the decoding has begun rather than before starting.
  This work is a precursor to using the decoder's report on sample rate
  and channels as the input to these methods.
- slSampleRate and slOutputChannels no longer computed in the
  constructor, but computed when needed in the construction and
  realization of the audio player.

Other changes:
- Remove some overly verbose logs on getDuration() and
  getCurrentPosition().
- Adding the decoder interface to the callback.
- Extract metadata from decoder method now takes the metadata
  interface, so this will be usable from the decoder callack in a follow
  up.
- Temporarily stop getting the metadata out of the decoder, I'm going
  to be doing it on the decoding callback instead.
- Renames the comment in AndroidManifest.xml to describe the
  correct invocation to run the common tests.

Bug: 5048252
Bug: 5048257
Change-Id: Icdc18b19ef89c9924f73128b70aa4696b4e727c5
diff --git a/variablespeed/jni/variablespeed.cc b/variablespeed/jni/variablespeed.cc
index 49eddbe..bf99c4d 100644
--- a/variablespeed/jni/variablespeed.cc
+++ b/variablespeed/jni/variablespeed.cc
@@ -58,7 +58,7 @@
 
 // Structure used when we perform a decoding callback.
 typedef struct CallbackContext_ {
-    SLPlayItf decoderPlay;
+    SLMetadataExtractionItf decoderMetadata;
     // Pointer to local storage buffers for decoded audio data.
     int8_t* pDataBase;
     // Pointer to the current buffer within local storage.
@@ -161,13 +161,11 @@
   CheckSLResult("stop playing", result);
 }
 
-static void ExtractMetadataFromDecoder(SLObjectItf decoder) {
-  SLMetadataExtractionItf decoderMetadata;
-  SLresult result = (*decoder)->GetInterface(decoder,
-      SL_IID_METADATAEXTRACTION, &decoderMetadata);
-  CheckSLResult("getting metadata interface", result);
+static void ExtractMetadataFromDecoder(
+    SLMetadataExtractionItf decoderMetadata) {
   SLuint32 itemCount;
-  result = (*decoderMetadata)->GetItemCount(decoderMetadata, &itemCount);
+  SLresult result = (*decoderMetadata)->GetItemCount(
+      decoderMetadata, &itemCount);
   CheckSLResult("getting item count", result);
   SLuint32 i, keySize, valueSize;
   SLMetadataInfo *keyInfo, *value;
@@ -213,32 +211,31 @@
 }
 
 static void RegisterCallbackContextAndAddEnqueueBuffersToDecoder(
-    SLAndroidSimpleBufferQueueItf decoderQueue, SLPlayItf player,
-    android::Mutex &callbackLock) {
+    SLAndroidSimpleBufferQueueItf decoderQueue,
+    SLMetadataExtractionItf decoderMetadata, android::Mutex &callbackLock,
+    CallbackContext* context) {
   android::Mutex::Autolock autoLock(callbackLock);
   // Initialize the callback structure, used during the decoding.
   // Then register a callback on the decoder queue, so that we will be called
   // throughout the decoding process (and can then extract the decoded audio
   // for the next bit of the pipeline).
-  CallbackContext cntxt;
-  cntxt.decoderPlay = player;
-  cntxt.pDataBase = pcmData;
-  cntxt.pData = pcmData;
-  {
-    SLresult result = (*decoderQueue)->RegisterCallback(
-        decoderQueue, DecodingBufferQueueCb, &cntxt);
-    CheckSLResult("decode callback", result);
-  }
+  context->decoderMetadata = decoderMetadata;
+  context->pDataBase = pcmData;
+  context->pData = pcmData;
+
+  SLresult result = (*decoderQueue)->RegisterCallback(
+      decoderQueue, DecodingBufferQueueCb, context);
+  CheckSLResult("decode callback", result);
 
   // Enqueue buffers to map the region of memory allocated to store the
   // decoded data.
   for (size_t i = 0; i < kNumberOfBuffersInQueue; i++) {
     SLresult result = (*decoderQueue)->Enqueue(
-        decoderQueue, cntxt.pData, kBufferSizeInBytes);
+        decoderQueue, context->pData, kBufferSizeInBytes);
     CheckSLResult("enqueue something", result);
-    cntxt.pData += kBufferSizeInBytes;
+    context->pData += kBufferSizeInBytes;
   }
-  cntxt.pData = cntxt.pDataBase;
+  context->pData = context->pDataBase;
 }
 
 // ****************************************************************************
@@ -251,8 +248,7 @@
     : decodeBuffer_(decodeInitialSize, decodeMaxSize),
       playingBuffers_(), freeBuffers_(), timeScaler_(NULL),
       floatBuffer_(NULL), injectBuffer_(NULL),
-      channels_(channels), sampleRate_(sampleRate), slSampleRate_(0),
-      slOutputChannels_(0),
+      channels_(channels), sampleRate_(sampleRate),
       targetFrames_(targetFrames),
       windowDuration_(windowDuration),
       windowOverlapDuration_(windowOverlapDuration),
@@ -260,23 +256,8 @@
       startPositionMillis_(startPositionMillis),
       totalDurationMs_(0), startRequested_(false),
       stopRequested_(false), finishedDecoding_(false) {
-  if (sampleRate_ == 44100) {
-    slSampleRate_ = SL_SAMPLINGRATE_44_1;
-  } else if (sampleRate_ == 8000) {
-    slSampleRate_ = SL_SAMPLINGRATE_8;
-  } else if (sampleRate_ == 11025) {
-    slSampleRate_ = SL_SAMPLINGRATE_11_025;
-  } else {
-    LOGE("unknown sample rate, not changing");
-    CHECK(false);
-  }
-  if (channels_ == 2) {
-    slOutputChannels_ = SL_SPEAKER_FRONT_LEFT | SL_SPEAKER_FRONT_RIGHT;
-  } else if (channels_ == 1) {
-    slOutputChannels_ = SL_SPEAKER_FRONT_LEFT;
-  } else {
-    LOGE("unknown channels, not changing");
-  }
+  floatBuffer_ = new float[targetFrames_ * channels_];
+  injectBuffer_ = new float[targetFrames_ * channels_];
 }
 
 AudioEngine::~AudioEngine() {
@@ -357,7 +338,6 @@
   PausePlaying(playItf);
 
   // Wait until the data has been prefetched.
-  // TODO(hugohudson): 0. Not dealing with error just yet.
   {
     SLuint32 prefetchStatus = SL_PREFETCHSTATUS_UNDERFLOW;
     android::Mutex::Autolock autoLock(prefetchLock_);
@@ -501,38 +481,70 @@
   decodeBuffer_.Clear();
 }
 
-bool AudioEngine::PlayFromThisSource(const SLDataSource& audioSrc) {
-  ClearDecodeBuffer();
-  floatBuffer_ = new float[targetFrames_ * channels_];
-  injectBuffer_ = new float[targetFrames_ * channels_];
-
-  // Create the engine.
+static void CreateAndRealizeEngine(SLObjectItf &engine,
+    SLEngineItf &engineInterface) {
   SLEngineOption EngineOption[] = { {
       SL_ENGINEOPTION_THREADSAFE, SL_BOOLEAN_TRUE } };
-  SLObjectItf engine;
   SLresult result = slCreateEngine(&engine, 1, EngineOption, 0, NULL, NULL);
   CheckSLResult("create engine", result);
   result = (*engine)->Realize(engine, SL_BOOLEAN_FALSE);
   CheckSLResult("realise engine", result);
-  SLEngineItf engineInterface;
   result = (*engine)->GetInterface(engine, SL_IID_ENGINE, &engineInterface);
   CheckSLResult("get interface", result);
+}
 
+static void CreateAndRealizeOutputMix(SLEngineItf &engineInterface,
+    SLObjectItf &outputMix) {
+  SLresult result;
   // Create the output mix for playing.
-  SLObjectItf outputMix;
   result = (*engineInterface)->CreateOutputMix(
       engineInterface, &outputMix, 0, NULL, NULL);
   CheckSLResult("create output mix", result);
   result = (*outputMix)->Realize(outputMix, SL_BOOLEAN_FALSE);
   CheckSLResult("realize", result);
+}
+
+static void CreateAndRealizeAudioPlayer(size_t sampleRate, size_t channels,
+    SLObjectItf &outputMix, SLObjectItf &audioPlayer,
+    SLEngineItf &engineInterface) {
+  SLresult result;
+  SLuint32 slSampleRate;
+  SLuint32 slOutputChannels;
+  switch (sampleRate) {
+    case 44100:
+      slSampleRate = SL_SAMPLINGRATE_44_1;
+      break;
+    case 8000:
+      slSampleRate = SL_SAMPLINGRATE_8;
+      break;
+    case 11025:
+      slSampleRate = SL_SAMPLINGRATE_11_025;
+      break;
+    default:
+      LOGE("unknown sample rate, using SL_SAMPLINGRATE_44_1");
+      slSampleRate = SL_SAMPLINGRATE_44_1;
+      break;
+  }
+  switch (channels) {
+    case 2:
+      slOutputChannels = SL_SPEAKER_FRONT_LEFT | SL_SPEAKER_FRONT_RIGHT;
+      break;
+    case 1:
+      slOutputChannels = SL_SPEAKER_FRONT_LEFT;
+      break;
+    default:
+      LOGE("unknown channels, using 2");
+      slOutputChannels = SL_SPEAKER_FRONT_LEFT | SL_SPEAKER_FRONT_RIGHT;
+      break;
+  }
 
   // Define the source and sink for the audio player: comes from a buffer queue
   // and goes to the output mix.
   SLDataLocator_AndroidSimpleBufferQueue loc_bufq = {
       SL_DATALOCATOR_ANDROIDSIMPLEBUFFERQUEUE, 2 };
-  SLDataFormat_PCM format_pcm = {SL_DATAFORMAT_PCM, channels_, slSampleRate_,
+  SLDataFormat_PCM format_pcm = {SL_DATAFORMAT_PCM, channels, slSampleRate,
       SL_PCMSAMPLEFORMAT_FIXED_16, SL_PCMSAMPLEFORMAT_FIXED_16,
-      slOutputChannels_, SL_BYTEORDER_LITTLEENDIAN};
+      slOutputChannels, SL_BYTEORDER_LITTLEENDIAN};
   SLDataSource playingSrc = {&loc_bufq, &format_pcm};
   SLDataLocator_OutputMix loc_outmix = {SL_DATALOCATOR_OUTPUTMIX, outputMix};
   SLDataSink audioSnk = {&loc_outmix, NULL};
@@ -543,27 +555,39 @@
   const SLInterfaceID iids[playerInterfaceCount] = {
       SL_IID_ANDROIDSIMPLEBUFFERQUEUE };
   const SLboolean reqs[playerInterfaceCount] = { SL_BOOLEAN_TRUE };
-  SLObjectItf audioPlayer;
   result = (*engineInterface)->CreateAudioPlayer(engineInterface, &audioPlayer,
       &playingSrc, &audioSnk, playerInterfaceCount, iids, reqs);
   CheckSLResult("create audio player", result);
   result = (*audioPlayer)->Realize(audioPlayer, SL_BOOLEAN_FALSE);
   CheckSLResult("realize buffer queue", result);
+}
 
+static void GetAudioPlayInterfacesAndRegisterCallback(SLObjectItf &audioPlayer,
+    SLPlayItf &audioPlayerPlay,
+    SLAndroidSimpleBufferQueueItf &audioPlayerQueue) {
+  SLresult result;
   // Get the play interface from the player, as well as the buffer queue
   // interface from its source.
   // Register for callbacks during play.
-  SLPlayItf audioPlayerPlay;
   result = (*audioPlayer)->GetInterface(
       audioPlayer, SL_IID_PLAY, &audioPlayerPlay);
   CheckSLResult("get interface", result);
-  SLAndroidSimpleBufferQueueItf audioPlayerQueue;
   result = (*audioPlayer)->GetInterface(audioPlayer,
       SL_IID_ANDROIDSIMPLEBUFFERQUEUE, &audioPlayerQueue);
   CheckSLResult("get interface again", result);
   result = (*audioPlayerQueue)->RegisterCallback(
       audioPlayerQueue, PlayingBufferQueueCb, NULL);
   CheckSLResult("register callback", result);
+}
+
+bool AudioEngine::PlayFromThisSource(const SLDataSource& audioSrc) {
+  ClearDecodeBuffer();
+
+  SLresult result;
+
+  SLObjectItf engine;
+  SLEngineItf engineInterface;
+  CreateAndRealizeEngine(engine, engineInterface);
 
   // Define the source and sink for the decoding player: comes from the source
   // this method was called with, is sent to another buffer queue.
@@ -571,7 +595,7 @@
   decBuffQueue.locatorType = SL_DATALOCATOR_ANDROIDSIMPLEBUFFERQUEUE;
   decBuffQueue.numBuffers = kNumberOfBuffersInQueue;
   // A valid value seems required here but is currently ignored.
-  SLDataFormat_PCM pcm = {SL_DATAFORMAT_PCM, 1, slSampleRate_,
+  SLDataFormat_PCM pcm = {SL_DATAFORMAT_PCM, 1, SL_SAMPLINGRATE_44_1,
       SL_PCMSAMPLEFORMAT_FIXED_16, 16,
       SL_SPEAKER_FRONT_LEFT, SL_BYTEORDER_LITTLEENDIAN};
   SLDataSink decDest = { &decBuffQueue, &pcm };
@@ -594,7 +618,7 @@
 
   // Get the play interface from the decoder, and register event callbacks.
   // Get the buffer queue, prefetch and seek interfaces.
-  SLPlayItf decoderPlay;
+  SLPlayItf decoderPlay = NULL;
   result = (*decoder)->GetInterface(decoder, SL_IID_PLAY, &decoderPlay);
   CheckSLResult("get play interface, implicit", result);
   result = (*decoderPlay)->SetCallbackEventsMask(
@@ -615,8 +639,15 @@
   result = (*decoder)->GetInterface(decoder, SL_IID_SEEK, &decoderSeek);
   CheckSLResult("get seek interface", result);
 
+  // Get the metadata interface from the decoder.
+  SLMetadataExtractionItf decoderMetadata;
+  result = (*decoder)->GetInterface(decoder,
+      SL_IID_METADATAEXTRACTION, &decoderMetadata);
+  CheckSLResult("getting metadata interface", result);
+
+  CallbackContext callbackContext;
   RegisterCallbackContextAndAddEnqueueBuffersToDecoder(
-      decoderQueue, decoderPlay, callbackLock_);
+      decoderQueue, decoderMetadata, callbackLock_, &callbackContext);
 
   // Initialize the callback for prefetch errors, if we can't open the
   // resource to decode.
@@ -631,15 +662,23 @@
 
   PrefetchDurationSampleRateAndChannels(decoderPlay, decoderPrefetch);
 
-  ExtractMetadataFromDecoder(decoder);
-
   StartPlaying(decoderPlay);
 
+  SLObjectItf outputMix = NULL;
+  SLObjectItf audioPlayer = NULL;
+  SLPlayItf audioPlayerPlay = NULL;
+  SLAndroidSimpleBufferQueueItf audioPlayerQueue = NULL;
+
   // The main loop - until we're told to stop: if there is audio data coming
   // out of the decoder, feed it through the time scaler.
   // As it comes out of the time scaler, feed it into the audio player.
   while (!Finished()) {
     if (GetWasStartRequested()) {
+      CreateAndRealizeOutputMix(engineInterface, outputMix);
+      CreateAndRealizeAudioPlayer(sampleRate_, channels_, outputMix,
+          audioPlayer, engineInterface);
+      GetAudioPlayInterfacesAndRegisterCallback(audioPlayer, audioPlayerPlay,
+          audioPlayerQueue);
       ClearRequestStart();
       StartPlaying(audioPlayerPlay);
     }
@@ -647,23 +686,27 @@
     usleep(kSleepTimeMicros);
   }
 
-  StopPlaying(audioPlayerPlay);
-  StopPlaying(decoderPlay);
-
-  // Delete the audio player.
-  result = (*audioPlayerQueue)->Clear(audioPlayerQueue);
-  CheckSLResult("clear audio player queue", result);
-  result = (*audioPlayerQueue)->RegisterCallback(audioPlayerQueue, NULL, NULL);
-  CheckSLResult("clear callback", result);
-  (*audioPlayer)->AbortAsyncOperation(audioPlayer);
-  audioPlayerPlay = NULL;
-  audioPlayerQueue = NULL;
-  (*audioPlayer)->Destroy(audioPlayer);
+  // Delete the audio player and output mix, iff they have been created.
+  if (audioPlayer != NULL) {
+    StopPlaying(audioPlayerPlay);
+    result = (*audioPlayerQueue)->Clear(audioPlayerQueue);
+    CheckSLResult("clear audio player queue", result);
+    result = (*audioPlayerQueue)->RegisterCallback(audioPlayerQueue, NULL, NULL);
+    CheckSLResult("clear callback", result);
+    (*audioPlayer)->AbortAsyncOperation(audioPlayer);
+    (*audioPlayer)->Destroy(audioPlayer);
+    (*outputMix)->Destroy(outputMix);
+    audioPlayer = NULL;
+    audioPlayerPlay = NULL;
+    audioPlayerQueue = NULL;
+    outputMix = NULL;
+  }
 
   // Delete the decoder.
+  StopPlaying(decoderPlay);
   result = (*decoderPrefetch)->RegisterCallback(decoderPrefetch, NULL, NULL);
   CheckSLResult("clearing prefetch error callback", result);
-  // TODO(hugohudson): 0. This is returning slresult 13 if I do no playback.
+  // This is returning slresult 13 if I do no playback.
   // Repro is to comment out all before this line, and all after enqueueing
   // my buffers.
   // result = (*decoderQueue)->Clear(decoderQueue);
@@ -679,10 +722,9 @@
   decoderPlay = NULL;
   (*decoder)->Destroy(decoder);
 
-  // Delete the output mix, then the engine.
-  (*outputMix)->Destroy(outputMix);
-  engineInterface = NULL;
+  // Delete the engine.
   (*engine)->Destroy(engine);
+  engineInterface = NULL;
 
   return true;
 }
@@ -738,7 +780,6 @@
 void AudioEngine::PrefetchEventCallback(
     SLPrefetchStatusItf caller, SLuint32 event) {
   // If there was a problem during decoding, then signal the end.
-  LOGI("in the prefetch callback");
   SLpermille level = 0;
   SLresult result = (*caller)->GetFillLevel(caller, &level);
   CheckSLResult("get fill level", result);
@@ -752,10 +793,8 @@
     SetEndOfDecoderReached();
   }
   if (SL_PREFETCHSTATUS_SUFFICIENTDATA == event) {
-    LOGI("looks like our event...");
     // android::Mutex::Autolock autoLock(prefetchLock_);
     // prefetchCondition_.broadcast();
-    LOGI("just sent a broadcast");
   }
 }
 
@@ -775,6 +814,10 @@
     decodeBuffer_.AddData(pCntxt->pDataBase, kBufferSizeInBytes);
   }
 
+  // TODO: This call must be added back in to fix the bug relating to using
+  // the correct sample rate and channels.  I will do this in the follow-up.
+  // ExtractMetadataFromDecoder(pCntxt->decoderMetadata);
+
   // Increase data pointer by buffer size
   pCntxt->pData += kBufferSizeInBytes;
   if (pCntxt->pData >= pCntxt->pDataBase +