Coverage Report

Created: 2026-04-12 07:27

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/vlc/modules/packetizer/hevc.c
Line
Count
Source
1
/*****************************************************************************
2
 * hevc.c: h.265/hevc video packetizer
3
 *****************************************************************************
4
 * Copyright (C) 2014 VLC authors and VideoLAN
5
 *
6
 * Authors: Denis Charmet <typx@videolan.org>
7
 *
8
 * This program is free software; you can redistribute it and/or modify it
9
 * under the terms of the GNU Lesser General Public License as published by
10
 * the Free Software Foundation; either version 2.1 of the License, or
11
 * (at your option) any later version.
12
 *
13
 * This program is distributed in the hope that it will be useful,
14
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16
 * GNU Lesser General Public License for more details.
17
 *
18
 * You should have received a copy of the GNU Lesser General Public License
19
 * along with this program; if not, write to the Free Software Foundation,
20
 * Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
21
 *****************************************************************************/
22
23
/*****************************************************************************
24
 * Preamble
25
 *****************************************************************************/
26
27
#ifdef HAVE_CONFIG_H
28
# include "config.h"
29
#endif
30
31
#include <vlc_common.h>
32
#include <vlc_plugin.h>
33
#include <vlc_codec.h>
34
#include <vlc_block.h>
35
#include <vlc_bits.h>
36
37
#include <vlc_block_helper.h>
38
#include "packetizer_helper.h"
39
#include "startcode_helper.h"
40
#include "hevc_nal.h"
41
#include "hxxx_nal.h"
42
#include "hxxx_sei.h"
43
#include "hxxx_common.h"
44
45
#include <limits.h>
46
47
/*****************************************************************************
48
 * Module descriptor
49
 *****************************************************************************/
50
static int  Open (vlc_object_t *);
51
static void Close(vlc_object_t *);
52
53
116
vlc_module_begin ()
54
58
    set_subcategory(SUBCAT_SOUT_PACKETIZER)
55
58
    set_description(N_("HEVC/H.265 video packetizer"))
56
58
    set_capability("video packetizer", 50)
57
116
    set_callbacks(Open, Close)
58
58
vlc_module_end ()
59
60
61
/****************************************************************************
62
 * Local prototypes
63
 ****************************************************************************/
64
struct hevc_tuple_s
65
{
66
    block_t *p_nal;
67
    void *p_decoded;
68
};
69
70
typedef struct
71
{
72
    /* */
73
    packetizer_t packetizer;
74
75
    struct
76
    {
77
        block_t *p_chain;
78
        block_t **pp_chain_last;
79
    } frame, pre, post;
80
81
    uint8_t  i_nal_length_size;
82
83
    struct hevc_tuple_s rg_vps[HEVC_MAX_NUM_VPS],
84
                        rg_sps[HEVC_MAX_NUM_SPS],
85
                        rg_pps[HEVC_MAX_NUM_PPS];
86
87
    const hevc_video_parameter_set_t    *p_active_vps;
88
    const hevc_sequence_parameter_set_t *p_active_sps;
89
    const hevc_picture_parameter_set_t  *p_active_pps;
90
    enum
91
    {
92
        MISSING = 0,
93
        COMPLETE,
94
        SENT,
95
    } sets;
96
    /* Recovery starts from IFRAME or SEI recovery point */
97
    bool b_recovery_point;
98
99
    hevc_sei_pic_timing_t *p_timing;
100
101
    date_t dts;
102
    vlc_tick_t pts;
103
    bool b_need_ts;
104
105
    /* */
106
    cc_storage_t *p_ccs;
107
} decoder_sys_t;
108
109
static block_t *PacketizeAnnexB(decoder_t *, block_t **);
110
static block_t *PacketizeHVC1(decoder_t *, block_t **);
111
static void PacketizeFlush( decoder_t * );
112
static void PacketizeReset(void *p_private, bool b_broken);
113
static block_t *PacketizeParse(void *p_private, bool *pb_ts_used, block_t *);
114
static block_t *ParseNALBlock(decoder_t *, bool *pb_ts_used, block_t *);
115
static inline block_t *ParseNALBlockW( void *opaque, bool *pb_ts_used, block_t *p_frag )
116
2.41k
{
117
2.41k
    return ParseNALBlock( (decoder_t *) opaque, pb_ts_used, p_frag );
118
2.41k
}
119
static int PacketizeValidate(void *p_private, block_t *);
120
static block_t * PacketizeDrain(void *);
121
static bool ParseSEICallback( const hxxx_sei_data_t *, void * );
122
static block_t *GetCc( decoder_t *, decoder_cc_desc_t * );
123
static block_t *GetXPSCopy(decoder_sys_t *);
124
125
48.1M
#define BLOCK_FLAG_DROP (1 << BLOCK_FLAG_PRIVATE_SHIFT)
126
127
/****************************************************************************
128
 * Helpers
129
 ****************************************************************************/
130
static inline void InitQueue( block_t **pp_head, block_t ***ppp_tail )
131
17.8M
{
132
17.8M
    *pp_head = NULL;
133
17.8M
    *ppp_tail = pp_head;
134
17.8M
}
135
17.8M
#define INITQ(name) InitQueue(&p_sys->name.p_chain, &p_sys->name.pp_chain_last)
136
137
static block_t * OutputQueues(decoder_sys_t *p_sys, bool b_valid)
138
17.0M
{
139
17.0M
    block_t *p_output = NULL;
140
17.0M
    block_t *p_xps = NULL;
141
17.0M
    block_t **pp_output_last = &p_output;
142
17.0M
    uint32_t i_flags = 0; /* Because block_ChainGather does not merge flags or times */
143
144
17.0M
    if(p_sys->b_recovery_point && p_sys->sets != SENT)
145
207k
        p_xps = GetXPSCopy(p_sys);
146
147
17.0M
    if(p_sys->pre.p_chain)
148
2.99M
    {
149
2.99M
        i_flags |= p_sys->pre.p_chain->i_flags;
150
151
2.99M
        if(p_sys->pre.p_chain->i_buffer >= 5 &&
152
2.99M
            hevc_getNALType(&p_sys->pre.p_chain->p_buffer[4]) == HEVC_NAL_AUD)
153
913k
        {
154
913k
            block_t *p_au = p_sys->pre.p_chain;
155
913k
            p_sys->pre.p_chain = p_sys->pre.p_chain->p_next;
156
913k
            p_au->p_next = NULL;
157
913k
            block_ChainLastAppend(&pp_output_last, p_au);
158
913k
        }
159
160
2.99M
        if(p_xps)
161
16.5k
            block_ChainLastAppend(&pp_output_last, p_xps);
162
163
2.99M
        if(p_sys->pre.p_chain)
164
2.71M
            block_ChainLastAppend(&pp_output_last, p_sys->pre.p_chain);
165
2.99M
        INITQ(pre);
166
2.99M
    }
167
14.0M
    else if(p_xps)
168
106k
    {
169
106k
        block_ChainLastAppend(&pp_output_last, p_xps);
170
106k
    }
171
172
17.0M
    if(p_sys->frame.p_chain)
173
7.90M
    {
174
7.90M
        i_flags |= p_sys->frame.p_chain->i_flags;
175
7.90M
        block_ChainLastAppend(&pp_output_last, p_sys->frame.p_chain);
176
7.90M
        p_output->i_dts = date_Get(&p_sys->dts);
177
7.90M
        p_output->i_pts = p_sys->pts;
178
7.90M
        INITQ(frame);
179
7.90M
    }
180
181
17.0M
    if(p_sys->post.p_chain)
182
6.91M
    {
183
6.91M
        i_flags |= p_sys->post.p_chain->i_flags;
184
6.91M
        block_ChainLastAppend(&pp_output_last, p_sys->post.p_chain);
185
6.91M
        INITQ(post);
186
6.91M
    }
187
188
17.0M
    if(p_output)
189
15.7M
    {
190
15.7M
        p_output->i_flags |= i_flags;
191
15.7M
        if(!b_valid)
192
13.0M
            p_output->i_flags |= BLOCK_FLAG_DROP;
193
15.7M
    }
194
195
17.0M
    return p_output;
196
17.0M
}
197
198
199
/*****************************************************************************
200
 * Open
201
 *****************************************************************************/
