| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182 | #include "EncodedAudioStream.h"#include <string.h>     // for memcpy, memmove#include <stdexcept>    // for runtime_error#include <type_traits>  // for remove_extent_t#include <utility>      // for move#include "BellLogger.h"      // for AbstractLogger, BELL_LOG, bell#include "ByteStream.h"      // for ByteStream#include "DecoderGlobals.h"  // for DecodersInstance, decodersInstance, AAC_...using namespace bell;EncodedAudioStream::EncodedAudioStream() {  bell::decodersInstance->ensureAAC();  bell::decodersInstance->ensureMP3();  inputBuffer = std::vector<uint8_t>(AAC_READBUF_SIZE * 4);  outputBuffer = std::vector<short>(AAC_MAX_NCHANS * AAC_MAX_NSAMPS * 4 * 4);  decodePtr = inputBuffer.data();}EncodedAudioStream::~EncodedAudioStream() {  this->innerStream->close();}void EncodedAudioStream::openWithStream(    std::unique_ptr<bell::ByteStream> byteStream) {  if (this->innerStream) {    this->innerStream->close();  }  this->innerStream = std::move(byteStream);  this->guessDataFormat();}bool EncodedAudioStream::vectorStartsWith(std::vector<uint8_t>& vec,                                          std::vector<uint8_t>& start) {  if (vec.size() < start.size()) {    return false;  }  for (int i = 0; i < start.size(); i++) {    if (vec[i] != start[i]) {      return false;    }  }  return true;}size_t EncodedAudioStream::decodeFrame(uint8_t* dst) {  if (innerStream->size() != 0 &&      innerStream->position() >= innerStream->size()) {    return 0;  }  switch (this->codec) {    case AudioCodec::AAC:      return decodeFrameAAC(dst);      break;    case AudioCodec::MP3:      return decodeFrameMp3(dst);      break;    default:      break;  }  return 0;}size_t EncodedAudioStream::decodeFrameMp3(uint8_t* dst) {  size_t writtenBytes = 0;  int bufSize = MP3_READBUF_SIZE;  int readBytes = innerStream->read(inputBuffer.data() + bytesInBuffer,                                    bufSize - bytesInBuffer);  if (readBytes > 0) {    bytesInBuffer += readBytes;    decodePtr = inputBuffer.data();    offset = MP3FindSyncWord(inputBuffer.data(), bytesInBuffer);    if (offset != -1) {      bytesInBuffer -= offset;      decodePtr += offset;      int decodeStatus =          MP3Decode(bell::decodersInstance->mp3Decoder, &decodePtr,                    &bytesInBuffer, outputBuffer.data(), 0);      MP3GetLastFrameInfo(bell::decodersInstance->mp3Decoder, &mp3FrameInfo);      if (decodeStatus == ERR_MP3_NONE) {        decodedSampleRate = mp3FrameInfo.samprate;        writtenBytes =            (mp3FrameInfo.bitsPerSample / 8) * mp3FrameInfo.outputSamps;        memcpy(dst, outputBuffer.data(), writtenBytes);      } else {        BELL_LOG(info, TAG, "Error in frame, moving two bytes %d",                 decodeStatus);        decodePtr += 1;        bytesInBuffer -= 1;      }    } else {      BELL_LOG(info, TAG, "Unexpected error in data, skipping a word");      decodePtr += 3800;      bytesInBuffer -= 3800;    }    memmove(inputBuffer.data(), decodePtr, bytesInBuffer);  }  return writtenBytes;}bool EncodedAudioStream::isReadable() {  return this->codec != AudioCodec::NONE;}size_t EncodedAudioStream::decodeFrameAAC(uint8_t* dst) {  size_t writtenBytes = 0;  auto bufSize = AAC_READBUF_SIZE;  int readBytes = innerStream->read(inputBuffer.data() + bytesInBuffer,                                    bufSize - bytesInBuffer);  if (readBytes > 0) {    bytesInBuffer += readBytes;    decodePtr = inputBuffer.data();    offset = AACFindSyncWord(inputBuffer.data(), bytesInBuffer);    if (offset != -1) {      bytesInBuffer -= offset;      decodePtr += offset;      int decodeStatus =          AACDecode(bell::decodersInstance->aacDecoder, &decodePtr,                    &bytesInBuffer, outputBuffer.data());      AACGetLastFrameInfo(bell::decodersInstance->aacDecoder, &aacFrameInfo);      if (decodeStatus == ERR_AAC_NONE) {        decodedSampleRate = aacFrameInfo.sampRateOut;        writtenBytes =            (aacFrameInfo.bitsPerSample / 8) * aacFrameInfo.outputSamps;        memcpy(dst, outputBuffer.data(), writtenBytes);      } else {        BELL_LOG(info, TAG, "Error in frame, moving two bytes %d",                 decodeStatus);        decodePtr += 1;        bytesInBuffer -= 1;      }    } else {      BELL_LOG(info, TAG, "Unexpected error in data, skipping a word");      decodePtr += 3800;      bytesInBuffer -= 3800;    }    memmove(inputBuffer.data(), decodePtr, bytesInBuffer);  }  return writtenBytes;}void EncodedAudioStream::guessDataFormat() {  // Read 14 bytes from the stream  this->innerStream->read(inputBuffer.data(), 14);  bytesInBuffer = 14;  BELL_LOG(info, TAG, "No codec set, reading secret bytes");  if (vectorStartsWith(inputBuffer, this->mp3MagicBytesIdc) ||      vectorStartsWith(inputBuffer, this->mp3MagicBytesUntagged)) {    BELL_LOG(info, TAG, "Detected MP3");    codec = AudioCodec::MP3;  } else if (vectorStartsWith(inputBuffer, this->aacMagicBytes) ||             vectorStartsWith(inputBuffer, this->aacMagicBytes4)) {    BELL_LOG(info, TAG, "Detected AAC");    codec = AudioCodec::AAC;  }  if (codec == AudioCodec::NONE) {    throw std::runtime_error("Codec not supported");  }}void EncodedAudioStream::readFully(uint8_t* dst, size_t nbytes) {}
 |