Open fatalfeel opened 2 years ago
fixed way
bool AACSource::HandleFrame(MediaChannelId channel_id, AVFrame frame) { uint8_t* frame_buf = frame.buffer.get(); uint32_t frame_size = frame.size;
if (frame.timestamp == 0) {
GetTimestamp(&frame.timeNow, &frame.timestamp);
}
/*printf("sendto: %02x%02x%02x%02x %02x%02x%02x%02x%02x%02x%02x%02x\n\n",
*((unsigned char*)(frame_buf+0)),
*((unsigned char*)(frame_buf+1)),
*((unsigned char*)(frame_buf+2)),
*((unsigned char*)(frame_buf+3)),
*((unsigned char*)(frame_buf+4)),
*((unsigned char*)(frame_buf+5)),
*((unsigned char*)(frame_buf+6)),
*((unsigned char*)(frame_buf+7)),
*((unsigned char*)(frame_buf+8)),
*((unsigned char*)(frame_buf+9)),
*((unsigned char*)(frame_buf+10)),
*((unsigned char*)(frame_buf+11)));*/
/*if (frame.size > (MAX_RTP_PAYLOAD_SIZE-AU_SIZE)) {
return false;
}*/
int adts_size = 0;
if (has_adts_) {
adts_size = ADTS_SIZE;
}
/*struct AdtsHeader
{
unsigned int syncword; //12 bit 同步字 '1111 1111 1111',说明一个ADTS帧的开始
unsigned int id; //1 bit MPEG 标示符, 0 for MPEG-4,1 for MPEG-2
unsigned int layer; //2 bit 总是'00'
unsigned int protectionAbsent; //1 bit 1表示没有crc,0表示有crc
unsigned int profile; //2 bit 表示使用哪个级别的AAC
unsigned int samplingFreqIndex; //4 bit 表示使用的采样频率
unsigned int privateBit; //1 bit
unsigned int channelCfg; //3 bit 表示声道数
unsigned int originalCopy; //1 bit
unsigned int home; //1 bit
//下面的为改变的参数即每一帧都不同
unsigned int copyrightIdentificationBit; //1 bit
unsigned int copyrightIdentificationStart; //1 bit
unsigned int aacFrameLength; //13 bit 一个ADTS帧的长度包括ADTS头和AAC原始流
unsigned int adtsBufferFullness; //11 bit 0x7FF 说明是码率可变的码流
unsigned int numberOfRawDataBlockInFrame; //2 bit 有number_of_raw_data_blocks_in_frame + 1个AAC原始帧
};*/
frame_buf += adts_size;
frame_size -= adts_size;
char AU[AU_SIZE] = { 0 };
AU[0] = 0x00;
AU[1] = 0x10;
AU[2] = (frame_size & 0x1fe0) >> 5;
AU[3] = (frame_size & 0x1f) << 3;
/*RtpPacket rtp_pkt;
rtp_pkt.type = frame.type;
rtp_pkt.timestamp = frame.timestamp;
rtp_pkt.timeNow = frame.timeNow;
rtp_pkt.size = frame_size + RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + AU_SIZE;
rtp_pkt.last = 1;
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 0] = AU[0];
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 1] = AU[1];
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 2] = AU[2];
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 3] = AU[3];
memcpy(rtp_pkt.data.get()+RTP_TCP_HEAD_SIZE+RTP_HEADER_SIZE+AU_SIZE, frame_buf, frame_size);
if (send_frame_callback_) {
send_frame_callback_(channel_id, rtp_pkt);
}*/
while (frame_size + AU_SIZE > MAX_RTP_PAYLOAD_SIZE)
{
RtpPacket rtp_pkt;
rtp_pkt.type = frame.type;
rtp_pkt.timestamp = frame.timestamp;
rtp_pkt.timeNow = frame.timeNow;
rtp_pkt.size = RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + MAX_RTP_PAYLOAD_SIZE; //3 FU in
rtp_pkt.last = 0;
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 0] = AU[0];
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 1] = AU[1];
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 2] = AU[2];
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 3] = AU[3];
memcpy(rtp_pkt.data.get()+RTP_TCP_HEAD_SIZE+RTP_HEADER_SIZE+AU_SIZE, frame_buf, MAX_RTP_PAYLOAD_SIZE-AU_SIZE);
if (send_frame_callback_)
{
/*uint8_t* buff = rtp_pkt.data.get();
printf("case 2:");
for(int i=0; i<4; i++)
{
printf("%02x ", buff[i]);
}
printf("\n");*/
if (!send_frame_callback_(channel_id, rtp_pkt))
{
return false;
}
}
frame_buf += (MAX_RTP_PAYLOAD_SIZE - AU_SIZE);
frame_size -= (MAX_RTP_PAYLOAD_SIZE - AU_SIZE);
}
//final packet
{
RtpPacket rtp_pkt;
rtp_pkt.type = frame.type;
rtp_pkt.timestamp = frame.timestamp;
rtp_pkt.timeNow = frame.timeNow;
rtp_pkt.size = RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + AU_SIZE + frame_size;
rtp_pkt.last = 1;
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 0] = AU[0];
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 1] = AU[1];
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 2] = AU[2];
rtp_pkt.data.get()[RTP_TCP_HEAD_SIZE + RTP_HEADER_SIZE + 3] = AU[3];
memcpy(rtp_pkt.data.get()+RTP_TCP_HEAD_SIZE+RTP_HEADER_SIZE+AU_SIZE, frame_buf, frame_size);
if (send_frame_callback_)
{
if (!send_frame_callback_(channel_id, rtp_pkt))
{
return false;
}
}
}
return true;
}
here is are links you can download it http://fatalfeel.blogspot.com/2013/12/rtsp-server-for-h264-h265-aac.html
when aac file some packet is over than MAX_RTP_PAYLOAD_SIZE-AU_SIZE its need like H264Source H265Source piece by piece send