202
static int Open(vlc_object_t *p_this)
203
85.2k
{
204
85.2k
    decoder_t     *p_dec = (decoder_t*)p_this;
205
85.2k
    decoder_sys_t *p_sys;
206
207
85.2k
    if (p_dec->fmt_in->i_codec != VLC_CODEC_HEVC)
208
62.8k
        return VLC_EGENERIC;
209
210
22.4k
    p_dec->p_sys = p_sys = calloc(1, sizeof(decoder_sys_t));
211
22.4k
    if (!p_dec->p_sys)
212
0
        return VLC_ENOMEM;
213
214
22.4k
    p_sys->p_ccs = cc_storage_new();
215
22.4k
    if(unlikely(!p_sys->p_ccs))
216
0
    {
217
0
        free(p_dec->p_sys);
218
0
        return VLC_ENOMEM;
219
0
    }
220
221
22.4k
    INITQ(pre);
222
22.4k
    INITQ(frame);
223
22.4k
    INITQ(post);
224
225
22.4k
    packetizer_Init(&p_sys->packetizer,
226
22.4k
                    annexb_startcode3, 3, startcode_FindAnnexB,
227
22.4k
                    annexb_startcode3, 1, 5,
228
22.4k
                    PacketizeReset, PacketizeParse, PacketizeValidate, PacketizeDrain,
229
22.4k
                    p_dec);
230
231
    /* Copy properties */
232
22.4k
    es_format_Copy(&p_dec->fmt_out, p_dec->fmt_in);
233
22.4k
    p_dec->fmt_out.b_packetized = true;
234
235
    /* Init timings */
236
22.4k
    if( p_dec->fmt_in->video.i_frame_rate_base &&
237
1.61k
        p_dec->fmt_in->video.i_frame_rate &&
238
1.56k
        p_dec->fmt_in->video.i_frame_rate <= UINT_MAX / 2 )
239
1.56k
        date_Init( &p_sys->dts, p_dec->fmt_in->video.i_frame_rate * 2,
240
1.56k
                                p_dec->fmt_in->video.i_frame_rate_base );
241
20.8k
    else
242
20.8k
        date_Init( &p_sys->dts, 2 * 30000, 1001 );
243
22.4k
    p_sys->pts = VLC_TICK_INVALID;
244
22.4k
    p_sys->b_need_ts = true;
245
22.4k
    p_sys->sets = MISSING;
246
247
    /* Set callbacks */
248
22.4k
    const uint8_t *p_extra = p_dec->fmt_in->p_extra;
249
22.4k
    const size_t i_extra = p_dec->fmt_in->i_extra;
250
    /* Check if we have hvcC as extradata */
251
22.4k
    if(hevc_ishvcC(p_extra, i_extra))
252
960
    {
253
960
        uint8_t *p_new_extra;
254
960
        size_t i_new_extra;
255
960
        if(!hevc_hvcC_to_AnnexB_NAL(p_extra, i_extra,
256
960
                                    &p_new_extra, &i_new_extra,
257
960
                                    &p_sys->i_nal_length_size))
258
280
        {
259
280
            msg_Err( p_dec, "Invalid HVCC extradata");
260
280
            Close( VLC_OBJECT(p_dec) );
261
280
            return VLC_EGENERIC;
262
280
        }
263
        /* Clear hvcC/HVC1 extra, to be replaced with AnnexB */
264
680
        free(p_dec->fmt_out.p_extra);
265
680
        p_dec->fmt_out.p_extra = p_new_extra;
266
680
        p_dec->fmt_out.i_extra = i_new_extra;
267
680
        p_dec->pf_packetize = PacketizeHVC1;
268
680
    }
269
21.4k
    else
270
21.4k
    {
271
21.4k
        p_dec->pf_packetize = PacketizeAnnexB;
272
21.4k
    }
273
22.1k
    p_dec->pf_flush = PacketizeFlush;
274
22.1k
    p_dec->pf_get_cc = GetCc;
275
276
22.1k
    if(p_dec->fmt_out.i_extra)
277
5.47k
    {
278
        /* Feed with AnnexB VPS/SPS/PPS/SEI extradata */
279
5.47k
        packetizer_Header(&p_sys->packetizer,
280
5.47k
                          p_dec->fmt_out.p_extra, p_dec->fmt_out.i_extra);
281
5.47k
    }
282
283
22.1k
    return VLC_SUCCESS;
284
22.4k
}
285
286
/*****************************************************************************
287
 * Close
288
 *****************************************************************************/
289
static void Close(vlc_object_t *p_this)
290
22.4k
{
291
22.4k
    decoder_t *p_dec = (decoder_t*)p_this;
292
22.4k
    decoder_sys_t *p_sys = p_dec->p_sys;
293
22.4k
    packetizer_Clean(&p_sys->packetizer);
294
295
22.4k
    block_ChainRelease(p_sys->frame.p_chain);
296
22.4k
    block_ChainRelease(p_sys->pre.p_chain);
297
22.4k
    block_ChainRelease(p_sys->post.p_chain);
298
299
1.45M
    for(unsigned i=0;i<HEVC_MAX_NUM_PPS; i++)
300
1.43M
    {
301
1.43M
        if(p_sys->rg_pps[i].p_decoded)
302
9.04k
            hevc_rbsp_release_pps(p_sys->rg_pps[i].p_decoded);
303
1.43M
        if(p_sys->rg_pps[i].p_nal)
304
9.04k
            block_Release(p_sys->rg_pps[i].p_nal);
305
1.43M
    }
306
307
380k
    for(unsigned i=0;i<HEVC_MAX_NUM_SPS; i++)
308
358k
    {
309
358k
        if(p_sys->rg_sps[i].p_decoded)
310
6.35k
            hevc_rbsp_release_sps(p_sys->rg_sps[i].p_decoded);
311
358k
        if(p_sys->rg_sps[i].p_nal)
312
6.35k
            block_Release(p_sys->rg_sps[i].p_nal);
313
358k
    }
314
315
380k
    for(unsigned i=0;i<HEVC_MAX_NUM_VPS; i++)
316
358k
    {
317
358k
        if(p_sys->rg_vps[i].p_decoded)
318
6.71k
            hevc_rbsp_release_vps(p_sys->rg_vps[i].p_decoded);
319
358k
        if(p_sys->rg_vps[i].p_nal)
320
6.71k
            block_Release(p_sys->rg_vps[i].p_nal);
321
358k
    }
322
323
22.4k
    hevc_release_sei_pic_timing( p_sys->p_timing );
324
325
22.4k
    cc_storage_delete( p_sys->p_ccs );
326
327
22.4k
    free(p_sys);
328
22.4k
}
329
330
/****************************************************************************
331
 * Packetize
332
 ****************************************************************************/
