/**
 * Copyright (C) 2020 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#include <binder/IPCThreadState.h>
#include <binder/IServiceManager.h>
#include <media/AudioSystem.h>
#include "../includes/common.h"

using namespace android;

#define MAX_NUMBER_OF_AUDIO_SESSIONS 1024
#define MAX_NUMBER_OF_THREADS 5
#define MAX_NUMBER_OF_ACQUIRE_SESSION_THREADS 2

struct pocAudioSessionCtxt {
  audio_session_t audioSession[MAX_NUMBER_OF_AUDIO_SESSIONS];
  volatile bool startThread;
};

static void *acquireSoundTriggerSessionThread(void *arg) {
  int i = 0;
  pocAudioSessionCtxt *ctxt = (pocAudioSessionCtxt *)arg;
  if (!ctxt) {
    return nullptr;
  }
  time_t currentTime = start_timer();
  while (timer_active(currentTime)) {
      if (ctxt->startThread) {
          audio_io_handle_t ioHandle = 0;
          audio_devices_t device = AUDIO_DEVICE_NONE;
          AudioSystem::acquireSoundTriggerSession(&(ctxt->audioSession[++i]), &ioHandle, &device);
          if (i >= MAX_NUMBER_OF_AUDIO_SESSIONS) {
              i = 0;
          }
      }
  }
  return nullptr;
}

static void *releaseSoundTriggerSessionThread(void *arg) {
  int i = 0;
  pocAudioSessionCtxt *ctxt = (pocAudioSessionCtxt *)arg;
  if (!ctxt) {
    return nullptr;
  }
  time_t currentTime = start_timer();
  while (timer_active(currentTime)) {
      if (ctxt->startThread) {
          AudioSystem::releaseSoundTriggerSession(ctxt->audioSession[++i]);
          if (i >= MAX_NUMBER_OF_AUDIO_SESSIONS) {
              i = 0;
          }
      }
  }
  return nullptr;
}

int main() {
  pocAudioSessionCtxt ctxt;
  pthread_t thread[MAX_NUMBER_OF_THREADS];
  ctxt.startThread = false;

  for (int i = 0; i < MAX_NUMBER_OF_ACQUIRE_SESSION_THREADS; ++i) {
    pthread_create(&thread[i], nullptr, acquireSoundTriggerSessionThread,
                   &ctxt);
  }

  for (int i = MAX_NUMBER_OF_ACQUIRE_SESSION_THREADS; i < MAX_NUMBER_OF_THREADS;
       ++i) {
    pthread_create(&thread[i], nullptr, releaseSoundTriggerSessionThread,
                   &ctxt);
  }

  ctxt.startThread = true;
  for (int i = 0; i < MAX_NUMBER_OF_THREADS; ++i) {
    pthread_join(thread[i], nullptr);
  }
  return EXIT_SUCCESS;
}
