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

📄 rfccrypto.cpp

📁 完整的RTP RTSP代码库
💻 CPP
📖 第 1 页 / 共 3 页
字号:
	u_int16_t maxPayloadSize,	char* PayloadMIMEType){  // gather information, and check for validity  u_int32_t numSamples =    MP4GetTrackNumberOfSamples(mp4File, mediaTrackId);  if (numSamples == 0) {    return false;  }  u_int32_t timeScale =    MP4GetTrackTimeScale(mp4File, mediaTrackId);  if (timeScale == 0) {    return false;  }  u_int8_t audioType =    MP4GetTrackEsdsObjectTypeId(mp4File, mediaTrackId);  if (audioType != MP4_MPEG4_AUDIO_TYPE      && !MP4_IS_AAC_AUDIO_TYPE(audioType)) {    return false;  }  u_int8_t mpeg4AudioType =    MP4GetTrackAudioMpeg4Type(mp4File, mediaTrackId);  if (audioType == MP4_MPEG4_AUDIO_TYPE) {    // check that track contains either MPEG-4 AAC or CELP    if (!MP4_IS_MPEG4_AAC_AUDIO_TYPE(mpeg4AudioType) 	&& mpeg4AudioType != MP4_MPEG4_CELP_AUDIO_TYPE) {      return false;    }  }  MP4Duration sampleDuration =     MP4AV_GetAudioSampleDuration(mp4File, mediaTrackId);  if (sampleDuration == MP4_INVALID_DURATION) {    return false;  }  /* get the ES configuration */  u_int8_t* pConfig = NULL;  u_int32_t configSize;  uint8_t channels;  MP4GetTrackESConfiguration(mp4File, mediaTrackId, &pConfig, 			     &configSize);  if (!pConfig) {    return false;  }       channels = MP4AV_AacConfigGetChannels(pConfig);  /* convert ES Config into ASCII form */  char* sConfig =     MP4BinaryToBase16(pConfig, configSize);  free(pConfig);  if (!sConfig) {    return false;  }  // now add the hint track  MP4TrackId hintTrackId =    MP4AddHintTrack(mp4File, mediaTrackId);  if (hintTrackId == MP4_INVALID_TRACK_ID) {    free(sConfig);    return false;  }  u_int8_t payloadNumber = MP4_SET_DYNAMIC_PAYLOAD;  char buffer[10];  if (channels != 1) {    snprintf(buffer, sizeof(buffer), "%u", channels);  }  MP4SetHintTrackRtpPayload(mp4File, hintTrackId, 			    (const char*)PayloadMIMEType, 			    &payloadNumber, 0, 			    channels != 1 ? buffer : NULL);  // moved this interleave check to here.  u_int32_t samplesPerPacket = 0;  if (interleave) {      u_int32_t maxSampleSize =      MP4GetTrackMaxSampleSize(mp4File, mediaTrackId);    // compute how many maximum size samples would fit in a packet    samplesPerPacket =       (maxPayloadSize - 2) / (maxSampleSize + 2);    // can't interleave if this number is 0 or 1    if (samplesPerPacket < 2) {      interleave = false;      // Since interleave is now false, reset delta IV length      // for the session to zero or headers will be wrong...AWV      // This needs to be done before the SDP is created. ...AWV      icPp->delta_iv_len = 0;    }   else       // set the delta IV length parameter to 2      // per the ismacryp specification (setting to 1 is too small)      icPp->delta_iv_len = 2;  }  // compute the ISMACryp configuration parameters  mjb  ISMACrypConfigTable_t ismac_table;  u_int16_t i;  memset(&ismac_table, 0, sizeof(ISMACrypConfigTable_t));  if(!InitISMACrypConfigTable(&ismac_table, icPp)){    free(sConfig);    return false;	}  char* sISMACrypConfig = NULL;  if (!MP4AV_RfcCryptoPolicyOk(&ismac_table)) {    free(sConfig);    for(i = 0; i < ismac_table.settings[ISMACRYP_KEY_COUNT];i++) {      free(ismac_table.keys[i]);		      free(ismac_table.salts[i]);	    }    return false;  }  if (!MP4AV_RfcCryptoConfigure(&ismac_table, &sISMACrypConfig)) {     free(sConfig);     return false;  }  int sdpBufLen = strlen(sConfig) + strlen(sISMACrypConfig) + ISMACRYP_SDP_ADDITIONAL_CONFIG_MAX_LEN;  char* sdpBuf = (char*)malloc(sdpBufLen);  if (!sdpBuf) {    free(sConfig);    free(sISMACrypConfig);    return false;  }  MP4Duration maxLatency;  bool OneByteHeader = false;  if (mpeg4AudioType == MP4_MPEG4_CELP_AUDIO_TYPE) {    snprintf(sdpBuf,             sdpBufLen,	    "a=fmtp:%u "	    "streamtype=5; profile-level-id=15; mode=CELP-vbr; "	    "config=%s; SizeLength=6; IndexLength=2; "	    "IndexDeltaLength=2; Profile=0;"	    "%s"	    "\015\012",	    payloadNumber,	    sConfig,	    sISMACrypConfig);     // 200 ms max latency for ISMA profile 1    maxLatency = timeScale / 5;    OneByteHeader = true;  } else { // AAC    snprintf(sdpBuf,             sdpBufLen,	    "a=fmtp:%u "	    "streamtype=5; profile-level-id=15; mode=AAC-hbr; "	    "config=%s; SizeLength=13; IndexLength=3; "	    "IndexDeltaLength=3; Profile=1;"	    "%s "                              //mjb	    "\015\012",	    payloadNumber,	    sConfig,	    sISMACrypConfig);     // 500 ms max latency for ISMA profile 1    maxLatency = timeScale / 2;  }  /* add this to the track's sdp */  MP4AppendHintTrackSdp(mp4File, hintTrackId, sdpBuf);  free(sConfig);  free(sdpBuf);  free(sISMACrypConfig);		//mjb  for(i = 0; i < ismac_table.settings[ISMACRYP_KEY_COUNT];i++) {    free(ismac_table.keys[i]);    free(ismac_table.salts[i]);	  }   // this is where the interleave check was....AWV  bool rc;  if (interleave) {    u_int32_t samplesPerGroup = maxLatency / sampleDuration;    u_int32_t stride;    stride = samplesPerGroup / samplesPerPacket;    if (OneByteHeader && stride > 3) stride = 3;    if (!OneByteHeader && stride > 7) stride = 7;#if 0    printf("max latency %llu sampleDuration %llu spg %u spp %u strid %u\n",                       maxLatency, sampleDuration, samplesPerGroup,                       samplesPerPacket, stride);#endif    rc = MP4AV_CryptoAudioInterleaveHinter(				     mp4File, 				     mediaTrackId, 				     hintTrackId,				     sampleDuration, 				     stride, // stride				     samplesPerPacket,		    // bundle				     maxPayloadSize,				     icPp);  } else {    rc = MP4AV_CryptoAudioConsecutiveHinter(				      mp4File, 				      mediaTrackId, 				      hintTrackId,				      sampleDuration, 				      2,				// perPacketHeaderSize				      2,				// perSampleHeaderSize				      maxLatency / sampleDuration,	// maxSamplesPerPacket				      maxPayloadSize,				      MP4GetSampleSize,				      icPp);  }  if (!rc) {    MP4DeleteTrack(mp4File, hintTrackId);    return false;  }  return true;}// based on MP4AV_Rfc3016Hinterextern "C" bool MP4AV_RfcCryptoVideoHinter(	MP4FileHandle mp4File, 	MP4TrackId mediaTrackId,         mp4av_ismacrypParams *icPp,	u_int16_t maxPayloadSize,	char* PayloadMIMEType){  u_int32_t numSamples = MP4GetTrackNumberOfSamples(mp4File, mediaTrackId);  u_int32_t maxSampleSize = MP4GetTrackMaxSampleSize(mp4File, mediaTrackId);	  if (numSamples == 0 || maxSampleSize == 0) {    return false;  }  MP4TrackId hintTrackId =    MP4AddHintTrack(mp4File, mediaTrackId);  if (hintTrackId == MP4_INVALID_TRACK_ID) {    return false;  }  u_int8_t payloadNumber = MP4_SET_DYNAMIC_PAYLOAD;  MP4SetHintTrackRtpPayload(mp4File, hintTrackId, 			    (const char*) PayloadMIMEType, &payloadNumber, 0);  /* get the mpeg4 video configuration */  u_int8_t* pConfig;  u_int32_t configSize;  u_int8_t systemsProfileLevel = 0xFE;  MP4GetTrackESConfiguration(mp4File, mediaTrackId, &pConfig, &configSize);  if (pConfig) {    // compute the ISMACryp configuration parameters  mjb    ISMACrypConfigTable_t ismac_table;    u_int16_t i;    memset(&ismac_table, 0, sizeof(ISMACrypConfigTable_t));    if(!InitISMACrypConfigTable(&ismac_table, icPp)){      return false;    }    char* sISMACrypConfig = NULL;    if (!MP4AV_RfcCryptoPolicyOk(&ismac_table)) {      for(i = 0; i < ismac_table.settings[ISMACRYP_KEY_COUNT];i++){	free(ismac_table.keys[i]);			free(ismac_table.salts[i]);	      }      return false;    }    if (!MP4AV_RfcCryptoConfigure(&ismac_table, &sISMACrypConfig))      return false;    // attempt to get a valid profile-level    static u_int8_t voshStartCode[4] = {       0x00, 0x00, 0x01, MP4AV_MPEG4_VOSH_START     };    if (configSize >= 5 && !memcmp(pConfig, voshStartCode, 4)) {      systemsProfileLevel = pConfig[4];    }     if (systemsProfileLevel == 0xFE) {      u_int8_t iodProfileLevel = MP4GetVideoProfileLevel(mp4File);      if (iodProfileLevel > 0 && iodProfileLevel < 0xFE) {	systemsProfileLevel = iodProfileLevel;      } else {	systemsProfileLevel = 1;      }    }     /* convert it into ASCII form */    char* sConfig = MP4BinaryToBase16(pConfig, configSize);    if (sConfig == NULL) {      MP4DeleteTrack(mp4File, hintTrackId);      free(sISMACrypConfig);      for(i = 0; i < ismac_table.settings[ISMACRYP_KEY_COUNT];i++) {	free(ismac_table.keys[i]);			free(ismac_table.salts[i]);	      }      return false;    }    int   sdpBufLen = strlen(sConfig) + strlen(sISMACrypConfig) + ISMACRYP_SDP_ADDITIONAL_CONFIG_MAX_LEN;    char* sdpBuf = (char*)malloc(sdpBufLen);    if (sdpBuf == NULL) {     free(sISMACrypConfig);     free(sConfig);     return false;    }    snprintf(sdpBuf,             sdpBufLen,	    "a=fmtp:%u profile-level-id=%u; mode=mpeg4-video; "	    "config=%s; %s; \015\012",	    payloadNumber,	    systemsProfileLevel,	    sConfig,	    sISMACrypConfig);     /* add this to the track's sdp */    MP4AppendHintTrackSdp(mp4File, hintTrackId, sdpBuf);    free(sConfig);    free(sdpBuf);    free(sISMACrypConfig);    for(i = 0; i < ismac_table.settings[ISMACRYP_KEY_COUNT];i++) {      free(ismac_table.keys[i]);		      free(ismac_table.salts[i]);	    }  }  u_int8_t* pSampleBuffer = (u_int8_t*)malloc(maxSampleSize);  if (pSampleBuffer == NULL) {    MP4DeleteTrack(mp4File, hintTrackId);    return false;  }    u_int8_t useSelectiveEnc = 0;  u_int8_t KIlen = 0;  u_int8_t IVlen = 0;  u_int8_t deltaIVlen = 0;  if (MP4AV_GetiSFMSettings(mp4File, mediaTrackId, &useSelectiveEnc, 			    &KIlen, &IVlen, false) == false) {    return false;  }  for (MP4SampleId sampleId = 1; sampleId <= numSamples; sampleId++) {    u_int32_t sampleSize = maxSampleSize;  // +IVlen +KIlen +1    MP4Timestamp startTime;    MP4Duration duration;    MP4Duration renderingOffset;    bool isSyncSample;    bool rc = MP4ReadSample(mp4File, mediaTrackId, sampleId, 			    &pSampleBuffer, &sampleSize, 			    &startTime, &duration, 			    &renderingOffset, &isSyncSample);    if (!rc) {      MP4DeleteTrack(mp4File, hintTrackId);      return false;    }    bool isBFrame =       (MP4AV_Mpeg4GetVopType(pSampleBuffer, sampleSize) == VOP_TYPE_B);    MP4AddRtpVideoHint(mp4File, hintTrackId, isBFrame, renderingOffset);    // comment from bill: may need to remove or put it in the header ??    if (sampleId == 1) {      MP4AddRtpESConfigurationPacket(mp4File, hintTrackId);    }    u_int32_t offset = 0;    u_int32_t remaining = sampleSize;    // TBD should scan for resync markers (if enabled in ES config)    // and packetize on those boundaries    while (remaining) {      bool isLastPacket = false;      u_int32_t length;      // need to add ismacryp AU header length       if (remaining <= maxPayloadSize) {	length = remaining;	isLastPacket = true;      } else {	length = maxPayloadSize;      }      MP4AddRtpPacket(mp4File, hintTrackId, isLastPacket);			      ismaCrypSampleHdrDataInfo_t *iCrypSampleHdrInfo = 	(ismaCrypSampleHdrDataInfo_t *) 	malloc (sizeof(ismaCrypSampleHdrDataInfo_t));      if (iCrypSampleHdrInfo == NULL)	return false;            memset(iCrypSampleHdrInfo, 0, sizeof(ismaCrypSampleHdrDataInfo_t));      u_int16_t ismaCrypAUHdrLen = 0;      bool rc = MP4AV_ProcessIsmaCrypHdrs(mp4File, mediaTrackId, 1, 					  &sampleId, useSelectiveEnc, 					  KIlen, IVlen, &deltaIVlen, 					  &ismaCrypAUHdrLen,					  &iCrypSampleHdrInfo, 					  icPp);            if (rc == false) {	// handle error	return false;      }      if (ismaCrypAUHdrLen > 0) {	// add AU hdr length	u_int8_t payloadHeader[2];	payloadHeader[0] = ismaCrypAUHdrLen >> 8;	payloadHeader[1] = ismaCrypAUHdrLen & 0xFF;	MP4AddRtpImmediateData(mp4File, hintTrackId,			       (u_int8_t*)&payloadHeader, sizeof(payloadHeader));	// add ismacryp AU headers	u_int32_t tmpSampleSize = maxSampleSize;	u_int8_t * pSampleBuffer = (u_int8_t *) malloc ((tmpSampleSize + IVlen + KIlen + 1)							* sizeof(u_int8_t));	if (pSampleBuffer == NULL)	  return false;		u_int8_t * pCurSampleBuf = pSampleBuffer;	bool rc2 = MP4ReadSample(mp4File, mediaTrackId, sampleId, 				 &pSampleBuffer, &tmpSampleSize);	if (rc2 == false) {	  // handle error	  return false;	}	if (iCrypSampleHdrInfo[0].hasEncField == 1) {	  MP4AddRtpImmediateData(mp4File, hintTrackId, pCurSampleBuf, 1);  	  pCurSampleBuf += 1;	} 	if (iCrypSampleHdrInfo[0].hasIVField == 1) {	  MP4AddRtpImmediateData(mp4File, hintTrackId, pCurSampleBuf, IVlen);	}	pCurSampleBuf += IVlen;	if (iCrypSampleHdrInfo[0].hasKIField == 1) {	  MP4AddRtpImmediateData(mp4File, hintTrackId, pCurSampleBuf, KIlen);	}	pCurSampleBuf += KIlen;	if (pSampleBuffer != NULL) {	  free(pSampleBuffer);	}	// remove size of ismaCryp sample header from the sample size	u_int32_t ismaCrypSampleHdrSize = MP4AV_GetIsmaCrypSampleHdrSize (iCrypSampleHdrInfo[0], 									  IVlen, KIlen);	sampleSize -= ismaCrypSampleHdrSize;      }      MP4AddRtpSampleData(mp4File, hintTrackId, sampleId, 			  offset, length);      offset += length;      remaining -= length;    }    MP4WriteRtpHint(mp4File, hintTrackId, duration, isSyncSample);  }  return true;}

⌨️ 快捷键说明

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