333
static block_t *PacketizeHVC1(decoder_t *p_dec, block_t **pp_block)
334
14.6k
{
335
14.6k
    decoder_sys_t *p_sys = p_dec->p_sys;
336
337
14.6k
    return PacketizeXXC1( p_dec, p_dec->obj.logger,
338
14.6k
                          p_sys->i_nal_length_size, pp_block,
339
14.6k
                          ParseNALBlockW, PacketizeDrain );
340
14.6k
}
341
342
static block_t *PacketizeAnnexB(decoder_t *p_dec, block_t **pp_block)
343
4.28M
{
344
4.28M
    decoder_sys_t *p_sys = p_dec->p_sys;
345
346
4.28M
    return packetizer_Packetize(&p_sys->packetizer, pp_block);
347
4.28M
}
348
349
static void PacketizeFlush( decoder_t *p_dec )
350
0
{
351
0
    decoder_sys_t *p_sys = p_dec->p_sys;
352
353
0
    packetizer_Flush( &p_sys->packetizer );
354
0
}
355
356
/*****************************************************************************
357
 * GetCc:
358
 *****************************************************************************/
359
static block_t *GetCc( decoder_t *p_dec, decoder_cc_desc_t *p_desc )
360
1.34M
{
361
1.34M
    decoder_sys_t *p_sys = p_dec->p_sys;
362
1.34M
    return cc_storage_get_current( p_sys->p_ccs, p_desc );
363
1.34M
}
364
365
/****************************************************************************
366
 * Packetizer Helpers
367
 ****************************************************************************/
368
static void PacketizeReset(void *p_private, bool b_flush)
369
350
{
370
350
    decoder_t *p_dec = p_private;
371
350
    decoder_sys_t *p_sys = p_dec->p_sys;
372
373
350
    block_t *p_out = OutputQueues(p_sys, false);
374
350
    if(p_out)
375
118
        block_ChainRelease(p_out);
376
377
350
    if(b_flush)
378
0
    {
379
0
        p_sys->sets = MISSING;
380
0
        p_sys->b_recovery_point = false;
381
0
    }
382
350
    p_sys->b_need_ts = true;
383
350
    date_Set(&p_sys->dts, VLC_TICK_INVALID);
384
350
}
385
386
static bool InsertXPS(decoder_t *p_dec, uint8_t i_nal_type, uint8_t i_id,
387
                      const block_t *p_nalb)
388
2.12M
{
389
2.12M
    decoder_sys_t *p_sys = p_dec->p_sys;
390
2.12M
    struct hevc_tuple_s *p_tuple;
391
2.12M
    void **pp_active;
392
393
2.12M
    switch(i_nal_type)
394
2.12M
    {
395
400k
        case HEVC_NAL_VPS:
396
400k
            if(i_id > HEVC_VPS_ID_MAX)
397
0
                return false;
398
400k
            p_tuple = &p_sys->rg_vps[i_id];
399
400k
            pp_active = (void**)&p_sys->p_active_vps;
400
400k
            break;
401
1.44M
        case HEVC_NAL_SPS:
402
1.44M
            if(i_id > HEVC_SPS_ID_MAX)
403
0
                return false;
404
1.44M
            p_tuple = &p_sys->rg_sps[i_id];
405
1.44M
            pp_active = (void**)&p_sys->p_active_sps;
406
1.44M
            break;
407
279k
        case HEVC_NAL_PPS:
408
279k
            if(i_id > HEVC_PPS_ID_MAX)
409
0
                return false;
410
279k
            p_tuple = &p_sys->rg_pps[i_id];
411
279k
            pp_active = (void**)&p_sys->p_active_pps;
412
279k
            break;
413
0
        default:
414
0
            return false;
415
2.12M
    }
416
417
    /* Check if we really need to re-decode/replace */
418
2.12M
    if(p_tuple->p_nal)
419
817k
    {
420
817k
        const uint8_t *p_stored = p_tuple->p_nal->p_buffer;
421
817k
        size_t i_stored = p_tuple->p_nal->i_buffer;
422
817k
        hxxx_strip_AnnexB_startcode(&p_stored, &i_stored);
423
817k
        const uint8_t *p_new = p_nalb->p_buffer;
424
817k
        size_t i_new = p_nalb->i_buffer;
425
817k
        hxxx_strip_AnnexB_startcode(&p_new, &i_new);
426
817k
        if(i_stored == i_new && !memcmp(p_stored, p_new, i_new))
427
98.3k
            return true;
428
817k
    }
429
430
    /* Free associated decoded version */
431
2.02M
    if(p_tuple->p_decoded)
432
718k
    {
433
718k
        switch(i_nal_type)
434
718k
        {
435
149k
            case HEVC_NAL_VPS:
436
149k
                hevc_rbsp_release_vps(p_tuple->p_decoded);
437
149k
                break;
438
529k
            case HEVC_NAL_SPS:
439
529k
                hevc_rbsp_release_sps(p_tuple->p_decoded);
440
529k
                break;
441
40.1k
            case HEVC_NAL_PPS:
442
40.1k
                hevc_rbsp_release_pps(p_tuple->p_decoded);
443
40.1k
                break;
444
718k
        }
445
718k
        if(*pp_active == p_tuple->p_decoded)
446
48.6k
            *pp_active = NULL;
447
670k
        else
448
670k
            pp_active = NULL; /* don't change pointer */
449
718k
        p_tuple->p_decoded = NULL;
450
718k
    }
451
1.30M
    else pp_active = NULL;
452
453
    /* Free raw stored version */
454
2.02M
    if(p_tuple->p_nal)
455
718k
    {
456
718k
        block_Release(p_tuple->p_nal);
457
718k
        p_tuple->p_nal = NULL;
458
718k
    }
459
460
2.02M
    const uint8_t *p_buffer = p_nalb->p_buffer;
461
2.02M
    size_t i_buffer = p_nalb->i_buffer;
462
2.02M
    if( hxxx_strip_AnnexB_startcode( &p_buffer, &i_buffer ) )
463
2.02M
    {
464
        /* Create decoded entries */
465
2.02M
        switch(i_nal_type)
466
2.02M
        {
467
1.43M
            case HEVC_NAL_SPS:
468
1.43M
                p_tuple->p_decoded = hevc_decode_sps(p_buffer, i_buffer, true);
469
1.43M
                if(!p_tuple->p_decoded)
470
895k
                {
471
895k
                    msg_Err(p_dec, "Failed decoding SPS id %d", i_id);
472
895k
                    return false;
473
895k
                }
474
535k
                break;
475
535k
            case HEVC_NAL_PPS:
476
208k
                p_tuple->p_decoded = hevc_decode_pps(p_buffer, i_buffer, true);
477
208k
                if(!p_tuple->p_decoded)
478
158k
                {
479
158k
                    msg_Err(p_dec, "Failed decoding PPS id %d", i_id);
480
158k
                    return false;
481
158k
                }
482
49.1k
                break;
483
389k
            case HEVC_NAL_VPS:
484
389k
                p_tuple->p_decoded = hevc_decode_vps(p_buffer, i_buffer, true);
485
389k
                if(!p_tuple->p_decoded)
486
233k
                {
487
233k
                    msg_Err(p_dec, "Failed decoding VPS id %d", i_id);
488
233k
                    return false;
489
233k
                }
490
156k
                break;
491
2.02M
        }
492
493
740k
        if(p_tuple->p_decoded && pp_active) /* restore active by id */
494
31.9k
            *pp_active = p_tuple->p_decoded;
495
496
740k
        p_tuple->p_nal = block_Duplicate((block_t *)p_nalb);
497
498
740k
        return true;
499
2.02M
    }
500
501
0
    return false;
502
2.02M
}
503
504
static block_t *GetXPSCopy(decoder_sys_t *p_sys)
505
207k
{
506
207k
    block_t *p_chain = NULL;
507
207k
    block_t **pp_append = &p_chain;
508
207k
    struct hevc_tuple_s *xpstype[3] = {p_sys->rg_vps, p_sys->rg_sps, p_sys->rg_pps};
509
207k
    size_t xpsmax[3] = {HEVC_MAX_NUM_VPS, HEVC_MAX_NUM_SPS, HEVC_MAX_NUM_PPS};
510
828k
    for(size_t i=0; i<3; i++)
511
621k
    {
512
621k
        struct hevc_tuple_s *xps = xpstype[i];
513
20.5M
        for(size_t j=0; j<xpsmax[i]; j++)
514
19.8M
        {
515
19.8M
            block_t *p_dup;
516
19.8M
            if(xps[j].p_nal &&
517
233k
               (p_dup = block_Duplicate(xps[j].p_nal)))
518
233k
                block_ChainLastAppend(&pp_append, p_dup);
519
19.8M
        };
520
621k
    }
521
207k
    return p_chain;
522
207k
}
523
524
static bool XPSReady(decoder_sys_t *p_sys)
525
10.3M
{
526
673M
    for(unsigned i=0;i<HEVC_MAX_NUM_PPS; i++)
527
663M
    {
528
663M
        const hevc_picture_parameter_set_t *p_pps = p_sys->rg_pps[i].p_decoded;
529
663M
        if (p_pps)
530
563k
        {
531
563k
            uint8_t id_sps = hevc_get_pps_sps_id(p_pps);
532
563k
            const hevc_sequence_parameter_set_t *p_sps = p_sys->rg_sps[id_sps].p_decoded;
533
563k
            if(p_sps)
534
37.9k
            {
535
37.9k
                uint8_t id_vps = hevc_get_sps_vps_id(p_sps);
536
37.9k
                if(p_sys->rg_vps[id_vps].p_decoded)
537
3.88k
                    return true;
538
37.9k
            }
539
563k
        }
540
663M
    }
541
10.3M
    return false;
542
10.3M
}
543
544
static void AppendAsAnnexB(const block_t *p_block,
545
                           uint8_t **pp_dst, size_t *pi_dst)
