/*
 *  Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#include "modules/audio_processing/aecm/echo_control_mobile.h"

#include <cstdint>
#include <cstdlib>
#include <cstring>
#ifdef AEC_DEBUG
#include <cstdio>
#endif

#include "modules/audio_processing/aecm/aecm_core.h"

extern "C" {
#include "common_audio/ring_buffer.h"
#include "common_audio/signal_processing/include/signal_processing_library.h"
#include "modules/audio_processing/aecm/aecm_defines.h"
}

namespace webrtc {

namespace {

#define BUF_SIZE_FRAMES 50  // buffer size (frames)
// Maximum length of resampled signal. Must be an integer multiple of frames
// (ceil(1/(1 + MIN_SKEW)*2) + 1)*FRAME_LEN
// The factor of 2 handles wb, and the + 1 is as a safety margin
#define MAX_RESAMP_LEN (5 * FRAME_LEN)

static const size_t kBufSizeSamp =
    BUF_SIZE_FRAMES * FRAME_LEN;  // buffer size (samples)
static const int kSampMsNb = 8;   // samples per ms in nb
// Target suppression levels for nlp modes
// log{0.001, 0.00001, 0.00000001}
static const int kInitCheck = 42;

typedef struct {
  int sampFreq;
  int scSampFreq;
  short bufSizeStart;
  int knownDelay;

  // Stores the last frame added to the farend buffer
  short farendOld[2][FRAME_LEN];
  short initFlag;  // indicates if AEC has been initialized

  // Variables used for averaging far end buffer size
  short counter;
  short sum;
  short firstVal;
  short checkBufSizeCtr;

  // Variables used for delay shifts
  short msInSndCardBuf;
  short filtDelay;
  int timeForDelayChange;
  int ECstartup;
  int checkBuffSize;
  int delayChange;
  short lastDelayDiff;

  int16_t echoMode;

#ifdef AEC_DEBUG
  FILE* bufFile;
  FILE* delayFile;
  FILE* preCompFile;
  FILE* postCompFile;
#endif  // AEC_DEBUG
  // Structures
  RingBuffer* farendBuf;

  AecmCore* aecmCore;
} AecMobile;

}  // namespace

// Estimates delay to set the position of the farend buffer read pointer
// (controlled by knownDelay)
static int WebRtcAecm_EstBufDelay(AecMobile* aecm, short msInSndCardBuf);

// Stuffs the farend buffer if the estimated delay is too large
static int WebRtcAecm_DelayComp(AecMobile* aecm);

void* WebRtcAecm_Create() {
  // Allocate zero-filled memory.
  AecMobile* aecm = static_cast<AecMobile*>(calloc(1, sizeof(AecMobile)));

  aecm->aecmCore = WebRtcAecm_CreateCore();
  if (!aecm->aecmCore) {
    WebRtcAecm_Free(aecm);
    return nullptr;
  }

  aecm->farendBuf = WebRtc_CreateBuffer(kBufSizeSamp, sizeof(int16_t));
  if (!aecm->farendBuf) {
    WebRtcAecm_Free(aecm);
    return nullptr;
  }

#ifdef AEC_DEBUG
  aecm->aecmCore->farFile = fopen("aecFar.pcm", "wb");
  aecm->aecmCore->nearFile = fopen("aecNear.pcm", "wb");
  aecm->aecmCore->outFile = fopen("aecOut.pcm", "wb");
  // aecm->aecmCore->outLpFile = fopen("aecOutLp.pcm","wb");

  aecm->bufFile = fopen("aecBuf.dat", "wb");
  aecm->delayFile = fopen("aecDelay.dat", "wb");
  aecm->preCompFile = fopen("preComp.pcm", "wb");
  aecm->postCompFile = fopen("postComp.pcm", "wb");
#endif  // AEC_DEBUG
  return aecm;
}

void WebRtcAecm_Free(void* aecmInst) {
  AecMobile* aecm = static_cast<AecMobile*>(aecmInst);

  if (aecm == nullptr) {
    return;
  }

#ifdef AEC_DEBUG
  fclose(aecm->aecmCore->farFile);
  fclose(aecm->aecmCore->nearFile);
  fclose(aecm->aecmCore->outFile);
  // fclose(aecm->aecmCore->outLpFile);

  fclose(aecm->bufFile);
  fclose(aecm->delayFile);
  fclose(aecm->preCompFile);
  fclose(aecm->postCompFile);
#endif  // AEC_DEBUG
  WebRtcAecm_FreeCore(aecm->aecmCore);
  WebRtc_FreeBuffer(aecm->farendBuf);
  free(aecm);
}

int32_t WebRtcAecm_Init(void* aecmInst, int32_t sampFreq) {
  AecMobile* aecm = static_cast<AecMobile*>(aecmInst);
  AecmConfig aecConfig;

  if (aecm == nullptr) {
    return -1;
  }

  if (sampFreq != 8000 && sampFreq != 16000) {
    return AECM_BAD_PARAMETER_ERROR;
  }
  aecm->sampFreq = sampFreq;

  // Initialize AECM core
  if (WebRtcAecm_InitCore(aecm->aecmCore, aecm->sampFreq) == -1) {
    return AECM_UNSPECIFIED_ERROR;
  }

  // Initialize farend buffer
  WebRtc_InitBuffer(aecm->farendBuf);

  aecm->initFlag = kInitCheck;  // indicates that initialization has been done

  aecm->delayChange = 1;

  aecm->sum = 0;
  aecm->counter = 0;
  aecm->checkBuffSize = 1;
  aecm->firstVal = 0;

  aecm->ECstartup = 1;
  aecm->bufSizeStart = 0;
  aecm->checkBufSizeCtr = 0;
  aecm->filtDelay = 0;
  aecm->timeForDelayChange = 0;
  aecm->knownDelay = 0;
  aecm->lastDelayDiff = 0;

  memset(&aecm->farendOld, 0, sizeof(aecm->farendOld));

  // Default settings.
  aecConfig.cngMode = AecmTrue;
  aecConfig.echoMode = 3;

  if (WebRtcAecm_set_config(aecm, aecConfig) == -1) {
    return AECM_UNSPECIFIED_ERROR;
  }

  return 0;
}

// Returns any error that is caused when buffering the
// farend signal.
int32_t WebRtcAecm_GetBufferFarendError(void* aecmInst,
                                        const int16_t* farend,
                                        size_t nrOfSamples) {
  AecMobile* aecm = static_cast<AecMobile*>(aecmInst);

  if (aecm == nullptr)
    return -1;

  if (farend == nullptr)
    return AECM_NULL_POINTER_ERROR;

  if (aecm->initFlag != kInitCheck)
    return AECM_UNINITIALIZED_ERROR;

  if (nrOfSamples != 80 && nrOfSamples != 160)
    return AECM_BAD_PARAMETER_ERROR;

  return 0;
}

int32_t WebRtcAecm_BufferFarend(void* aecmInst,
                                const int16_t* farend,
                                size_t nrOfSamples) {
  AecMobile* aecm = static_cast<AecMobile*>(aecmInst);

  const int32_t err =
      WebRtcAecm_GetBufferFarendError(aecmInst, farend, nrOfSamples);

  if (err != 0)
    return err;

  // TODO(unknown): Is this really a good idea?
  if (!aecm->ECstartup) {
    WebRtcAecm_DelayComp(aecm);
  }

  WebRtc_WriteBuffer(aecm->farendBuf, farend, nrOfSamples);

  return 0;
}

int32_t WebRtcAecm_Process(void* aecmInst,
                           const int16_t* nearendNoisy,
                           const int16_t* nearendClean,
                           int16_t* out,
                           size_t nrOfSamples,
                           int16_t msInSndCardBuf) {
  AecMobile* aecm = static_cast<AecMobile*>(aecmInst);
  int32_t retVal = 0;
  size_t i;
  short nmbrOfFilledBuffers;
  size_t nBlocks10ms;
  size_t nFrames;
#ifdef AEC_DEBUG
  short msInAECBuf;
#endif

  if (aecm == nullptr) {
    return -1;
  }

  if (nearendNoisy == nullptr) {
    return AECM_NULL_POINTER_ERROR;
  }

  if (out == nullptr) {
    return AECM_NULL_POINTER_ERROR;
  }

  if (aecm->initFlag != kInitCheck) {
    return AECM_UNINITIALIZED_ERROR;
  }

  if (nrOfSamples != 80 && nrOfSamples != 160) {
    return AECM_BAD_PARAMETER_ERROR;
  }

  if (msInSndCardBuf < 0) {
    msInSndCardBuf = 0;
    retVal = AECM_BAD_PARAMETER_WARNING;
  } else if (msInSndCardBuf > 500) {
    msInSndCardBuf = 500;
    retVal = AECM_BAD_PARAMETER_WARNING;
  }
  msInSndCardBuf += 10;
  aecm->msInSndCardBuf = msInSndCardBuf;

  nFrames = nrOfSamples / FRAME_LEN;
  nBlocks10ms = nFrames / aecm->aecmCore->mult;

  if (aecm->ECstartup) {
    if (nearendClean == nullptr) {
      if (out != nearendNoisy) {
        memcpy(out, nearendNoisy, sizeof(short) * nrOfSamples);
      }
    } else if (out != nearendClean) {
      memcpy(out, nearendClean, sizeof(short) * nrOfSamples);
    }

    nmbrOfFilledBuffers =
        (short)WebRtc_available_read(aecm->farendBuf) / FRAME_LEN;
    // The AECM is in the start up mode
    // AECM is disabled until the soundcard buffer and farend buffers are OK

    // Mechanism to ensure that the soundcard buffer is reasonably stable.
    if (aecm->checkBuffSize) {
      aecm->checkBufSizeCtr++;
      // Before we fill up the far end buffer we require the amount of data on
      // the sound card to be stable (+/-8 ms) compared to the first value. This
      // comparison is made during the following 4 consecutive frames. If it
      // seems to be stable then we start to fill up the far end buffer.

      if (aecm->counter == 0) {
        aecm->firstVal = aecm->msInSndCardBuf;
        aecm->sum = 0;
      }

      if (abs(aecm->firstVal - aecm->msInSndCardBuf) <
          WEBRTC_SPL_MAX(0.2 * aecm->msInSndCardBuf, kSampMsNb)) {
        aecm->sum += aecm->msInSndCardBuf;
        aecm->counter++;
      } else {
        aecm->counter = 0;
      }

      if (aecm->counter * nBlocks10ms >= 6) {
        // The farend buffer size is determined in blocks of 80 samples
        // Use 75% of the average value of the soundcard buffer
        aecm->bufSizeStart = WEBRTC_SPL_MIN(
            (3 * aecm->sum * aecm->aecmCore->mult) / (aecm->counter * 40),
            BUF_SIZE_FRAMES);
        // buffersize has now been determined
        aecm->checkBuffSize = 0;
      }

      if (aecm->checkBufSizeCtr * nBlocks10ms > 50) {
        // for really bad sound cards, don't disable echocanceller for more than
        // 0.5 sec
        aecm->bufSizeStart = WEBRTC_SPL_MIN(
            (3 * aecm->msInSndCardBuf * aecm->aecmCore->mult) / 40,
            BUF_SIZE_FRAMES);
        aecm->checkBuffSize = 0;
      }
    }

    // if checkBuffSize changed in the if-statement above
    if (!aecm->checkBuffSize) {
      // soundcard buffer is now reasonably stable
      // When the far end buffer is filled with approximately the same amount of
      // data as the amount on the sound card we end the start up phase and
      // start to cancel echoes.

      if (nmbrOfFilledBuffers == aecm->bufSizeStart) {
        aecm->ECstartup = 0;  // Enable the AECM
      } else if (nmbrOfFilledBuffers > aecm->bufSizeStart) {
        WebRtc_MoveReadPtr(aecm->farendBuf,
                           (int)WebRtc_available_read(aecm->farendBuf) -
                               (int)aecm->bufSizeStart * FRAME_LEN);
        aecm->ECstartup = 0;
      }
    }

  } else {
    // AECM is enabled

    // Note only 1 block supported for nb and 2 blocks for wb
    for (i = 0; i < nFrames; i++) {
      int16_t farend[FRAME_LEN];
      const int16_t* farend_ptr = nullptr;

      nmbrOfFilledBuffers =
          (short)WebRtc_available_read(aecm->farendBuf) / FRAME_LEN;

      // Check that there is data in the far end buffer
      if (nmbrOfFilledBuffers > 0) {
        // Get the next 80 samples from the farend buffer
        WebRtc_ReadBuffer(aecm->farendBuf, (void**)&farend_ptr, farend,
                          FRAME_LEN);

        // Always store the last frame for use when we run out of data
        memcpy(&(aecm->farendOld[i][0]), farend_ptr, FRAME_LEN * sizeof(short));
      } else {
        // We have no data so we use the last played frame
        memcpy(farend, &(aecm->farendOld[i][0]), FRAME_LEN * sizeof(short));
        farend_ptr = farend;
      }

      // Call buffer delay estimator when all data is extracted,
      // i,e. i = 0 for NB and i = 1 for WB
      if ((i == 0 && aecm->sampFreq == 8000) ||
          (i == 1 && aecm->sampFreq == 16000)) {
        WebRtcAecm_EstBufDelay(aecm, aecm->msInSndCardBuf);
      }

      // Call the AECM
      /*WebRtcAecm_ProcessFrame(aecm->aecmCore, farend, &nearend[FRAME_LEN * i],
       &out[FRAME_LEN * i], aecm->knownDelay);*/
      if (WebRtcAecm_ProcessFrame(
              aecm->aecmCore, farend_ptr, &nearendNoisy[FRAME_LEN * i],
              (nearendClean ? &nearendClean[FRAME_LEN * i] : nullptr),
              &out[FRAME_LEN * i]) == -1)
        return -1;
    }
  }

#ifdef AEC_DEBUG
  msInAECBuf = (short)WebRtc_available_read(aecm->farendBuf) /
               (kSampMsNb * aecm->aecmCore->mult);
  fwrite(&msInAECBuf, 2, 1, aecm->bufFile);
  fwrite(&(aecm->knownDelay), sizeof(aecm->knownDelay), 1, aecm->delayFile);
#endif

  return retVal;
}

int32_t WebRtcAecm_set_config(void* aecmInst, AecmConfig config) {
  AecMobile* aecm = static_cast<AecMobile*>(aecmInst);

  if (aecm == nullptr) {
    return -1;
  }

  if (aecm->initFlag != kInitCheck) {
    return AECM_UNINITIALIZED_ERROR;
  }

  if (config.cngMode != AecmFalse && config.cngMode != AecmTrue) {
    return AECM_BAD_PARAMETER_ERROR;
  }
  aecm->aecmCore->cngMode = config.cngMode;

  if (config.echoMode < 0 || config.echoMode > 4) {
    return AECM_BAD_PARAMETER_ERROR;
  }
  aecm->echoMode = config.echoMode;

  if (aecm->echoMode == 0) {
    aecm->aecmCore->supGain = SUPGAIN_DEFAULT >> 3;
    aecm->aecmCore->supGainOld = SUPGAIN_DEFAULT >> 3;
    aecm->aecmCore->supGainErrParamA = SUPGAIN_ERROR_PARAM_A >> 3;
    aecm->aecmCore->supGainErrParamD = SUPGAIN_ERROR_PARAM_D >> 3;
    aecm->aecmCore->supGainErrParamDiffAB =
        (SUPGAIN_ERROR_PARAM_A >> 3) - (SUPGAIN_ERROR_PARAM_B >> 3);
    aecm->aecmCore->supGainErrParamDiffBD =
        (SUPGAIN_ERROR_PARAM_B >> 3) - (SUPGAIN_ERROR_PARAM_D >> 3);
  } else if (aecm->echoMode == 1) {
    aecm->aecmCore->supGain = SUPGAIN_DEFAULT >> 2;
    aecm->aecmCore->supGainOld = SUPGAIN_DEFAULT >> 2;
    aecm->aecmCore->supGainErrParamA = SUPGAIN_ERROR_PARAM_A >> 2;
    aecm->aecmCore->supGainErrParamD = SUPGAIN_ERROR_PARAM_D >> 2;
    aecm->aecmCore->supGainErrParamDiffAB =
        (SUPGAIN_ERROR_PARAM_A >> 2) - (SUPGAIN_ERROR_PARAM_B >> 2);
    aecm->aecmCore->supGainErrParamDiffBD =
        (SUPGAIN_ERROR_PARAM_B >> 2) - (SUPGAIN_ERROR_PARAM_D >> 2);
  } else if (aecm->echoMode == 2) {
    aecm->aecmCore->supGain = SUPGAIN_DEFAULT >> 1;
    aecm->aecmCore->supGainOld = SUPGAIN_DEFAULT >> 1;
    aecm->aecmCore->supGainErrParamA = SUPGAIN_ERROR_PARAM_A >> 1;
    aecm->aecmCore->supGainErrParamD = SUPGAIN_ERROR_PARAM_D >> 1;
    aecm->aecmCore->supGainErrParamDiffAB =
        (SUPGAIN_ERROR_PARAM_A >> 1) - (SUPGAIN_ERROR_PARAM_B >> 1);
    aecm->aecmCore->supGainErrParamDiffBD =
        (SUPGAIN_ERROR_PARAM_B >> 1) - (SUPGAIN_ERROR_PARAM_D >> 1);
  } else if (aecm->echoMode == 3) {
    aecm->aecmCore->supGain = SUPGAIN_DEFAULT;
    aecm->aecmCore->supGainOld = SUPGAIN_DEFAULT;
    aecm->aecmCore->supGainErrParamA = SUPGAIN_ERROR_PARAM_A;
    aecm->aecmCore->supGainErrParamD = SUPGAIN_ERROR_PARAM_D;
    aecm->aecmCore->supGainErrParamDiffAB =
        SUPGAIN_ERROR_PARAM_A - SUPGAIN_ERROR_PARAM_B;
    aecm->aecmCore->supGainErrParamDiffBD =
        SUPGAIN_ERROR_PARAM_B - SUPGAIN_ERROR_PARAM_D;
  } else if (aecm->echoMode == 4) {
    aecm->aecmCore->supGain = SUPGAIN_DEFAULT << 1;
    aecm->aecmCore->supGainOld = SUPGAIN_DEFAULT << 1;
    aecm->aecmCore->supGainErrParamA = SUPGAIN_ERROR_PARAM_A << 1;
    aecm->aecmCore->supGainErrParamD = SUPGAIN_ERROR_PARAM_D << 1;
    aecm->aecmCore->supGainErrParamDiffAB =
        (SUPGAIN_ERROR_PARAM_A << 1) - (SUPGAIN_ERROR_PARAM_B << 1);
    aecm->aecmCore->supGainErrParamDiffBD =
        (SUPGAIN_ERROR_PARAM_B << 1) - (SUPGAIN_ERROR_PARAM_D << 1);
  }

  return 0;
}

