adts.cpp
资源名称:NETVIDEO.rar [点击查看]
上传用户:sun1608
上传日期:2007-02-02
资源大小:6116k
文件大小:6k
源码类别:
流媒体/Mpeg4/MP4
开发平台:
Visual C++
- /*
- * The contents of this file are subject to the Mozilla Public
- * License Version 1.1 (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.mozilla.org/MPL/
- *
- * Software distributed under the License is distributed on an "AS
- * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
- * implied. See the License for the specific language governing
- * rights and limitations under the License.
- *
- * The Original Code is MPEG4IP.
- *
- * The Initial Developer of the Original Code is Cisco Systems Inc.
- * Portions created by Cisco Systems Inc. are
- * Copyright (C) Cisco Systems Inc. 2000-2002. All Rights Reserved.
- *
- * Contributor(s):
- * Dave Mackie dmackie@cisco.com
- */
- /*
- * Notes:
- * - file formatted with tabstops == 4 spaces
- */
- #include <mp4av_common.h>
- /*
- * ADTS Header:
- * MPEG-2 version 56 bits (byte aligned)
- * MPEG-4 version 58 bits (not byte aligned)
- *
- * syncword 12 bits
- * id 1 bit
- * layer 2 bits
- * protection_absent 1 bit
- * profile 2 bits
- * sampling_frequency_index 4 bits
- * private 1 bit
- * channel_configuraton 3 bits
- * original 1 bit
- * home 1 bit
- * emphasis 2 bits
- * copyright_id 1 bit
- * copyright_id_start 1 bit
- * aac_frame_length 13 bits
- * adts_buffer_fullness 11 bits
- * num_raw_data_blocks 2 bits
- *
- * if (protection_absent == 0)
- * crc_check 16 bits
- */
- u_int32_t AdtsSamplingRates[NUM_ADTS_SAMPLING_RATES] = {
- 96000, 88200, 64000, 48000, 44100, 32000, 24000, 22050,
- 16000, 12000, 11025, 8000, 7350, 0, 0, 0
- };
- /*
- * compute ADTS frame size
- */
- extern "C" u_int16_t MP4AV_AdtsGetFrameSize(u_int8_t* pHdr)
- {
- /* extract the necessary fields from the header */
- u_int8_t isMpeg4 = !(pHdr[1] & 0x08);
- u_int16_t frameLength;
- if (isMpeg4) {
- frameLength = (((u_int16_t)pHdr[4]) << 5) | (pHdr[5] >> 3);
- } else { /* MPEG-2 */
- frameLength = (((u_int16_t)(pHdr[3] & 0x3)) << 11)
- | (((u_int16_t)pHdr[4]) << 3) | (pHdr[5] >> 5);
- }
- return frameLength;
- }
- /*
- * Compute length of ADTS header in bits
- */
- extern "C" u_int16_t MP4AV_AdtsGetHeaderBitSize(u_int8_t* pHdr)
- {
- u_int8_t isMpeg4 = !(pHdr[1] & 0x08);
- u_int8_t hasCrc = !(pHdr[1] & 0x01);
- u_int16_t hdrSize;
- if (isMpeg4) {
- hdrSize = 58;
- } else {
- hdrSize = 56;
- }
- if (hasCrc) {
- hdrSize += 16;
- }
- return hdrSize;
- }
- extern "C" u_int16_t MP4AV_AdtsGetHeaderByteSize(u_int8_t* pHdr)
- {
- return (MP4AV_AdtsGetHeaderBitSize(pHdr) + 7) / 8;
- }
- extern "C" u_int8_t MP4AV_AdtsGetVersion(u_int8_t* pHdr)
- {
- return (pHdr[1] & 0x08) >> 3;
- }
- extern "C" u_int8_t MP4AV_AdtsGetProfile(u_int8_t* pHdr)
- {
- return (pHdr[2] & 0xc0) >> 6;
- }
- extern "C" u_int8_t MP4AV_AdtsGetSamplingRateIndex(u_int8_t* pHdr)
- {
- return (pHdr[2] & 0x3c) >> 2;
- }
- extern "C" u_int8_t MP4AV_AdtsFindSamplingRateIndex(u_int32_t samplingRate)
- {
- for (u_int8_t i = 0; i < NUM_ADTS_SAMPLING_RATES; i++) {
- if (samplingRate == AdtsSamplingRates[i]) {
- return i;
- }
- }
- return NUM_ADTS_SAMPLING_RATES - 1;
- }
- extern "C" u_int32_t MP4AV_AdtsGetSamplingRate(u_int8_t* pHdr)
- {
- return AdtsSamplingRates[MP4AV_AdtsGetSamplingRateIndex(pHdr)];
- }
- extern "C" u_int8_t MP4AV_AdtsGetChannels(u_int8_t* pHdr)
- {
- return ((pHdr[2] & 0x1) << 2) | ((pHdr[3] & 0xc0) >> 6);
- }
- extern "C" bool MP4AV_AdtsMakeFrameFromMp4Sample(
- MP4FileHandle mp4File,
- MP4TrackId trackId,
- MP4SampleId sampleId,
- u_int8_t** ppAdtsData,
- u_int32_t* pAdtsDataLength)
- {
- static MP4FileHandle lastMp4File = MP4_INVALID_FILE_HANDLE;
- static MP4TrackId lastMp4TrackId = MP4_INVALID_TRACK_ID;
- static bool isMpeg2;
- static u_int8_t profile;
- static u_int32_t samplingFrequency;
- static u_int8_t channels;
- if (mp4File != lastMp4File || trackId != lastMp4TrackId) {
- // changed cached file and track info
- lastMp4File = mp4File;
- lastMp4TrackId = trackId;
- u_int8_t audioType = MP4GetTrackAudioType(mp4File, trackId);
- if (MP4_IS_MPEG2_AAC_AUDIO_TYPE(audioType)) {
- isMpeg2 = true;
- profile = audioType - MP4_MPEG2_AAC_MAIN_AUDIO_TYPE;
- } else if (audioType == MP4_MPEG4_AUDIO_TYPE) {
- isMpeg2 = false;
- profile = MP4GetTrackAudioMpeg4Type(mp4File, trackId) - 1;
- } else {
- lastMp4File = MP4_INVALID_FILE_HANDLE;
- lastMp4TrackId = MP4_INVALID_TRACK_ID;
- return false;
- }
- u_int8_t* pConfig = NULL;
- u_int32_t configLength;
- MP4GetTrackESConfiguration(
- mp4File,
- trackId,
- &pConfig,
- &configLength);
- if (pConfig == NULL || configLength < 2) {
- lastMp4File = MP4_INVALID_FILE_HANDLE;
- lastMp4TrackId = MP4_INVALID_TRACK_ID;
- return false;
- }
- samplingFrequency = MP4AV_AacConfigGetSamplingRate(pConfig);
- channels = MP4AV_AacConfigGetChannels(pConfig);
- }
- bool rc;
- u_int8_t* pSample = NULL;
- u_int32_t sampleSize = 0;
- rc = MP4ReadSample(
- mp4File,
- trackId,
- sampleId,
- &pSample,
- &sampleSize);
- if (!rc) {
- return false;
- }
- rc = MP4AV_AdtsMakeFrame(
- pSample,
- sampleSize,
- isMpeg2,
- profile,
- samplingFrequency,
- channels,
- ppAdtsData,
- pAdtsDataLength);
- free(pSample);
- return rc;
- }
- extern "C" bool MP4AV_AdtsMakeFrame(
- u_int8_t* pData,
- u_int16_t dataLength,
- bool isMpeg2,
- u_int8_t profile,
- u_int32_t samplingFrequency,
- u_int8_t channels,
- u_int8_t** ppAdtsData,
- u_int32_t* pAdtsDataLength)
- {
- *pAdtsDataLength = (isMpeg2 ? 7 : 8) + dataLength;
- CMemoryBitstream adts;
- try {
- adts.AllocBytes(*pAdtsDataLength);
- *ppAdtsData = adts.GetBuffer();
- // build adts header
- adts.PutBits(0xFFF, 12); // syncword
- adts.PutBits(isMpeg2, 1); // id
- adts.PutBits(0, 2); // layer
- adts.PutBits(1, 1); // protection_absent
- adts.PutBits(profile, 2); // profile
- adts.PutBits(
- MP4AV_AdtsFindSamplingRateIndex(samplingFrequency),
- 4); // sampling_frequency_index
- adts.PutBits(0, 1); // private
- adts.PutBits(channels, 3); // channel_configuration
- adts.PutBits(0, 1); // original
- adts.PutBits(0, 1); // home
- adts.PutBits(0, 2); // emphasis
- adts.PutBits(0, 1); // copyright_id
- adts.PutBits(0, 1); // copyright_id_start
- adts.PutBits(*pAdtsDataLength, 13); // aac_frame_length
- adts.PutBits(0x7FF, 11); // adts_buffer_fullness
- adts.PutBits(1, 2); // num_raw_data_blocks
- // copy audio frame data
- adts.PutBytes(pData, dataLength);
- }
- catch (int e) {
- return false;
- }
- return true;
- }