546
8.96k
{
547
8.96k
    if(SIZE_MAX - p_block->i_buffer < *pi_dst )
548
0
        return;
549
550
8.96k
    size_t i_realloc = p_block->i_buffer + *pi_dst;
551
8.96k
    uint8_t *p_realloc = realloc(*pp_dst, i_realloc);
552
8.96k
    if(p_realloc)
553
8.96k
    {
554
8.96k
        memcpy(&p_realloc[*pi_dst], p_block->p_buffer, p_block->i_buffer);
555
8.96k
        *pi_dst = i_realloc;
556
8.96k
        *pp_dst = p_realloc;
557
8.96k
    }
558
8.96k
}
559
560
#define APPENDIF(maxcount, set, rg, b) \
561
224k
    for(size_t i=0; i<maxcount; i++)\
562
217k
    {\
563
217k
        if(((set != rg[i].p_decoded) == !b) && rg[i].p_nal)\
564
217k
        {\
565
8.96k
            AppendAsAnnexB(rg[i].p_nal, &p_data, &i_data);\
566
8.96k
            if(b) break;\
567
8.96k
        }\
568
217k
    }
569
570
static void SetsToAnnexB(decoder_sys_t *p_sys,
571
                         const hevc_picture_parameter_set_t *p_pps,
572
                         const hevc_sequence_parameter_set_t *p_sps,
573
                         const hevc_video_parameter_set_t *p_vps,
574
                         uint8_t **pp_out, size_t *pi_out)
575
2.14k
{
576
2.14k
    uint8_t *p_data = NULL;
577
2.14k
    size_t i_data = 0;
578
579
2.14k
    APPENDIF(HEVC_MAX_NUM_VPS, p_vps, p_sys->rg_vps, true);
580
2.14k
    APPENDIF(HEVC_MAX_NUM_VPS, p_vps, p_sys->rg_vps, false);
581
2.14k
    APPENDIF(HEVC_MAX_NUM_SPS, p_sps, p_sys->rg_sps, true);
582
2.14k
    APPENDIF(HEVC_MAX_NUM_SPS, p_sps, p_sys->rg_sps, false);
583
2.14k
    APPENDIF(HEVC_MAX_NUM_PPS, p_pps, p_sys->rg_pps, true);
584
2.14k
    APPENDIF(HEVC_MAX_NUM_PPS, p_pps, p_sys->rg_pps, false);
585
586
    /* because we copy to i_extra :/ */
587
2.14k
    if(i_data <= INT_MAX)
588
2.14k
    {
589
2.14k
        *pp_out = p_data;
590
2.14k
        *pi_out = i_data;
591
2.14k
    }
592
0
    else free(p_data);
593
2.14k
}
594
595
static void ActivateSets(decoder_t *p_dec,
596
                         const hevc_picture_parameter_set_t *p_pps,
597
                         const hevc_sequence_parameter_set_t *p_sps,
598
                         const hevc_video_parameter_set_t *p_vps)