int32_t WebRtcAecm_InitEchoPath(void* aecmInst,
                                const void* echo_path,
                                size_t size_bytes) {
  AecMobile* aecm = static_cast<AecMobile*>(aecmInst);
  const int16_t* echo_path_ptr = static_cast<const int16_t*>(echo_path);

  if (aecmInst == nullptr) {
    return -1;
  }
  if (echo_path == nullptr) {
    return AECM_NULL_POINTER_ERROR;
  }
  if (size_bytes != WebRtcAecm_echo_path_size_bytes()) {
    // Input channel size does not match the size of AECM
    return AECM_BAD_PARAMETER_ERROR;
  }
  if (aecm->initFlag != kInitCheck) {
    return AECM_UNINITIALIZED_ERROR;
  }

  WebRtcAecm_InitEchoPathCore(aecm->aecmCore, echo_path_ptr);

  return 0;
}

int32_t WebRtcAecm_GetEchoPath(void* aecmInst,
                               void* echo_path,
                               size_t size_bytes) {
  AecMobile* aecm = static_cast<AecMobile*>(aecmInst);
  int16_t* echo_path_ptr = static_cast<int16_t*>(echo_path);

  if (aecmInst == nullptr) {
    return -1;
  }
  if (echo_path == nullptr) {
    return AECM_NULL_POINTER_ERROR;
  }
  if (size_bytes != WebRtcAecm_echo_path_size_bytes()) {
    // Input channel size does not match the size of AECM
    return AECM_BAD_PARAMETER_ERROR;
  }
  if (aecm->initFlag != kInitCheck) {
    return AECM_UNINITIALIZED_ERROR;
  }

  memcpy(echo_path_ptr, aecm->aecmCore->channelStored, size_bytes);
  return 0;
}

