ALACMP4Decoder.cpp 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197
  1. /* copyright 2006 Ben Allison */
  2. #include "ALACMP4Decoder.h"
  3. #include "alac/ALACBitUtilities.h"
  4. #include "api__alac.h"
  5. #include "decomp.h"
  6. #include <math.h>
  7. #include <string.h>
  8. #include "../external_dependencies/libmp4v2/mp4.h"
  9. #include "../Plugins/Input/in_mp4/mpeg4audio.h"
  10. // {B6CB4A7C-A8D0-4c55-8E60-9F7A7A23DA0F}
  11. static const GUID playbackConfigGroupGUID =
  12. { 0xb6cb4a7c, 0xa8d0, 0x4c55, { 0x8e, 0x60, 0x9f, 0x7a, 0x7a, 0x23, 0xda, 0xf } };
  13. int ALACMP4Decoder::OpenMP4(MP4FileHandle mp4_file, MP4TrackId mp4_track, size_t output_bits, size_t maxChannels, bool useFloat)
  14. {
  15. if (useFloat)
  16. return MP4_FAILURE;
  17. // get requested output bits
  18. this->output_bits = (int)output_bits;
  19. use_rg = false;
  20. rg = 1.0f;
  21. uint64_t val;
  22. if (MP4GetTrackIntegerProperty(mp4_file, mp4_track, "mdia.minf.stbl.stsd.*[0].channels", &val))
  23. channels = (int)val;
  24. else
  25. channels=2;
  26. if (MP4GetTrackIntegerProperty(mp4_file, mp4_track, "mdia.minf.stbl.stsd.*[0].sampleSize", &val))
  27. bps= (int)val;
  28. else
  29. bps=16;
  30. return MP4_SUCCESS;
  31. }
  32. int ALACMP4Decoder::GetCurrentBitrate(unsigned int *bitrate)
  33. {
  34. if (mpAlacDecoder->mConfig.avgBitRate)
  35. {
  36. *bitrate = mpAlacDecoder->mConfig.avgBitRate;
  37. return MP4_SUCCESS;
  38. }
  39. return MP4_GETCURRENTBITRATE_UNKNOWN; // TODO
  40. }
  41. /*
  42. * 32 bits atom size
  43. * 32 bits tag ("alac")
  44. *
  45. * Following data is passed to the function, ALACSpecificConfig structure (24 Bytes) does not contain
  46. * "tag version", check and skip if data contains it
  47. *
  48. * 32 bits tag version (0)
  49. * 32 bits samples per frame (used when not set explicitly in the frames) --> frameLength
  50. * 8 bits compatible version (0)
  51. * 8 bits sample size --> bitDepth
  52. * 8 bits history mult (40)
  53. * 8 bits initial history (10)
  54. * 8 bits rice param limit (14)
  55. * 8 bits channels --> numChannels
  56. * 16 bits maxRun (255)
  57. * 32 bits max coded frame size (0 means unknown) --> maxFrameBytes
  58. * 32 bits average bitrate (0 means unknown)
  59. * 32 bits samplerate
  60. */
  61. int ALACMP4Decoder::AudioSpecificConfiguration(void *buffer, size_t buffer_size)
  62. {
  63. mpAlacDecoder = new ALACDecoder();
  64. if (buffer_size > sizeof(ALACSpecificConfig))
  65. {
  66. // we have the "tag version" embedded;
  67. // just skip
  68. size_t skip = sizeof(uint32_t);
  69. mpAlacDecoder->Init((void*)((char*)buffer + skip), sizeof(ALACSpecificConfig));
  70. }
  71. else
  72. {
  73. mpAlacDecoder->Init(buffer, buffer_size);
  74. }
  75. /*alac = create_alac(bps, channels);
  76. alac_set_info(alac, reinterpret_cast<char *>(buffer));*/
  77. return MP4_SUCCESS;
  78. }
  79. void ALACMP4Decoder::Flush()
  80. {
  81. // TODO
  82. }
  83. void ALACMP4Decoder::Close()
  84. {
  85. if (mpAlacDecoder)
  86. {
  87. delete mpAlacDecoder;
  88. mpAlacDecoder = 0;
  89. }
  90. }
  91. int ALACMP4Decoder::GetOutputProperties(unsigned int *sampleRate, unsigned int *channels, unsigned int *bitsPerSample)
  92. {
  93. *sampleRate = mpAlacDecoder->mConfig.sampleRate; // TODO: verify
  94. *channels = mpAlacDecoder->mConfig.numChannels;
  95. *bitsPerSample = mpAlacDecoder->mConfig.bitDepth;
  96. return MP4_SUCCESS;
  97. }
  98. int ALACMP4Decoder::OutputFrameSize(size_t *frameSize)
  99. {
  100. *frameSize = mpAlacDecoder->mConfig.frameLength; // TODO: verify
  101. return MP4_SUCCESS;
  102. }
  103. #define PA_CLIP_( val, min, max )\
  104. { val = ((val) < (min)) ? (min) : (((val) > (max)) ? (max) : (val)); }
  105. inline static void clip(double &x, double a, double b)
  106. {
  107. double x1 = fabs (x - a);
  108. double x2 = fabs (x - b);
  109. x = x1 + (a + b);
  110. x -= x2;
  111. x *= 0.5;
  112. }
  113. int ALACMP4Decoder::DecodeSample(void *inputBuffer, size_t inputBufferBytes, void *outputBuffer, size_t *outputBufferBytes)
  114. {
  115. struct BitBuffer inputChunk;
  116. BitBufferInit(&inputChunk, (uint8_t*)(inputBuffer), inputBufferBytes);
  117. uint32_t numFrames = 0;
  118. mpAlacDecoder->Decode(&inputChunk, (uint8_t*)(outputBuffer), mpAlacDecoder->mConfig.frameLength , mpAlacDecoder->mConfig.numChannels, &numFrames);
  119. size_t bytesPerSample = (mpAlacDecoder->mConfig.bitDepth / 8) * mpAlacDecoder->mConfig.numChannels;
  120. *outputBufferBytes = mpAlacDecoder->mConfig.frameLength * bytesPerSample;
  121. if (use_rg && mpAlacDecoder->mConfig.bitDepth == 16)
  122. {
  123. size_t numSamples = *outputBufferBytes / (mpAlacDecoder->mConfig.bitDepth / 8);
  124. //if (bitsPerSample == 16)
  125. {
  126. // TODO: this algorithm assumes ALAC bps is 16!!
  127. int16_t* audioBuffer = (int16_t*)outputBuffer;
  128. for (size_t i = 0; i != numSamples; i++)
  129. {
  130. float sample = (float)audioBuffer[i];
  131. int32_t temp = (int32_t)(sample * rg);
  132. PA_CLIP_(temp, -0x8000, 0x7FFF);
  133. audioBuffer[i] = (uint16_t)temp;
  134. }
  135. }
  136. }
  137. return MP4_SUCCESS;
  138. }
  139. const char *ALACMP4Decoder::GetCodecInfoString()
  140. {
  141. return "mdia.minf.stbl.stsd.alac.alac.decoderConfig";
  142. }
  143. int ALACMP4Decoder::CanHandleCodec(const char *codecName)
  144. {
  145. return !strcmp(codecName, "alac");
  146. }
  147. int ALACMP4Decoder::SetGain(float gain)
  148. {
  149. if (gain != 1.0f)
  150. {
  151. use_rg = true;
  152. rg = gain;
  153. }
  154. return MP4_SUCCESS;
  155. }
  156. #ifdef CBCLASS
  157. #undef CBCLASS
  158. #endif
  159. #define CBCLASS ALACMP4Decoder
  160. START_DISPATCH;
  161. CB(MPEG4_AUDIO_OPENMP4, OpenMP4)
  162. CB(MPEG4_AUDIO_ASC, AudioSpecificConfiguration)
  163. CB(MPEG4_AUDIO_BITRATE, GetCurrentBitrate)
  164. CB(MPEG4_AUDIO_FRAMESIZE, OutputFrameSize)
  165. CB(MPEG4_AUDIO_OUTPUTINFO, GetOutputProperties)
  166. CB(MPEG4_AUDIO_DECODE, DecodeSample)
  167. VCB(MPEG4_AUDIO_FLUSH, Flush)
  168. VCB(MPEG4_AUDIO_CLOSE, Close)
  169. CB(MPEG4_AUDIO_CODEC_INFO_STRING, GetCodecInfoString)
  170. CB(MPEG4_AUDIO_HANDLES_CODEC, CanHandleCodec)
  171. CB(MPEG4_AUDIO_SET_GAIN, SetGain)
  172. END_DISPATCH;