599
96.6k
{
600
96.6k
    decoder_sys_t *p_sys = p_dec->p_sys;
601
96.6k
    p_sys->p_active_pps = p_pps;
602
96.6k
    p_sys->p_active_sps = p_sps;
603
96.6k
    p_sys->p_active_vps = p_vps;
604
96.6k
    if(p_sps)
605
96.6k
    {
606
96.6k
        if(!p_dec->fmt_out.video.i_frame_rate || !p_dec->fmt_out.video.i_frame_rate_base)
607
2.77k
        {
608
2.77k
            unsigned num, den;
609
2.77k
            if(hevc_get_frame_rate( p_sps, p_vps, &num, &den ))
610
1.63k
            {
611
1.63k
                p_dec->fmt_out.video.i_frame_rate = num;
612
1.63k
                p_dec->fmt_out.video.i_frame_rate_base = den;
613
1.63k
                if(num <= UINT_MAX / 2 &&
614
1.10k
                   (p_sys->dts.i_divider_den != den ||
615
39
                    p_sys->dts.i_divider_num != 2 * num))
616
1.09k
                {
617
1.09k
                    date_Change(&p_sys->dts, 2 * num, den);
618
1.09k
                }
619
1.63k
            }
620
2.77k
            p_dec->fmt_out.video.i_frame_rate = p_sys->dts.i_divider_num >> 1;
621
2.77k
            p_dec->fmt_out.video.i_frame_rate_base = p_sys->dts.i_divider_den;
622
2.77k
        }
623
624
96.6k
        if(p_dec->fmt_in->video.primaries == COLOR_PRIMARIES_UNDEF)
625
93.9k
        {
626
93.9k
            (void) hevc_get_colorimetry( p_sps,
627
93.9k
                                         &p_dec->fmt_out.video.primaries,
628
93.9k
                                         &p_dec->fmt_out.video.transfer,
629
93.9k
                                         &p_dec->fmt_out.video.space,
630
93.9k
                                         &p_dec->fmt_out.video.color_range);
631
93.9k
        }
632
633
96.6k
        unsigned sizes[6];
634
96.6k
        if( hevc_get_picture_size( p_sps, &sizes[0], &sizes[1],
635
96.6k
                                          &sizes[2], &sizes[3],
636
96.6k
                                          &sizes[4], &sizes[5] ) )
637
89.1k
        {
638
89.1k
            p_dec->fmt_out.video.i_x_offset = sizes[0];
639
89.1k
            p_dec->fmt_out.video.i_y_offset = sizes[1];
640
89.1k
            p_dec->fmt_out.video.i_width = sizes[2];
641
89.1k
            p_dec->fmt_out.video.i_height = sizes[3];
642
89.1k
            if(p_dec->fmt_in->video.i_visible_width == 0)
643
60.9k
            {
644
60.9k
                p_dec->fmt_out.video.i_visible_width = sizes[4];
645
60.9k
                p_dec->fmt_out.video.i_visible_height = sizes[5];
646
60.9k
            }
647
89.1k
        }
648
649
96.6k
        if ( p_dec->fmt_in->video.i_sar_num == 0 || p_dec->fmt_in->video.i_sar_den == 0)
650
89.7k
        {
651
89.7k
            unsigned num, den;
652
89.7k
            if ( hevc_get_aspect_ratio( p_sps, &num, &den ) )
653
6.10k
            {
654
6.10k
                p_dec->fmt_out.video.i_sar_num = num;
655
6.10k
                p_dec->fmt_out.video.i_sar_den = den;
656
6.10k
            }
657
89.7k
        }
658
659
96.6k
        if(p_dec->fmt_in->i_profile == -1)
660
68.9k
        {
661
68.9k
            uint8_t i_profile, i_level;
662
68.9k
            if( hevc_get_sps_profile_tier_level( p_sps, &i_profile, &i_level ) )
663
66.9k
            {
664
66.9k
                p_dec->fmt_out.i_profile = i_profile;
665
66.9k
                p_dec->fmt_out.i_level = i_level;
666
66.9k
            }
667
68.9k
        }
668
669
96.6k
        if(p_dec->fmt_out.i_extra == 0 && p_vps && p_pps)
670
2.14k
            SetsToAnnexB(p_sys, p_pps, p_sps, p_vps,
671
2.14k
                         (uint8_t **)&p_dec->fmt_out.p_extra, &p_dec->fmt_out.i_extra);
672
96.6k
    }
673
96.6k
}
674
675
static void GetXPSSet(uint8_t i_pps_id, void *priv,
676
                      hevc_picture_parameter_set_t **pp_pps,
677
                      hevc_sequence_parameter_set_t **pp_sps,
678
                      hevc_video_parameter_set_t **pp_vps)