size_t WebRtcAecm_echo_path_size_bytes() {
  return (PART_LEN1 * sizeof(int16_t));
}

static int WebRtcAecm_EstBufDelay(AecMobile* aecm, short msInSndCardBuf) {
  short delayNew, nSampSndCard;
  short nSampFar = (short)WebRtc_available_read(aecm->farendBuf);
  short diff;

  nSampSndCard = msInSndCardBuf * kSampMsNb * aecm->aecmCore->mult;

  delayNew = nSampSndCard - nSampFar;

  if (delayNew < FRAME_LEN) {
    WebRtc_MoveReadPtr(aecm->farendBuf, FRAME_LEN);
    delayNew += FRAME_LEN;
  }

  aecm->filtDelay =
      WEBRTC_SPL_MAX(0, (8 * aecm->filtDelay + 2 * delayNew) / 10);

  diff = aecm->filtDelay - aecm->knownDelay;
  if (diff > 224) {
    if (aecm->lastDelayDiff < 96) {
      aecm->timeForDelayChange = 0;
    } else {
      aecm->timeForDelayChange++;
    }
  } else if (diff < 96 && aecm->knownDelay > 0) {
    if (aecm->lastDelayDiff > 224) {
      aecm->timeForDelayChange = 0;
    } else {
      aecm->timeForDelayChange++;
    }
  } else {
    aecm->timeForDelayChange = 0;
  }
  aecm->lastDelayDiff = diff;

  if (aecm->timeForDelayChange > 25) {
    aecm->knownDelay = WEBRTC_SPL_MAX((int)aecm->filtDelay - 160, 0);
  }
  return 0;
}

static int WebRtcAecm_DelayComp(AecMobile* aecm) {
  int nSampFar = (int)WebRtc_available_read(aecm->farendBuf);
  int nSampSndCard, delayNew, nSampAdd;
  const int maxStuffSamp = 10 * FRAME_LEN;

  nSampSndCard = aecm->msInSndCardBuf * kSampMsNb * aecm->aecmCore->mult;
  delayNew = nSampSndCard - nSampFar;

  if (delayNew > FAR_BUF_LEN - FRAME_LEN * aecm->aecmCore->mult) {
    // The difference of the buffer sizes is larger than the maximum
    // allowed known delay. Compensate by stuffing the buffer.
    nSampAdd =
        (int)(WEBRTC_SPL_MAX(((nSampSndCard >> 1) - nSampFar), FRAME_LEN));
    nSampAdd = WEBRTC_SPL_MIN(nSampAdd, maxStuffSamp);

    WebRtc_MoveReadPtr(aecm->farendBuf, -nSampAdd);
    aecm->delayChange = 1;  // the delay needs to be updated
  }

  return 0;
}

}  // namespace webrtc
