[vlc-commits] packetizer: h264: gather nals incrementally
Francois Cartegnie
git at videolan.org
Wed Mar 15 17:59:25 CET 2017
vlc | branch: master | Francois Cartegnie <fcvlcdev at free.fr> | Wed Mar 15 17:15:34 2017 +0100| [55428248fb06924d0b0fe522870e5628f1dd31d5] | committer: Francois Cartegnie
packetizer: h264: gather nals incrementally
allows to insert something else than sps/pps
and uses last block pointer
> http://git.videolan.org/gitweb.cgi/vlc.git/?a=commit;h=55428248fb06924d0b0fe522870e5628f1dd31d5
---
modules/packetizer/h264.c | 61 +++++++++++++++++++++++++++--------------------
1 file changed, 35 insertions(+), 26 deletions(-)
diff --git a/modules/packetizer/h264.c b/modules/packetizer/h264.c
index ee273e30..ae005e9 100644
--- a/modules/packetizer/h264.c
+++ b/modules/packetizer/h264.c
@@ -676,7 +676,8 @@ static block_t *ParseNALBlock( decoder_t *p_dec, bool *pb_ts_used, block_t *p_fr
static block_t *OutputPicture( decoder_t *p_dec )
{
decoder_sys_t *p_sys = p_dec->p_sys;
- block_t *p_pic;
+ block_t *p_pic = NULL;
+ block_t **pp_pic_last = &p_pic;
if ( !p_sys->b_header && p_sys->i_recovery_frames != -1 )
{
@@ -688,6 +689,12 @@ static block_t *OutputPicture( decoder_t *p_dec )
--p_sys->i_recovery_frames;
}
+ if( unlikely(!p_sys->p_frame) )
+ {
+ assert( p_sys->p_frame );
+ return NULL;
+ }
+
if( !p_sys->b_header && p_sys->i_recovery_frames == -1 &&
p_sys->slice.i_frame_type != BLOCK_FLAG_TYPE_I)
return NULL;
@@ -698,49 +705,51 @@ static block_t *OutputPicture( decoder_t *p_dec )
if( !p_pps || !p_sps )
return NULL;
+ /* Gather PPS/SPS if required */
+ block_t *p_xpsnal = NULL;
+ block_t **pp_xpsnal_tail = &p_xpsnal;
const bool b_sps_pps_i = p_sys->slice.i_frame_type == BLOCK_FLAG_TYPE_I &&
p_sys->p_active_pps &&
p_sys->p_active_sps;
if( b_sps_pps_i || p_sys->b_new_sps || p_sys->b_new_pps )
{
- block_t *p_head = NULL;
- if( p_sys->p_frame->i_flags & BLOCK_FLAG_PRIVATE_AUD )
- {
- p_head = p_sys->p_frame;
- p_sys->p_frame = p_sys->p_frame->p_next;
- if( p_sys->p_frame == NULL )
- p_sys->pp_frame_last = &p_sys->p_frame;
- p_head->p_next = NULL;
- }
-
- block_t *p_list = NULL;
- block_t **pp_list_tail = &p_list;
for( int i = 0; i <= H264_SPS_ID_MAX && (b_sps_pps_i || p_sys->b_new_sps); i++ )
{
if( p_sys->sps[i].p_block )
- block_ChainLastAppend( &pp_list_tail, block_Duplicate( p_sys->sps[i].p_block ) );
+ block_ChainLastAppend( &pp_xpsnal_tail, block_Duplicate( p_sys->sps[i].p_block ) );
}
for( int i = 0; i < H264_PPS_ID_MAX && (b_sps_pps_i || p_sys->b_new_pps); i++ )
{
if( p_sys->pps[i].p_block )
- block_ChainLastAppend( &pp_list_tail, block_Duplicate( p_sys->pps[i].p_block ) );
+ block_ChainLastAppend( &pp_xpsnal_tail, block_Duplicate( p_sys->pps[i].p_block ) );
}
- if( b_sps_pps_i && p_list )
+ if( b_sps_pps_i && p_xpsnal )
p_sys->b_header = true;
-
- if( p_list )
- block_ChainAppend( &p_head, p_list );
-
- if( p_sys->p_frame )
- block_ChainAppend( &p_head, p_sys->p_frame );
-
- p_pic = block_ChainGather( p_head );
}
- else
+
+ /* Now rebuild NAL Sequence, inserting PPS/SPS if any */
+ if( p_sys->p_frame->i_flags & BLOCK_FLAG_PRIVATE_AUD )
{
- p_pic = block_ChainGather( p_sys->p_frame );
+ block_t *p_au = p_sys->p_frame;
+ p_sys->p_frame = p_au->p_next;
+ p_au->p_next = NULL;
+ p_au->i_flags &= ~BLOCK_FLAG_PRIVATE_AUD;
+ block_ChainLastAppend( &pp_pic_last, p_au );
}
+ if( p_xpsnal )
+ block_ChainLastAppend( &pp_pic_last, p_xpsnal );
+
+ assert( p_sys->p_frame );
+ if( p_sys->p_frame )
+ block_ChainLastAppend( &pp_pic_last, p_sys->p_frame );
+
+ /* Reset chains, now empty */
+ p_sys->p_frame = NULL;
+ p_sys->pp_frame_last = &p_sys->p_frame;
+
+ p_pic = block_ChainGather( p_pic );
+
if( !p_pic )
return NULL;
More information about the vlc-commits
mailing list