Files
gb28181/GB28181Device/rtp/ps.cpp
2024-12-15 20:42:32 +08:00

390 lines
9.2 KiB
C++

/***************************************************************************************
*
* IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
*
* By downloading, copying, installing or using the software you agree to this license.
* If you do not agree to this license, do not download, install,
* copy or use the software.
*
* Copyright (C) 2014-2022, Happytimesoft Corporation, all rights reserved.
*
* Redistribution and use in binary forms, with or without modification, are permitted.
*
* Unless required by applicable law or agreed to in writing, software distributed
* under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
* CONDITIONS OF ANY KIND, either express or implied. See the License for the specific
* language governing permissions and limitations under the License.
*
****************************************************************************************/
#include "sys_inc.h"
#include "rtp.h"
#include "ps.h"
/********************************************************************/
void ps_init_header(PSHDR * ps_h)
{
if (ps_h == 0)
{
return;
}
ps_h->system_header_start_code[0] = 0x00;
ps_h->system_header_start_code[1] = 0x00;
ps_h->system_header_start_code[2] = 0x01;
ps_h->system_header_start_code[3] = 0xBA;
ps_h->fix_bit = 0x01;
ps_h->marker_bit = 0x01;
ps_h->marker_bit1 = 0x01;
ps_h->marker_bit2 = 0x01;
ps_h->marker_bit3 = 0x01;
ps_h->marker_bit4 = 0x01;
ps_h->marker_bit5 = 0x01;
ps_h->reserved = 0x1F;
ps_h->pack_stuffing_length = 0x00;
ps_h->system_clock_reference_extension1 = 0;
ps_h->system_clock_reference_extension2 = 0;
ps_h->program_mux_rate1 = 0x00;
ps_h->program_mux_rate2 = 0x5F;
ps_h->program_mux_rate3 = 0x1A;
}
void ps_init_system_header(PSSYSHDR * sys_h)
{
if (sys_h == NULL)
{
return;
}
sys_h->system_header_start_code[0] = 0x00;
sys_h->system_header_start_code[1] = 0x00;
sys_h->system_header_start_code[2] = 0x01;
sys_h->system_header_start_code[3] = 0xBB;
sys_h->header_length[0] = 0x00;
sys_h->header_length[1] = 0x0C;
sys_h->rate_bound1 = 0x00;
sys_h->rate_bound2 = 0xCC;
sys_h->rate_bound3 = 0x7A;
sys_h->marker_bit = 0x01;
sys_h->marker_bit1 = 0x01;
sys_h->csps_flag = 0x00;
sys_h->fixed_flag = 0x00;
sys_h->audio_bound = 0x01;
sys_h->video_bound = 0x01;
sys_h->marker_bit2 = 0x01;
sys_h->video_lock_flag = 0x01;
sys_h->audio_lock_flag = 0x01;
sys_h->reserved = 0x7F;
sys_h->stream_id1 = 0xE0;
sys_h->std_buffer_size_bound11 = 0x00;
sys_h->std_buffer_bound_scale1 = 0x01;
sys_h->marker_bit13 = 0x03;
sys_h->std_buffer_size_bound12 = 0xE8;
sys_h->stream_id2 = 0xC0;
sys_h->std_buffer_size_bound21 = 0x00;
sys_h->std_buffer_bound_scale2 = 0x00;
sys_h->marker_bit23 = 0x03;
sys_h->std_buffer_size_bound22 = 0x20;
}
/*
* vtype : 0x1B - h264; 0x24 - h265; 0x10 - MPEG-4; 0x80 - SVAC
* atype : 0x90 - G711; 0X92 - G722.1; 0X93 - G723.1; 0X99 - G729; 0X9B - SVAC; 0x0f - AAC
*/
void ps_init_system_map(PSSYSMAP * sys_m, int vtype, int atype)
{
if (sys_m == NULL)
{
return;
}
sys_m->packet_start_code_prefix[0] = 0x00;
sys_m->packet_start_code_prefix[1] = 0x00;
sys_m->packet_start_code_prefix[2] = 0x01;
sys_m->map_stream_id = 0xBC;
sys_m->program_stream_map_length[0] = 0x00;
sys_m->program_stream_map_length[1] = 0x12;
sys_m->current_next_indicator = 0x01;
sys_m->reserved1 = 0x03;
sys_m->program_stream_map_version = 0x01;
sys_m->reserved2 = 0x7F;
sys_m->marker_bit = 0x01;
sys_m->program_stream_info_length[0] = 0x00;
sys_m->program_stream_info_length[1] = 0x00;
sys_m->elementary_stream_map_length[0] = 0x00;
sys_m->elementary_stream_map_length[1] = 0x08;
sys_m->stream_type1 = vtype; // 0x1B - h264; 0x24 - h265; 0x10 - MPEG-4; 0x80 - SVAC
sys_m->elementary_stream_id1 = 0xE0;
sys_m->elementary_stream_info_length1[0] = 0x00;
sys_m->elementary_stream_info_length1[1] = 0x00;
sys_m->stream_type2 = atype; // 0x90 - G711; 0X92 - G722.1; 0X93 - G723.1; 0X99 - G729; 0X9B - SVAC; 0x0f - AAC
sys_m->elementary_stream_id2 = 0xC0;
sys_m->elementary_stream_info_length2[0] = 0x00;
sys_m->elementary_stream_info_length2[1] = 0x00;
sys_m->crc32[0] = 0x00;
sys_m->crc32[1] = 0x00;
sys_m->crc32[2] = 0x00;
sys_m->crc32[3] = 0x00;
}
void ps_init_pes_header(PESHDR * pes_h)
{
pes_h->packet_start_code_prefix[0] = 0x00;
pes_h->packet_start_code_prefix[1] = 0x00;
pes_h->packet_start_code_prefix[2] = 0x01;
pes_h->PES_packet_length[0] = 0x00;
pes_h->PES_packet_length[1] = 0x00;
pes_h->stream_id = 0xE0;
pes_h->original_or_copy = 0;
pes_h->copyright = 0;
pes_h->data_alignment_indicator = 0;
pes_h->PES_priority = 1;
pes_h->PES_scrambling_control = 0;
pes_h->fix_bit = 0x02;
pes_h->PES_extension_flag = 0;
pes_h->PES_CRC_flag = 0;
pes_h->additional_copy_info_flag = 0;
pes_h->DSM_trick_mode_flag = 0;
pes_h->ES_rate_flag = 0;
pes_h->ESCR_flag = 0;
pes_h->PTS_DTS_flags = 0x02;
pes_h->PES_header_data_length = 0x05;
}
void ps_init_pts_tag(PPTS_TAG pts_t)
{
if (pts_t == NULL)
{
return;
}
pts_t->fix_bit = 0x02;
pts_t->marker_bit = 0x01;
pts_t->marker_bit1 = 0x01;
pts_t->marker_bit2 = 0x01;
}
/*
* vtype : 0x1B - h264; 0x24 - h265; 0x10 - MPEG-4; 0x80 - SVAC
* atype : 0x90 - G711; 0X92 - G722.1; 0X93 - G723.1; 0X99 - G729; 0X9B - SVACss
*/
void ps_init_info(PSPKTI * ps_pkt_i, int vtype, int atype)
{
if (ps_pkt_i == NULL)
{
return;
}
if (ps_pkt_i->init_flag == 1)
{
return;
}
ps_pkt_i->scr = 0;
ps_pkt_i->pts = 0;
ps_init_header(&ps_pkt_i->ePSHeader);
ps_init_system_header(&ps_pkt_i->ePSSHeader);
ps_init_system_map(&ps_pkt_i->ePSMHeader, vtype, atype);
ps_init_pes_header(&ps_pkt_i->ePESHeader);
ps_init_pts_tag(&ps_pkt_i->ePTS);
ps_pkt_i->init_flag = 1;
}
int ps_get_pes_size()
{
return 9;
}
int ps_get_pts_size()
{
return 5;
}
void ps_set_pts(PPTS_TAG pts_t, uint32 pts)
{
if (pts_t == NULL)
{
return;
}
pts_t->PTS1 = (pts >> 30) & 0x07;
pts_t->PTS21 = (pts >> 22) & 0xFF;
pts_t->PTS22 = (pts >> 15) & 0x7F;
pts_t->PTS31 = (pts >> 7) & 0xFF;
pts_t->PTS32 = pts & 0x7F;
}
int ps_make_pes_header(PSPKTI * ps_pkt_i, uint8 * header, uint32 framelen, uint32 * pusedlen)
{
uint32 pes_len = ps_get_pes_size() + ps_get_pts_size() - 6;
uint16 sDataLen = 0;
uint32 tatol_len = 65535 - 100;
if (pes_len + framelen > tatol_len)
{
sDataLen = tatol_len;
*pusedlen = tatol_len - pes_len;
}
else
{
sDataLen = pes_len + framelen;
*pusedlen = framelen;
}
ps_pkt_i->ePESHeader.PES_packet_length[0] = sDataLen >> 8;
ps_pkt_i->ePESHeader.PES_packet_length[1] = sDataLen & 0xFF;
memcpy(header, &ps_pkt_i->ePESHeader, ps_get_pes_size());
ps_set_pts(&ps_pkt_i->ePTS, ps_pkt_i->pts);
memcpy(header + ps_get_pes_size(), &ps_pkt_i->ePTS, ps_get_pts_size());
return ps_get_pes_size() + ps_get_pts_size();
}
int ps_get_header_size()
{
return 14;
}
void ps_set_system_clock_reference_base(PSHDR * ps_h, uint32 scr)
{
if (ps_h == NULL)
{
return;
}
ps_h->system_clock_reference_base1 = (scr >> 30) & 0x07;
ps_h->system_clock_reference_base21 = (scr >> 28) & 0x03;
ps_h->system_clock_reference_base22 = (scr >> 20) & 0xFF;
ps_h->system_clock_reference_base23 = (scr >> 15) & 0x1F;
ps_h->system_clock_reference_base31 = (scr >> 13) & 0x03;
ps_h->system_clock_reference_base32 = (scr >> 5) & 0xFF;
ps_h->system_clock_reference_base33 = scr & 0x1F;
}
int ps_make_packet_header(PSPKTI * ps_pkt_i, uint8 *header)
{
ps_set_system_clock_reference_base(&ps_pkt_i->ePSHeader, ps_pkt_i->scr);
memcpy(header, &ps_pkt_i->ePSHeader, ps_get_header_size());
return ps_get_header_size();
}
int ps_get_system_header_size()
{
return 18;
}
int ps_make_system_header(PSPKTI * ps_pkt_i, uint8 *header)
{
memcpy(header, &ps_pkt_i->ePSSHeader, ps_get_system_header_size());
return ps_get_system_header_size();
}
int ps_get_system_map_size()
{
return 24;
}
int ps_make_system_map(PSPKTI * ps_pkt_i, uint8 *header)
{
memcpy(header, &ps_pkt_i->ePSMHeader, ps_get_system_map_size());
return ps_get_system_map_size();
}
int ps_make_header(PSPKTI * ps_pkt_i, uint8 * header, uint32 framelen, uint32 ts, int frametype, uint32 * pusedlen)
{
int offset = 0;
if (ps_pkt_i == NULL)
{
return 0;
}
if (frametype == 1 || frametype == 3) // 1 3 视频帧
{
ps_pkt_i->pts = ts;
ps_pkt_i->scr = ps_pkt_i->pts;
offset = ps_make_packet_header(ps_pkt_i, header);
// I帧增加系统头和map头
if (frametype == 3)
{
offset += ps_make_system_header(ps_pkt_i, header + offset);
offset += ps_make_system_map(ps_pkt_i, header + offset);
}
ps_pkt_i->ePESHeader.stream_id = 0xE0;
offset += ps_make_pes_header(ps_pkt_i, header + offset, framelen, pusedlen);
}
else if (frametype == 2) // 2 音频帧
{
ps_pkt_i->pts = ts;
ps_pkt_i->scr = ps_pkt_i->pts;
offset = ps_make_packet_header(ps_pkt_i, header);
ps_pkt_i->ePESHeader.stream_id = 0xC0;
offset += ps_make_pes_header(ps_pkt_i, header + offset, framelen, pusedlen);
}
else if (frametype == 4) // 4 前一个视频包的拆分包
{
ps_pkt_i->ePESHeader.stream_id = 0xE0;
offset += ps_make_pes_header(ps_pkt_i, header + offset, framelen, pusedlen);
}
else if (frametype == 5) // 5 前一个音频包的拆分包
{
ps_pkt_i->ePESHeader.stream_id = 0xC0;
offset = ps_make_pes_header(ps_pkt_i, header + offset, framelen, pusedlen);
}
return offset;
}