123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226 |
- #include "ADTSHeader.h"
- #include "nmrCommon/services/stdServiceImpl.h"
- enum
- {
- ADTS_NOT_PROTECTED = 1,
- ADTS_PROTECTED = 0,
- ADTS_SYNC = 0xFFF,
- ADTS_MAIN = 0x00,
- ADTS_LC = 0x01,
- ADTS_SSR = 0x10,
- ADTS_LTP = 0x11
- };
- const int aac_adts_parse(const aac_adts_header_t header, const __uint8 *buffer)
- {
- header->syncword = ((buffer[0] << 4) | (buffer[1] >> 4));
- if (header->syncword != ADTS_SYNC)
- {
- return NErr_LostSynchronization;
- }
- header->id = ((buffer[1] >> 3) & 1);
- header->layer = ((buffer[1] >> 1) & 3);
- if (header->layer != 0)
- {
- return NErr_WrongFormat;
- }
- header->protection = ((buffer[1]) & 1);
- header->profile = ((buffer[2] >> 6) & 3);
- header->sample_rate_index = ((buffer[2] >> 2) & 0xF);
- if (header->sample_rate_index == 15)
- {
- return NErr_UnsupportedFormat; // might actually be OK if we can separately signal the sample rate
- }
- if (header->sample_rate_index > 13)
- {
- return NErr_Reserved;
- }
- header->private_bit = ((buffer[2] >> 1) & 1);
- header->channel_configuration = ((buffer[2] & 1) << 2) | ((buffer[3] >> 6) & 3);
- header->original = ((buffer[3] >> 5) & 1);
- header->home = ((buffer[3] >> 4) & 1);
- header->frame_length = ((buffer[3] & 3) << 11) | (buffer[4]<<3) | ((buffer[5] >> 5) & 7);
- header->buffer_fullness = ((buffer[5] & 0x1F) << 6) | (buffer[6] >> 2);
- header->num_data_blocks = (buffer[6] & 3);
- return NErr_Success;
- }
- static const unsigned int aac_sratetab[] =
- {
- 96000,
- 88200,
- 64000,
- 48000,
- 44100,
- 32000,
- 24000,
- 22050,
- 16000,
- 12000,
- 11025,
- 8000,
- 7350,
- };
- #if 0
- const int aac_adts_match(const aac_adts_header_t header1, const aac_adts_header_t header2)
- {
- if (header1->id != header2->id)
- {
- return NErr_False;
- }
- if (header1->profile != header2->profile)
- {
- return NErr_False;
- }
- if (header1->sample_rate_index != header2->sample_rate_index)
- {
- return NErr_False;
- }
- if (header1->channel_configuration != header2->channel_configuration)
- {
- return NErr_False;
- }
- return NErr_True;
- }
- #endif
- const int aac_adts_get_channel_count(const aac_adts_header_t header)
- {
- switch (header->channel_configuration)
- {
- case 7:
- {
- return 8;
- }
- default:
- {
- return header->channel_configuration;
- }
- }
- }
- const __uint16 getADTSFrameInfo(const char *hdr, unsigned int *samplerate, __uint8 *asc_header)
- {
- ADTSHeader header = {0};
- if (aac_adts_parse(&header, (const __uint8 *)hdr) == NErr_Success)
- {
- *samplerate = aac_sratetab[header.sample_rate_index];
- // we need this when generating flv frames
- // as it creates the AudioSpecificConfig
- // from the existing ADTS header details
- // (is like a mini-ADTS header to create)
- if (asc_header)
- {
- asc_header[0] |= (((header.profile + 1) & 31) << 3) + (header.sample_rate_index >> 1);
- asc_header[1] |= ((header.sample_rate_index & 0x1) << 7) + (header.channel_configuration << 3);
- }
- //*bitrate = (int)(((header.frame_length / 1/*frames*/) * (aac_sratetab[header.sample_rate_index] / 1024.0)) + 0.5) * 8;
- return (__uint16)header.frame_length;
- }
- return 0;
- }
- const char *AAC_FrameInfo::getVersionName() const
- {
- if (m_version)
- return "v2";
- return "v4";
- }
- const char *AAC_FrameInfo::getAOT() const
- {
- switch (m_aot)
- {
- case 2: return "LC";
- case 5: return "SBR";
- case 29: return "PS";
- default: return "unknown profile";
- }
- }
- int getAACFrameLength (const unsigned char *p, unsigned int len)
- {
- if (len < 6)
- return -1;
- return ((p[3] & 0x3) << 11) + (p[4] << 3) + ((p[5] & 0xE0) >> 5);
- }
- int getAACFrameInfo (const unsigned char *p, unsigned int len, AAC_FrameInfo &info)
- {
- if (len < 6)
- return -1;
- if ((((long)p[0])<<4 | (p[1]>>4)) != 0xfff)
- return -1;
- int layer = ((p[1] >> 1) & 3);
- if (layer != 0)
- return -1;
- int sample_rate_index = ((p[2] >> 2) & 0xF);
- if (sample_rate_index > 13)
- return -1;
- int samplerate = aac_sratetab [sample_rate_index];
- if (info.m_samplerate)
- {
- if (info.m_samplerate != samplerate)
- return -1;
- }
- else
- info.m_samplerate = samplerate;
- info.m_blocks = (p[6] & 0x3) + 1;
- info.m_pattern = (((unsigned long)(p[0])<<24) | (p[1]<<16) | (p[2]<<8) | p[0]) & info.m_mask;
- return getAACFrameLength (p, len);
- }
- int AAC_FrameInfo::verifyFrame (const unsigned char *buf, unsigned int len)
- {
- if (len > 6)
- {
- unsigned long v = (unsigned long)(buf[0])<<24 | (buf[1]<<16) | (buf[2]<<8) | buf[0];
- if ((v & m_mask) == m_pattern)
- {
- m_blocks = (buf[6] & 0x3) + 1;
- m_version = (buf[1] >> 3) & 1; // 1 mpeg2, 0 mpeg4
- m_aot = ((buf[2] >> 6) & 3) + 1;
- return getAACFrameLength (buf, len);
- }
- // DLOG ("AAC failed sync, retry..");
- return -1;
- }
- return 0;
- }
- AAC_FrameInfo::AAC_FrameInfo (unsigned long value) : parserInfo (0xFFFEFDC0, value)
- {
- m_description = "AAC";
- m_blocks = 0;
- m_aot = 0;
- }
- AAC_FrameInfo::AAC_FrameInfo(const unsigned char *p, unsigned int len) : parserInfo()
- {
- m_mask = 0xFFFEFDC0;
- m_description = "AAC";
- m_blocks = 0;
- getAACFrameInfo (p, len, *this);
- }
|