679
433k
{
680
433k
    decoder_sys_t *p_sys = priv;
681
433k
    *pp_sps = NULL;
682
433k
    *pp_vps = NULL;
683
433k
    if((*pp_pps = p_sys->rg_pps[i_pps_id].p_decoded))
684
333k
        if((*pp_sps = p_sys->rg_sps[hevc_get_pps_sps_id(*pp_pps)].p_decoded))
685
274k
            *pp_vps = p_sys->rg_vps[hevc_get_sps_vps_id(*pp_sps)].p_decoded;
686
433k
}
687
688
static void ParseStoredSEI( decoder_t *p_dec )
689
4.24M
{
690
4.24M
    decoder_sys_t *p_sys = p_dec->p_sys;
691
692
4.24M
    for( block_t *p_nal = p_sys->pre.p_chain;
693
4.49M
                  p_nal; p_nal = p_nal->p_next )
694
247k
    {
695
247k
        if( p_nal->i_buffer < 5 )
696
0
            continue;
697
698
247k
        if( hevc_getNALType(&p_nal->p_buffer[4]) == HEVC_NAL_PREF_SEI )
699
5.74k
        {
700
5.74k
            HxxxParse_AnnexB_SEI( p_nal->p_buffer, p_nal->i_buffer,
701
5.74k
                                  2 /* nal header */, ParseSEICallback, p_dec );
702
5.74k
        }
703
247k
    }
704
4.24M
}
705
706
static block_t *ParseVCL(decoder_t *p_dec, uint8_t i_nal_type, block_t *p_frag)
707
41.7M
{
708
41.7M
    decoder_sys_t *p_sys = p_dec->p_sys;
709
41.7M
    block_t *p_outputchain = NULL;
710
711
41.7M
    const uint8_t *p_buffer = p_frag->p_buffer;
712
41.7M
    size_t i_buffer = p_frag->i_buffer;
713
714
41.7M
    if(unlikely(!hxxx_strip_AnnexB_startcode(&p_buffer, &i_buffer) || i_buffer < 3))
715
26.2M
    {
716
26.2M
        block_ChainLastAppend(&p_sys->frame.pp_chain_last, p_frag); /* might be corrupted */
717
26.2M
        return NULL;
718
26.2M
    }
719
720
15.4M
    const uint8_t i_layer = hevc_getNALLayer( p_buffer );
721
15.4M
    bool b_first_slice_in_pic = p_buffer[2] & 0x80;
722
15.4M
    if (b_first_slice_in_pic)
723
4.24M
    {
724
4.24M
        if(p_sys->frame.p_chain)
725
3.64M
        {
726
            /* Starting new frame: return previous frame data for output */
727
3.64M
            p_outputchain = OutputQueues(p_sys, p_sys->sets != MISSING &&
728
2.51M
                                                p_sys->b_recovery_point);
729
3.64M
        }
730
731
4.24M
        hevc_slice_segment_header_t *p_sli = hevc_decode_slice_header(p_buffer, i_buffer, true,
732
4.24M
                                                                      GetXPSSet, p_sys);
733
4.24M
        if(p_sli && i_layer == 0)
734
96.6k
        {
735
96.6k
            hevc_sequence_parameter_set_t *p_sps;
736
96.6k
            hevc_picture_parameter_set_t *p_pps;
737
96.6k
            hevc_video_parameter_set_t *p_vps;
738
96.6k
            GetXPSSet(hevc_get_slice_pps_id(p_sli), p_sys, &p_pps, &p_sps, &p_vps);
739
96.6k
            ActivateSets(p_dec, p_pps, p_sps, p_vps);
740
96.6k
        }
741
742
4.24M
        ParseStoredSEI( p_dec );
743
744
4.24M
        switch(i_nal_type)
745
4.24M
        {
746
1.31k
            case HEVC_NAL_BLA_W_LP:
747
2.55k
            case HEVC_NAL_BLA_W_RADL:
748
102k
            case HEVC_NAL_BLA_N_LP:
749
127k
            case HEVC_NAL_IDR_W_RADL:
750
129k
            case HEVC_NAL_IDR_N_LP:
751
2.51M
            case HEVC_NAL_CRA:
752
2.51M
                p_frag->i_flags |= BLOCK_FLAG_TYPE_I;
753
2.51M
                break;
754
755
1.73M
            default:
756
1.73M
            {
757
1.73M
                if(p_sli)
758
43.1k
                {
759
43.1k
                    enum hevc_slice_type_e type;
760
43.1k
                    if(hevc_get_slice_type( p_sli, &type ))
761
43.1k
                    {
762
43.1k
                        switch(type)
763
43.1k
                        {
764
40.5k
                            case HEVC_SLICE_TYPE_B:
765
40.5k
                                p_frag->i_flags |= BLOCK_FLAG_TYPE_B;
766
40.5k
                                break;
767
380
                            case HEVC_SLICE_TYPE_P:
768
380
                                p_frag->i_flags |= BLOCK_FLAG_TYPE_P;
769
380
                                break;
770
2.21k
                            case HEVC_SLICE_TYPE_I:
771
2.21k
                                p_frag->i_flags |= BLOCK_FLAG_TYPE_I;
772
2.21k
                                break;
773
43.1k
                        }
774
43.1k
                    }
775
43.1k
                }
776
1.68M
                else p_frag->i_flags |= BLOCK_FLAG_TYPE_B;
777
1.73M
            }
778
1.73M
            break;
779
4.24M
        }
780
781
4.24M
        if(p_sli)
782
104k
            hevc_rbsp_release_slice_header(p_sli);
783
4.24M
    }
784
785
15.4M
    if(p_sys->sets == MISSING && i_layer == 0 && XPSReady(p_sys))
786
3.88k
        p_sys->sets = COMPLETE;
787
788
15.4M
    if(p_sys->sets != MISSING && (p_frag->i_flags & BLOCK_FLAG_TYPE_I))
789
2.43M
    {
790
2.43M
        p_sys->b_recovery_point = true; /* won't care about SEI recovery */
791
2.43M
    }
792
793
15.4M
    if(!p_sys->b_recovery_point) /* content will be dropped */
794
12.4M
        cc_storage_reset(p_sys->p_ccs);
795
796
15.4M
    block_ChainLastAppend(&p_sys->frame.pp_chain_last, p_frag);
797
798
15.4M
    return p_outputchain;
799
15.4M
}
800
801
static block_t * ParseAUHead(decoder_t *p_dec, uint8_t i_nal_type, block_t *p_nalb)
802
7.68M
{
803
7.68M
    decoder_sys_t *p_sys = p_dec->p_sys;
804
7.68M
    block_t *p_ret = NULL;
805
806
7.68M
    if(p_sys->post.p_chain || p_sys->frame.p_chain)
807
1.54M
        p_ret = OutputQueues(p_sys, p_sys->sets != MISSING &&
808
131k
                                    p_sys->b_recovery_point);
809
810
7.68M
    switch(i_nal_type)
811
7.68M
    {
812
914k
        case HEVC_NAL_AUD:
813
914k
            if(!p_ret && p_sys->pre.p_chain)
814
394k
                p_ret = OutputQueues(p_sys, p_sys->sets != MISSING &&
815
2.08k
                                            p_sys->b_recovery_point);
816
914k
            break;
817
818
410k
        case HEVC_NAL_VPS:
819
2.49M
        case HEVC_NAL_SPS:
820
3.28M
        case HEVC_NAL_PPS:
821
3.28M
        {
822
3.28M
            uint8_t i_id;
823
3.28M
            const uint8_t *p_xps = p_nalb->p_buffer;
824
3.28M
            size_t i_xps = p_nalb->i_buffer;
825
3.28M
            if(hxxx_strip_AnnexB_startcode(&p_xps, &i_xps) &&
826
3.28M
               hevc_get_xps_id(p_xps, i_xps, &i_id))
827
2.12M
                InsertXPS(p_dec, i_nal_type, i_id, p_nalb);
828
3.28M
            if(p_sys->sets != SENT) /* will store/inject on first recovery point */
829
3.02M
            {
830
3.02M
                block_Release(p_nalb);
831
3.02M
                return p_ret;
832
3.02M
            }
833
254k
            break;
834
3.28M
        }
835
836
1.05M
        case HEVC_NAL_PREF_SEI:
837
            /* stored an parsed later when we get sps & frame */
838
3.48M
        default:
839
3.48M
            break;
840
7.68M
    }
841
842
4.65M
    block_ChainLastAppend(&p_sys->pre.pp_chain_last, p_nalb);
843
844
4.65M
    return p_ret;
845
7.68M
}
846
847
static block_t * ParseAUTail(decoder_t *p_dec, uint8_t i_nal_type, block_t *p_nalb)
848
7.02M
{
849
7.02M
    decoder_sys_t *p_sys = p_dec->p_sys;
850
7.02M
    block_t *p_ret = NULL;
851
852
7.02M
    block_ChainLastAppend(&p_sys->post.pp_chain_last, p_nalb);
853
854
7.02M
    switch(i_nal_type)
855
7.02M
    {
856
1.30M
        case HEVC_NAL_EOS:
857
1.98M
        case HEVC_NAL_EOB:
858
1.98M
            p_ret = OutputQueues(p_sys, p_sys->sets != MISSING &&
859
41.8k
                                        p_sys->b_recovery_point);
860
1.98M
            if( p_ret )
861
1.98M
                p_ret->i_flags |= BLOCK_FLAG_END_OF_SEQUENCE;
862
1.98M
            break;
863
864
343k
        case HEVC_NAL_SUFF_SEI:
865
343k
            HxxxParse_AnnexB_SEI( p_nalb->p_buffer, p_nalb->i_buffer,
866
343k
                                  2 /* nal header */, ParseSEICallback, p_dec );
867
343k
            break;
868
7.02M
    }
869
870
7.02M
    if(!p_ret && p_sys->frame.p_chain == NULL)
871
4.52M
        p_ret = OutputQueues(p_sys, false);
872
873
7.02M
    return p_ret;
874
7.02M
}
875
876
static block_t * ParseNonVCL(decoder_t *p_dec, uint8_t i_nal_type, block_t *p_nalb)
877
14.7M
{
878
14.7M
    block_t *p_ret = NULL;
879
880
14.7M
    if ( (i_nal_type >= HEVC_NAL_VPS        && i_nal_type <= HEVC_NAL_AUD) ||
881
10.5M
          i_nal_type == HEVC_NAL_PREF_SEI ||
882
9.45M
         (i_nal_type >= HEVC_NAL_RSV_NVCL41 && i_nal_type <= HEVC_NAL_RSV_NVCL44) ||
883
8.64M
         (i_nal_type >= HEVC_NAL_UNSPEC48   && i_nal_type <= HEVC_NAL_UNSPEC55) )
884
7.68M
    {
885
7.68M
        p_ret = ParseAUHead(p_dec, i_nal_type, p_nalb);
886
7.68M
    }
887
7.02M
    else
888
7.02M
    {
889
7.02M
        p_ret = ParseAUTail(p_dec, i_nal_type, p_nalb);
890
7.02M
    }
891
892
14.7M
    return p_ret;
893
14.7M
}
894
895
static block_t *GatherAndValidateChain(block_t *p_outputchain)
896
61.4M
{
897
61.4M
    block_t *p_output = NULL;
898
899
61.4M
    if(p_outputchain)
900
15.7M
    {
901
15.7M
        if(p_outputchain->i_flags & BLOCK_FLAG_DROP)
902
13.0M
            p_output = p_outputchain; /* Avoid useless gather */
903
2.67M
        else
904
2.67M
            p_output = block_ChainGather(p_outputchain);
905
15.7M
    }
906
907
61.4M
    if(p_output && (p_output->i_flags & BLOCK_FLAG_DROP))
908
13.0M
    {
909
13.0M
        block_ChainRelease(p_output); /* Chain! see above */
910
13.0M
        p_output = NULL;
911
13.0M
    }
912
913
61.4M
    return p_output;
914
61.4M
}
915
916
static void SetOutputBlockProperties(decoder_t *p_dec, block_t *p_output)
917
2.67M
{
918
2.67M
    decoder_sys_t *p_sys = p_dec->p_sys;
919
    /* Set frame duration */
920
2.67M
    if(p_sys->p_active_sps)
921
846k
    {
922
846k
        uint8_t i_num_clock_ts = hevc_get_num_clock_ts(p_sys->p_active_sps,
923
846k
                                                       p_sys->p_timing);
924
846k
        const vlc_tick_t i_start = date_Get(&p_sys->dts);
925
846k
        if( i_start != VLC_TICK_INVALID )
926
846k
        {
927
846k
            date_Increment(&p_sys->dts, i_num_clock_ts);
928
846k
            p_output->i_length = date_Get(&p_sys->dts) - i_start;
929
846k
        }
930
846k
        p_sys->pts = VLC_TICK_INVALID;
931
846k
    }
932
2.67M
    p_output->i_flags &= ~BLOCK_FLAG_AU_END;
933
2.67M
    hevc_release_sei_pic_timing(p_sys->p_timing);
934
2.67M
    p_sys->p_timing = NULL;
935
2.67M
}
936
937
/*****************************************************************************
938
 * ParseNALBlock: parses annexB type NALs
939
 * All p_frag blocks are required to start with 0 0 0 1 4-byte startcode
940
 *****************************************************************************/
941
static block_t *ParseNALBlock(decoder_t *p_dec, bool *pb_ts_used, block_t *p_frag)
942
61.4M
{
943
61.4M
    decoder_sys_t *p_sys = p_dec->p_sys;
944
61.4M
    *pb_ts_used = false;
945
61.4M
    bool b_au_end = p_frag->i_flags & BLOCK_FLAG_AU_END;
946
947
61.4M
    if(p_sys->b_need_ts)
948
27.0M
    {
949
27.0M
        if(p_frag->i_dts != VLC_TICK_INVALID)
950
19.2k
            date_Set(&p_sys->dts, p_frag->i_dts);
951
27.0M
        p_sys->pts = p_frag->i_pts;
952
27.0M
        if(date_Get( &p_sys->dts ) != VLC_TICK_INVALID)
953
19.2k
            p_sys->b_need_ts = false;
954
27.0M
        *pb_ts_used = true;
955
27.0M
    }
956
957
61.4M
    if(unlikely(p_frag->i_buffer < 5))
958
0
    {
959
0
        msg_Warn(p_dec,"NAL too small");
960
0
        block_Release(p_frag);
961
0
        return NULL;
962
0
    }
963
964
61.4M
    if(p_frag->p_buffer[4] & 0x80)
965
4.98M
    {
966
4.98M
        msg_Warn(p_dec,"Forbidden zero bit not null, corrupted NAL");
967
4.98M
        block_Release(p_frag);
968
4.98M
        return GatherAndValidateChain(OutputQueues(p_sys, false)); /* will drop */
969
4.98M
    }
970
971
    /* Get NALU type */
972
56.4M
    const vlc_tick_t dts = p_frag->i_dts, pts = p_frag->i_pts;
973
56.4M
    block_t * p_output = NULL;
974
56.4M
    uint8_t i_nal_type = hevc_getNALType(&p_frag->p_buffer[4]);
975
976
56.4M
    if (i_nal_type < HEVC_NAL_VPS)
977
41.7M
    {
978
        /* NAL is a VCL NAL */
979
41.7M
        p_output = ParseVCL(p_dec, i_nal_type, p_frag);
980
41.7M
        if (p_output && (p_output->i_flags & BLOCK_FLAG_DROP))
981
41.7M
            msg_Info(p_dec, "Waiting for VPS/SPS/PPS");
982
41.7M
    }
983
14.7M
    else
984
14.7M
    {
985
14.7M
        p_output = ParseNonVCL(p_dec, i_nal_type, p_frag);
986
14.7M
    }
987
988
56.4M
    if( !p_output && b_au_end )
989
0
        p_output = OutputQueues(p_sys, p_sys->sets != MISSING &&
990
0
                                       p_sys->b_recovery_point);
991
992
56.4M
    p_output = GatherAndValidateChain(p_output);
993
56.4M
    if(p_output)
994
2.66M
    {
995
2.66M
        if(p_sys->sets != SENT)
996
2.85k
        {
997
2.85k
            assert(p_sys->sets == COMPLETE);
998
2.85k
            p_sys->sets = SENT;
999
2.85k
        }
1000
1001
2.66M
        SetOutputBlockProperties( p_dec, p_output );
1002
2.66M
        if (dts != VLC_TICK_INVALID)
1003
2.64M
            date_Set(&p_sys->dts, dts);
1004
2.66M
        p_sys->pts = pts;
1005
2.66M
        *pb_ts_used = true;
1006
2.66M
    }
1007
1008
56.4M
    return p_output;
1009
56.4M
}
1010
1011
static block_t *PacketizeParse(void *p_private, bool *pb_ts_used, block_t *p_block)
1012
61.4M
{
1013
61.4M
    decoder_t *p_dec = p_private;
1014
61.4M
    decoder_sys_t *p_sys = p_dec->p_sys;
1015
1016
    /* Remove trailing 0 bytes */
1017
488M
    while (p_block->i_buffer > 5 && p_block->p_buffer[p_block->i_buffer-1] == 0x00 )
1018
426M
        p_block->i_buffer--;
1019
1020
61.4M
    p_block = ParseNALBlock( p_dec, pb_ts_used, p_block );
1021
61.4M
    if( p_block )
1022
2.66M
        cc_storage_commit( p_sys->p_ccs, p_block );
1023
1024
61.4M
    return p_block;
1025
61.4M
}
1026
1027
static int PacketizeValidate( void *p_private, block_t *p_au )
1028
2.67M
{
1029
2.67M
    VLC_UNUSED(p_private);
1030
2.67M
    VLC_UNUSED(p_au);
1031
2.67M
    return VLC_SUCCESS;
1032
2.67M
}
1033
1034
static block_t * PacketizeDrain(void *p_private)
1035
29.9k
{
1036
29.9k
    decoder_t *p_dec = p_private;
1037
29.9k
    decoder_sys_t *p_sys = p_dec->p_sys;
1038
1039
29.9k
    block_t *p_out = NULL;
1040
1041
29.9k
    if( p_sys->frame.p_chain &&
1042
11.0k
        p_sys->sets != MISSING &&
1043
2.65k
        p_sys->b_recovery_point )
1044
2.41k
    {
1045
2.41k
        p_out = OutputQueues(p_sys, true);
1046
2.41k
        if( p_out )
1047
2.41k
        {
1048
2.41k
            p_out = GatherAndValidateChain(p_out);
1049
2.41k
            if( p_out )
1050
2.41k
                SetOutputBlockProperties( p_dec, p_out );
1051
2.41k
        }
1052
2.41k
    }
1053
29.9k
    return p_out;
1054
29.9k
}
1055
1056
static bool ParseSEICallback( const hxxx_sei_data_t *p_sei_data, void *cbdata )
1057
39.0k
{
1058
39.0k
    decoder_t *p_dec = (decoder_t *) cbdata;
1059
39.0k
    decoder_sys_t *p_sys = p_dec->p_sys;
1060
1061
39.0k
    switch( p_sei_data->i_type )
1062
39.0k
    {
1063
12.0k
        case HXXX_SEI_PIC_TIMING:
1064
12.0k
        {
1065
12.0k
            if( p_sys->p_active_sps )
1066
4.73k
            {
1067
4.73k
                hevc_release_sei_pic_timing( p_sys->p_timing );
1068
4.73k
                p_sys->p_timing = hevc_decode_sei_pic_timing( p_sei_data->p_bs,
1069
4.73k
                                                              p_sys->p_active_sps );
1070
4.73k
            }
1071
12.0k
        } break;
1072
15.9k
        case HXXX_SEI_USER_DATA_REGISTERED_ITU_T_T35:
1073
15.9k
        {
1074
15.9k
            if( p_sei_data->itu_t35.type == HXXX_ITU_T35_TYPE_CC )
1075
15.9k
            {
1076
15.9k
                cc_storage_append( p_sys->p_ccs, true, p_sei_data->itu_t35.u.cc.p_data,
1077
15.9k
                                                       p_sei_data->itu_t35.u.cc.i_data );
1078
15.9k
            }
1079
15.9k
        } break;
1080
7.35k
        case HXXX_SEI_RECOVERY_POINT:
1081
7.35k
        {
1082
7.35k
            hevc_sei_recovery_point_t reco;
1083
7.35k
            if( !p_sys->b_recovery_point &&
1084
938
                hevc_decode_sei_recovery_point( p_sei_data->p_bs, &reco ) )
1085
938
            {
1086
938
                msg_Dbg( p_dec, "Seen SEI recovery point, %d recovery frames", reco.i_frames );
1087
938
                p_sys->b_recovery_point = true;
1088
938
            }
1089
7.35k
        } break;
1090
0
        case HXXX_SEI_FRAME_PACKING_ARRANGEMENT:
1091
0
        {
1092
0
            if( p_dec->fmt_in->video.multiview_mode == MULTIVIEW_2D )
1093
0
            {
1094
0
                video_multiview_mode_t mode;
1095
0
                switch( p_sei_data->frame_packing.type )
1096
0
                {
1097
0
                    case FRAME_PACKING_INTERLEAVED_CHECKERBOARD:
1098
0
                        mode = MULTIVIEW_STEREO_CHECKERBOARD; break;
1099
0
                    case FRAME_PACKING_INTERLEAVED_COLUMN:
1100
0
                        mode = MULTIVIEW_STEREO_COL; break;
1101
0
                    case FRAME_PACKING_INTERLEAVED_ROW:
1102
0
                        mode = MULTIVIEW_STEREO_ROW; break;
1103
0
                    case FRAME_PACKING_SIDE_BY_SIDE:
1104
0
                        mode = MULTIVIEW_STEREO_SBS; break;
1105
0
                    case FRAME_PACKING_TOP_BOTTOM:
1106
0
                        mode = MULTIVIEW_STEREO_TB; break;
1107
0
                    case FRAME_PACKING_TEMPORAL:
1108
0
                        mode = MULTIVIEW_STEREO_FRAME; break;
1109
0
                    case FRAME_PACKING_TILED:
1110
0
                    default:
1111
0
                        mode = MULTIVIEW_2D; break;
1112
0
                }
1113
0
                p_dec->fmt_out.video.multiview_mode = mode;
1114
0
            }
1115
0
        } break;
1116
1.62k
        case HXXX_SEI_MASTERING_DISPLAY_COLOUR_VOLUME:
1117
1.62k
        {
1118
1.62k
            video_format_t *p_fmt = &p_dec->fmt_out.video;
1119
11.3k
            for (size_t i=0; i<ARRAY_SIZE(p_sei_data->colour_volume.primaries); ++i)
1120
9.76k
                p_fmt->mastering.primaries[i] = p_sei_data->colour_volume.primaries[i];
1121
4.88k
            for (size_t i=0; i<ARRAY_SIZE(p_sei_data->colour_volume.white_point); ++i)
1122
3.25k
                p_fmt->mastering.white_point[i] = p_sei_data->colour_volume.white_point[i];
1123
1.62k
            p_fmt->mastering.max_luminance = p_sei_data->colour_volume.max_luminance;
1124
1.62k
            p_fmt->mastering.min_luminance = p_sei_data->colour_volume.min_luminance;
1125
1.62k
        } break;
1126
2.13k
        case HXXX_SEI_CONTENT_LIGHT_LEVEL:
1127
2.13k
        {
1128
2.13k
            video_format_t *p_fmt = &p_dec->fmt_out.video;
1129
2.13k
            p_fmt->lighting.MaxCLL = p_sei_data->content_light_lvl.MaxCLL;
1130
2.13k
            p_fmt->lighting.MaxFALL = p_sei_data->content_light_lvl.MaxFALL;
1131
2.13k
        } break;
1132
39.0k
    }
1133
1134
39.0k
    return true;
1135
39.0k
}