⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 latm.cpp

📁 完整的RTP RTSP代码库
💻 CPP
字号:
/* * 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. 2001.  All Rights Reserved. *  * Contributor(s):  *              Bill May        wmay@cisco.com */#include "latm.h"#include "mp4util/mpeg4_audio_config.h"#include "rtp/rtp.h"//#define DEBUG_LATM_AAC#define latm_message iptr->m_vft->log_msgstatic const char *latmrtp="latmrtp";static rtp_check_return_t check (lib_message_func_t msg, 				 format_list_t *fmt, 				 uint8_t rtp_payload_type,				 CConfigSet *pConfig){  if (fmt == NULL || fmt->rtpmap_name == NULL)     return RTP_PLUGIN_NO_MATCH;  if (strcasecmp(fmt->rtpmap_name, "mp4a-latm") != 0) {    return RTP_PLUGIN_NO_MATCH;  }  fmtp_parse_t *fmtp;  int len, cpresent;  fmtp = parse_fmtp_for_rfc3016(fmt->fmt_param, msg);  if (fmtp == NULL) {    (msg)(LOG_ERR, latmrtp, "Couldn't parse fmtp");    return RTP_PLUGIN_NO_MATCH;  }  len = fmtp->config_binary_len;  cpresent = fmtp->cpresent;  free_fmtp_parse(fmtp);  if (len == 0 || cpresent != 0) {    (msg)(LOG_ERR, latmrtp, "%s len %u cpresent %u", fmt->rtpmap_name,	  len, cpresent);    return RTP_PLUGIN_NO_MATCH;  }  return RTP_PLUGIN_MATCH;}/* * latm rtp bytestream has a potential set of headers at the beginning * of each rtp frame.  This can interleave frames in different packets */rtp_plugin_data_t *latm_rtp_plugin_create (format_list_t *media_fmt,					   uint8_t rtp_payload_type, 					   rtp_vft_t *vft,					   void *ifptr){  latm_rtp_data_t *iptr;    iptr = MALLOC_STRUCTURE(latm_rtp_data_t);  memset(iptr, 0, sizeof(latm_rtp_data_t));  iptr->m_vft = vft;  iptr->m_ifptr = ifptr;  return (&iptr->plug);}static void latm_rtp_destroy (rtp_plugin_data_t *pifptr){  latm_rtp_data_t *iptr = (latm_rtp_data_t *)pifptr;  if (iptr->m_rpak != NULL) {    (iptr->m_vft->free_pak)(iptr->m_rpak);    iptr->m_rpak = NULL;  }  CHECK_AND_FREE(iptr->m_frag_buffer);#ifdef LATM_RTP_DUMP_OUTPUT_TO_FILE  fclose(iptr->m_outfile);#endif  free(iptr);}static bool start_next_frame (rtp_plugin_data_t *pifptr, 			      uint8_t **buffer, 			      uint32_t *buflen,			      frame_timestamp_t *ts,			      void **userdata){  latm_rtp_data_t *iptr = (latm_rtp_data_t *)pifptr;  uint64_t timetick;  rtp_packet *rpak;  uint32_t rtp_ts;  uint8_t *dptr;  uint32_t dlen;  uint32_t calc_len;  uint64_t ntp_ts;  if (iptr->m_rpak != NULL) {    (iptr->m_vft->free_pak)(iptr->m_rpak);    iptr->m_rpak = NULL;  }  rpak = (iptr->m_vft->get_head_and_check)(iptr->m_ifptr, false, 0);  if (rpak == NULL) return false;  dlen = rpak->rtp_data_len;  dptr = rpak->rtp_data;  rtp_ts = rpak->rtp_pak_ts;  ntp_ts = rpak->pd.rtp_pd_timestamp;  calc_len = 0;  uint8_t value;  do {    value = *dptr++;    calc_len += value;    dlen--;  } while (value == 0xff);#if 0  latm_message(LOG_DEBUG, latmrtp, "len %u header %u", 	       calc_len, rpak->rtp_data_len - dlen);#endif  if (rpak->rtp_pak_m != 0) {    // just one packet - we should have frame length    if (calc_len != dlen) {      latm_message(LOG_ERR, latmrtp, "header length not correct %u %u", 		   calc_len, dlen);      return false;    }        iptr->m_rpak = rpak;    *buffer = dptr;    *buflen = dlen;  } else {    if (calc_len > iptr->m_frag_buffer_len) {      iptr->m_frag_buffer = (uint8_t *)realloc(iptr->m_frag_buffer, calc_len);      iptr->m_frag_buffer_len = calc_len;    }    memcpy(iptr->m_frag_buffer, dptr, dlen);    calc_len -= dlen;    uint32_t offset = dlen;    (iptr->m_vft->free_pak)(rpak);    do {      rpak = iptr->m_vft->get_head_and_check(iptr->m_ifptr,					     true, 					     rtp_ts);      if (rpak == NULL) return false;      if (calc_len < rpak->rtp_data_len) {	latm_message(LOG_ERR, latmrtp, "Illegal frag len - remaining %u pak len %u", calc_len, rpak->rtp_data_len);	return false;      }      memcpy(iptr->m_frag_buffer + offset,	     rpak->rtp_data,	     rpak->rtp_data_len);      calc_len -= rpak->rtp_data_len;      offset += rpak->rtp_data_len;    } while (calc_len > 0);  }      timetick = iptr->m_vft->rtp_ts_to_msec(iptr->m_ifptr, 					 rtp_ts, 					 ntp_ts, 					 0);  ts->audio_freq_timestamp = rtp_ts;  ts->msec_timestamp = timetick;  ts->timestamp_is_pts = true;  return (true);}static void used_bytes_for_frame (rtp_plugin_data_t *pifptr, uint32_t bytes){}static void reset (rtp_plugin_data_t *pifptr){}static void flush_rtp_packets (rtp_plugin_data_t *pifptr){}static bool have_frame (rtp_plugin_data_t *pifptr){  latm_rtp_data_t *iptr = (latm_rtp_data_t *)pifptr;  return (iptr->m_vft->find_mbit)(iptr->m_ifptr);}RTP_PLUGIN("mpeg4-latm", 	   check,	   latm_rtp_plugin_create,	   latm_rtp_destroy,	   start_next_frame, 	   used_bytes_for_frame,	   reset, 	   flush_rtp_packets,	   have_frame,	   NULL,	   0);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -