Statistics
| Branch: | Revision:

ffmpeg / libavcodec / dvbsubdec.c @ e31a7441

History | View | Annotate | Download (40.1 KB)

1
/*
2
 * DVB subtitle decoding for ffmpeg
3
 * Copyright (c) 2005 Ian Caulfield
4
 *
5
 * This file is part of FFmpeg.
6
 *
7
 * FFmpeg is free software; you can redistribute it and/or
8
 * modify it under the terms of the GNU Lesser General Public
9
 * License as published by the Free Software Foundation; either
10
 * version 2.1 of the License, or (at your option) any later version.
11
 *
12
 * FFmpeg is distributed in the hope that it will be useful,
13
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15
 * Lesser General Public License for more details.
16
 *
17
 * You should have received a copy of the GNU Lesser General Public
18
 * License along with FFmpeg; if not, write to the Free Software
19
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20
 */
21
#include "avcodec.h"
22
#include "dsputil.h"
23
#include "get_bits.h"
24
#include "bytestream.h"
25
#include "libavutil/colorspace.h"
26

    
27
//#define DEBUG
28
//#define DEBUG_PACKET_CONTENTS
29
//#define DEBUG_SAVE_IMAGES
30

    
31
#define DVBSUB_PAGE_SEGMENT     0x10
32
#define DVBSUB_REGION_SEGMENT   0x11
33
#define DVBSUB_CLUT_SEGMENT     0x12
34
#define DVBSUB_OBJECT_SEGMENT   0x13
35
#define DVBSUB_DISPLAYDEFINITION_SEGMENT 0x14
36
#define DVBSUB_DISPLAY_SEGMENT  0x80
37

    
38
#define cm (ff_cropTbl + MAX_NEG_CROP)
39

    
40
#ifdef DEBUG_SAVE_IMAGES
41
#undef fprintf
42
#if 0
43
static void png_save(const char *filename, uint8_t *bitmap, int w, int h,
44
                     uint32_t *rgba_palette)
45
{
46
    int x, y, v;
47
    FILE *f;
48
    char fname[40], fname2[40];
49
    char command[1024];
50

51
    snprintf(fname, 40, "%s.ppm", filename);
52

53
    f = fopen(fname, "w");
54
    if (!f) {
55
        perror(fname);
56
        exit(1);
57
    }
58
    fprintf(f, "P6\n"
59
            "%d %d\n"
60
            "%d\n",
61
            w, h, 255);
62
    for(y = 0; y < h; y++) {
63
        for(x = 0; x < w; x++) {
64
            v = rgba_palette[bitmap[y * w + x]];
65
            putc((v >> 16) & 0xff, f);
66
            putc((v >> 8) & 0xff, f);
67
            putc((v >> 0) & 0xff, f);
68
        }
69
    }
70
    fclose(f);
71

72

73
    snprintf(fname2, 40, "%s-a.pgm", filename);
74

75
    f = fopen(fname2, "w");
76
    if (!f) {
77
        perror(fname2);
78
        exit(1);
79
    }
80
    fprintf(f, "P5\n"
81
            "%d %d\n"
82
            "%d\n",
83
            w, h, 255);
84
    for(y = 0; y < h; y++) {
85
        for(x = 0; x < w; x++) {
86
            v = rgba_palette[bitmap[y * w + x]];
87
            putc((v >> 24) & 0xff, f);
88
        }
89
    }
90
    fclose(f);
91

92
    snprintf(command, 1024, "pnmtopng -alpha %s %s > %s.png 2> /dev/null", fname2, fname, filename);
93
    system(command);
94

95
    snprintf(command, 1024, "rm %s %s", fname, fname2);
96
    system(command);
97
}
98
#endif
99

    
100
static void png_save2(const char *filename, uint32_t *bitmap, int w, int h)
101
{
102
    int x, y, v;
103
    FILE *f;
104
    char fname[40], fname2[40];
105
    char command[1024];
106

    
107
    snprintf(fname, sizeof(fname), "%s.ppm", filename);
108

    
109
    f = fopen(fname, "w");
110
    if (!f) {
111
        perror(fname);
112
        exit(1);
113
    }
114
    fprintf(f, "P6\n"
115
            "%d %d\n"
116
            "%d\n",
117
            w, h, 255);
118
    for(y = 0; y < h; y++) {
119
        for(x = 0; x < w; x++) {
120
            v = bitmap[y * w + x];
121
            putc((v >> 16) & 0xff, f);
122
            putc((v >> 8) & 0xff, f);
123
            putc((v >> 0) & 0xff, f);
124
        }
125
    }
126
    fclose(f);
127

    
128

    
129
    snprintf(fname2, sizeof(fname2), "%s-a.pgm", filename);
130

    
131
    f = fopen(fname2, "w");
132
    if (!f) {
133
        perror(fname2);
134
        exit(1);
135
    }
136
    fprintf(f, "P5\n"
137
            "%d %d\n"
138
            "%d\n",
139
            w, h, 255);
140
    for(y = 0; y < h; y++) {
141
        for(x = 0; x < w; x++) {
142
            v = bitmap[y * w + x];
143
            putc((v >> 24) & 0xff, f);
144
        }
145
    }
146
    fclose(f);
147

    
148
    snprintf(command, sizeof(command), "pnmtopng -alpha %s %s > %s.png 2> /dev/null", fname2, fname, filename);
149
    system(command);
150

    
151
    snprintf(command, sizeof(command), "rm %s %s", fname, fname2);
152
    system(command);
153
}
154
#endif
155

    
156
#define RGBA(r,g,b,a) (((a) << 24) | ((r) << 16) | ((g) << 8) | (b))
157

    
158
typedef struct DVBSubCLUT {
159
    int id;
160

    
161
    uint32_t clut4[4];
162
    uint32_t clut16[16];
163
    uint32_t clut256[256];
164

    
165
    struct DVBSubCLUT *next;
166
} DVBSubCLUT;
167

    
168
static DVBSubCLUT default_clut;
169

    
170
typedef struct DVBSubObjectDisplay {
171
    int object_id;
172
    int region_id;
173

    
174
    int x_pos;
175
    int y_pos;
176

    
177
    int fgcolor;
178
    int bgcolor;
179

    
180
    struct DVBSubObjectDisplay *region_list_next;
181
    struct DVBSubObjectDisplay *object_list_next;
182
} DVBSubObjectDisplay;
183

    
184
typedef struct DVBSubObject {
185
    int id;
186

    
187
    int type;
188

    
189
    DVBSubObjectDisplay *display_list;
190

    
191
    struct DVBSubObject *next;
192
} DVBSubObject;
193

    
194
typedef struct DVBSubRegionDisplay {
195
    int region_id;
196

    
197
    int x_pos;
198
    int y_pos;
199

    
200
    struct DVBSubRegionDisplay *next;
201
} DVBSubRegionDisplay;
202

    
203
typedef struct DVBSubRegion {
204
    int id;
205

    
206
    int width;
207
    int height;
208
    int depth;
209

    
210
    int clut;
211
    int bgcolor;
212

    
213
    uint8_t *pbuf;
214
    int buf_size;
215

    
216
    DVBSubObjectDisplay *display_list;
217

    
218
    struct DVBSubRegion *next;
219
} DVBSubRegion;
220

    
221
typedef struct DVBSubDisplayDefinition {
222
    int version;
223

    
224
    int x;
225
    int y;
226
    int width;
227
    int height;
228
} DVBSubDisplayDefinition;
229

    
230
typedef struct DVBSubContext {
231
    int composition_id;
232
    int ancillary_id;
233

    
234
    int time_out;
235
    DVBSubRegion *region_list;
236
    DVBSubCLUT   *clut_list;
237
    DVBSubObject *object_list;
238

    
239
    int display_list_size;
240
    DVBSubRegionDisplay *display_list;
241
    DVBSubDisplayDefinition *display_definition;
242
} DVBSubContext;
243

    
244

    
245
static DVBSubObject* get_object(DVBSubContext *ctx, int object_id)
246
{
247
    DVBSubObject *ptr = ctx->object_list;
248

    
249
    while (ptr && ptr->id != object_id) {
250
        ptr = ptr->next;
251
    }
252

    
253
    return ptr;
254
}
255

    
256
static DVBSubCLUT* get_clut(DVBSubContext *ctx, int clut_id)
257
{
258
    DVBSubCLUT *ptr = ctx->clut_list;
259

    
260
    while (ptr && ptr->id != clut_id) {
261
        ptr = ptr->next;
262
    }
263

    
264
    return ptr;
265
}
266

    
267
static DVBSubRegion* get_region(DVBSubContext *ctx, int region_id)
268
{
269
    DVBSubRegion *ptr = ctx->region_list;
270

    
271
    while (ptr && ptr->id != region_id) {
272
        ptr = ptr->next;
273
    }
274

    
275
    return ptr;
276
}
277

    
278
static void delete_region_display_list(DVBSubContext *ctx, DVBSubRegion *region)
279
{
280
    DVBSubObject *object, *obj2, **obj2_ptr;
281
    DVBSubObjectDisplay *display, *obj_disp, **obj_disp_ptr;
282

    
283
    while (region->display_list) {
284
        display = region->display_list;
285

    
286
        object = get_object(ctx, display->object_id);
287

    
288
        if (object) {
289
            obj_disp_ptr = &object->display_list;
290
            obj_disp = *obj_disp_ptr;
291

    
292
            while (obj_disp && obj_disp != display) {
293
                obj_disp_ptr = &obj_disp->object_list_next;
294
                obj_disp = *obj_disp_ptr;
295
            }
296

    
297
            if (obj_disp) {
298
                *obj_disp_ptr = obj_disp->object_list_next;
299

    
300
                if (!object->display_list) {
301
                    obj2_ptr = &ctx->object_list;
302
                    obj2 = *obj2_ptr;
303

    
304
                    while (obj2 != object) {
305
                        assert(obj2);
306
                        obj2_ptr = &obj2->next;
307
                        obj2 = *obj2_ptr;
308
                    }
309

    
310
                    *obj2_ptr = obj2->next;
311

    
312
                    av_free(obj2);
313
                }
314
            }
315
        }
316

    
317
        region->display_list = display->region_list_next;
318

    
319
        av_free(display);
320
    }
321

    
322
}
323

    
324
static void delete_state(DVBSubContext *ctx)
325
{
326
    DVBSubRegion *region;
327
    DVBSubCLUT *clut;
328

    
329
    while (ctx->region_list) {
330
        region = ctx->region_list;
331

    
332
        ctx->region_list = region->next;
333

    
334
        delete_region_display_list(ctx, region);
335
        av_free(region->pbuf);
336
        av_free(region);
337
    }
338

    
339
    while (ctx->clut_list) {
340
        clut = ctx->clut_list;
341

    
342
        ctx->clut_list = clut->next;
343

    
344
        av_free(clut);
345
    }
346

    
347
    av_freep(&ctx->display_definition);
348

    
349
    /* Should already be null */
350
    if (ctx->object_list)
351
        av_log(0, AV_LOG_ERROR, "Memory deallocation error!\n");
352
}
353

    
354
static av_cold int dvbsub_init_decoder(AVCodecContext *avctx)
355
{
356
    int i, r, g, b, a = 0;
357
    DVBSubContext *ctx = avctx->priv_data;
358

    
359
    if (!avctx->extradata || avctx->extradata_size != 4) {
360
        av_log(avctx, AV_LOG_WARNING, "Invalid extradata, subtitle streams may be combined!\n");
361
        ctx->composition_id = -1;
362
        ctx->ancillary_id   = -1;
363
    } else {
364
        ctx->composition_id = AV_RB16(avctx->extradata);
365
        ctx->ancillary_id   = AV_RB16(avctx->extradata + 2);
366
    }
367

    
368
    default_clut.id = -1;
369
    default_clut.next = NULL;
370

    
371
    default_clut.clut4[0] = RGBA(  0,   0,   0,   0);
372
    default_clut.clut4[1] = RGBA(255, 255, 255, 255);
373
    default_clut.clut4[2] = RGBA(  0,   0,   0, 255);
374
    default_clut.clut4[3] = RGBA(127, 127, 127, 255);
375

    
376
    default_clut.clut16[0] = RGBA(  0,   0,   0,   0);
377
    for (i = 1; i < 16; i++) {
378
        if (i < 8) {
379
            r = (i & 1) ? 255 : 0;
380
            g = (i & 2) ? 255 : 0;
381
            b = (i & 4) ? 255 : 0;
382
        } else {
383
            r = (i & 1) ? 127 : 0;
384
            g = (i & 2) ? 127 : 0;
385
            b = (i & 4) ? 127 : 0;
386
        }
387
        default_clut.clut16[i] = RGBA(r, g, b, 255);
388
    }
389

    
390
    default_clut.clut256[0] = RGBA(  0,   0,   0,   0);
391
    for (i = 1; i < 256; i++) {
392
        if (i < 8) {
393
            r = (i & 1) ? 255 : 0;
394
            g = (i & 2) ? 255 : 0;
395
            b = (i & 4) ? 255 : 0;
396
            a = 63;
397
        } else {
398
            switch (i & 0x88) {
399
            case 0x00:
400
                r = ((i & 1) ? 85 : 0) + ((i & 0x10) ? 170 : 0);
401
                g = ((i & 2) ? 85 : 0) + ((i & 0x20) ? 170 : 0);
402
                b = ((i & 4) ? 85 : 0) + ((i & 0x40) ? 170 : 0);
403
                a = 255;
404
                break;
405
            case 0x08:
406
                r = ((i & 1) ? 85 : 0) + ((i & 0x10) ? 170 : 0);
407
                g = ((i & 2) ? 85 : 0) + ((i & 0x20) ? 170 : 0);
408
                b = ((i & 4) ? 85 : 0) + ((i & 0x40) ? 170 : 0);
409
                a = 127;
410
                break;
411
            case 0x80:
412
                r = 127 + ((i & 1) ? 43 : 0) + ((i & 0x10) ? 85 : 0);
413
                g = 127 + ((i & 2) ? 43 : 0) + ((i & 0x20) ? 85 : 0);
414
                b = 127 + ((i & 4) ? 43 : 0) + ((i & 0x40) ? 85 : 0);
415
                a = 255;
416
                break;
417
            case 0x88:
418
                r = ((i & 1) ? 43 : 0) + ((i & 0x10) ? 85 : 0);
419
                g = ((i & 2) ? 43 : 0) + ((i & 0x20) ? 85 : 0);
420
                b = ((i & 4) ? 43 : 0) + ((i & 0x40) ? 85 : 0);
421
                a = 255;
422
                break;
423
            }
424
        }
425
        default_clut.clut256[i] = RGBA(r, g, b, a);
426
    }
427

    
428
    return 0;
429
}
430

    
431
static av_cold int dvbsub_close_decoder(AVCodecContext *avctx)
432
{
433
    DVBSubContext *ctx = avctx->priv_data;
434
    DVBSubRegionDisplay *display;
435

    
436
    delete_state(ctx);
437

    
438
    while (ctx->display_list) {
439
        display = ctx->display_list;
440
        ctx->display_list = display->next;
441

    
442
        av_free(display);
443
    }
444

    
445
    return 0;
446
}
447

    
448
static int dvbsub_read_2bit_string(uint8_t *destbuf, int dbuf_len,
449
                                   const uint8_t **srcbuf, int buf_size,
450
                                   int non_mod, uint8_t *map_table)
451
{
452
    GetBitContext gb;
453

    
454
    int bits;
455
    int run_length;
456
    int pixels_read = 0;
457

    
458
    init_get_bits(&gb, *srcbuf, buf_size << 3);
459

    
460
    while (get_bits_count(&gb) < buf_size << 3 && pixels_read < dbuf_len) {
461
        bits = get_bits(&gb, 2);
462

    
463
        if (bits) {
464
            if (non_mod != 1 || bits != 1) {
465
                if (map_table)
466
                    *destbuf++ = map_table[bits];
467
                else
468
                    *destbuf++ = bits;
469
            }
470
            pixels_read++;
471
        } else {
472
            bits = get_bits1(&gb);
473
            if (bits == 1) {
474
                run_length = get_bits(&gb, 3) + 3;
475
                bits = get_bits(&gb, 2);
476

    
477
                if (non_mod == 1 && bits == 1)
478
                    pixels_read += run_length;
479
                else {
480
                    if (map_table)
481
                        bits = map_table[bits];
482
                    while (run_length-- > 0 && pixels_read < dbuf_len) {
483
                        *destbuf++ = bits;
484
                        pixels_read++;
485
                    }
486
                }
487
            } else {
488
                bits = get_bits1(&gb);
489
                if (bits == 0) {
490
                    bits = get_bits(&gb, 2);
491
                    if (bits == 2) {
492
                        run_length = get_bits(&gb, 4) + 12;
493
                        bits = get_bits(&gb, 2);
494

    
495
                        if (non_mod == 1 && bits == 1)
496
                            pixels_read += run_length;
497
                        else {
498
                            if (map_table)
499
                                bits = map_table[bits];
500
                            while (run_length-- > 0 && pixels_read < dbuf_len) {
501
                                *destbuf++ = bits;
502
                                pixels_read++;
503
                            }
504
                        }
505
                    } else if (bits == 3) {
506
                        run_length = get_bits(&gb, 8) + 29;
507
                        bits = get_bits(&gb, 2);
508

    
509
                        if (non_mod == 1 && bits == 1)
510
                            pixels_read += run_length;
511
                        else {
512
                            if (map_table)
513
                                bits = map_table[bits];
514
                            while (run_length-- > 0 && pixels_read < dbuf_len) {
515
                                *destbuf++ = bits;
516
                                pixels_read++;
517
                            }
518
                        }
519
                    } else if (bits == 1) {
520
                        pixels_read += 2;
521
                        if (map_table)
522
                            bits = map_table[0];
523
                        else
524
                            bits = 0;
525
                        if (pixels_read <= dbuf_len) {
526
                            *destbuf++ = bits;
527
                            *destbuf++ = bits;
528
                        }
529
                    } else {
530
                        (*srcbuf) += (get_bits_count(&gb) + 7) >> 3;
531
                        return pixels_read;
532
                    }
533
                } else {
534
                    if (map_table)
535
                        bits = map_table[0];
536
                    else
537
                        bits = 0;
538
                    *destbuf++ = bits;
539
                    pixels_read++;
540
                }
541
            }
542
        }
543
    }
544

    
545
    if (get_bits(&gb, 6))
546
        av_log(0, AV_LOG_ERROR, "DVBSub error: line overflow\n");
547

    
548
    (*srcbuf) += (get_bits_count(&gb) + 7) >> 3;
549

    
550
    return pixels_read;
551
}
552

    
553
static int dvbsub_read_4bit_string(uint8_t *destbuf, int dbuf_len,
554
                                   const uint8_t **srcbuf, int buf_size,
555
                                   int non_mod, uint8_t *map_table)
556
{
557
    GetBitContext gb;
558

    
559
    int bits;
560
    int run_length;
561
    int pixels_read = 0;
562

    
563
    init_get_bits(&gb, *srcbuf, buf_size << 3);
564

    
565
    while (get_bits_count(&gb) < buf_size << 3 && pixels_read < dbuf_len) {
566
        bits = get_bits(&gb, 4);
567

    
568
        if (bits) {
569
            if (non_mod != 1 || bits != 1) {
570
                if (map_table)
571
                    *destbuf++ = map_table[bits];
572
                else
573
                    *destbuf++ = bits;
574
            }
575
            pixels_read++;
576
        } else {
577
            bits = get_bits1(&gb);
578
            if (bits == 0) {
579
                run_length = get_bits(&gb, 3);
580

    
581
                if (run_length == 0) {
582
                    (*srcbuf) += (get_bits_count(&gb) + 7) >> 3;
583
                    return pixels_read;
584
                }
585

    
586
                run_length += 2;
587

    
588
                if (map_table)
589
                    bits = map_table[0];
590
                else
591
                    bits = 0;
592

    
593
                while (run_length-- > 0 && pixels_read < dbuf_len) {
594
                    *destbuf++ = bits;
595
                    pixels_read++;
596
                }
597
            } else {
598
                bits = get_bits1(&gb);
599
                if (bits == 0) {
600
                    run_length = get_bits(&gb, 2) + 4;
601
                    bits = get_bits(&gb, 4);
602

    
603
                    if (non_mod == 1 && bits == 1)
604
                        pixels_read += run_length;
605
                    else {
606
                        if (map_table)
607
                            bits = map_table[bits];
608
                        while (run_length-- > 0 && pixels_read < dbuf_len) {
609
                            *destbuf++ = bits;
610
                            pixels_read++;
611
                        }
612
                    }
613
                } else {
614
                    bits = get_bits(&gb, 2);
615
                    if (bits == 2) {
616
                        run_length = get_bits(&gb, 4) + 9;
617
                        bits = get_bits(&gb, 4);
618

    
619
                        if (non_mod == 1 && bits == 1)
620
                            pixels_read += run_length;
621
                        else {
622
                            if (map_table)
623
                                bits = map_table[bits];
624
                            while (run_length-- > 0 && pixels_read < dbuf_len) {
625
                                *destbuf++ = bits;
626
                                pixels_read++;
627
                            }
628
                        }
629
                    } else if (bits == 3) {
630
                        run_length = get_bits(&gb, 8) + 25;
631
                        bits = get_bits(&gb, 4);
632

    
633
                        if (non_mod == 1 && bits == 1)
634
                            pixels_read += run_length;
635
                        else {
636
                            if (map_table)
637
                                bits = map_table[bits];
638
                            while (run_length-- > 0 && pixels_read < dbuf_len) {
639
                                *destbuf++ = bits;
640
                                pixels_read++;
641
                            }
642
                        }
643
                    } else if (bits == 1) {
644
                        pixels_read += 2;
645
                        if (map_table)
646
                            bits = map_table[0];
647
                        else
648
                            bits = 0;
649
                        if (pixels_read <= dbuf_len) {
650
                            *destbuf++ = bits;
651
                            *destbuf++ = bits;
652
                        }
653
                    } else {
654
                        if (map_table)
655
                            bits = map_table[0];
656
                        else
657
                            bits = 0;
658
                        *destbuf++ = bits;
659
                        pixels_read ++;
660
                    }
661
                }
662
            }
663
        }
664
    }
665

    
666
    if (get_bits(&gb, 8))
667
        av_log(0, AV_LOG_ERROR, "DVBSub error: line overflow\n");
668

    
669
    (*srcbuf) += (get_bits_count(&gb) + 7) >> 3;
670

    
671
    return pixels_read;
672
}
673

    
674
static int dvbsub_read_8bit_string(uint8_t *destbuf, int dbuf_len,
675
                                    const uint8_t **srcbuf, int buf_size,
676
                                    int non_mod, uint8_t *map_table)
677
{
678
    const uint8_t *sbuf_end = (*srcbuf) + buf_size;
679
    int bits;
680
    int run_length;
681
    int pixels_read = 0;
682

    
683
    while (*srcbuf < sbuf_end && pixels_read < dbuf_len) {
684
        bits = *(*srcbuf)++;
685

    
686
        if (bits) {
687
            if (non_mod != 1 || bits != 1) {
688
                if (map_table)
689
                    *destbuf++ = map_table[bits];
690
                else
691
                    *destbuf++ = bits;
692
            }
693
            pixels_read++;
694
        } else {
695
            bits = *(*srcbuf)++;
696
            run_length = bits & 0x7f;
697
            if ((bits & 0x80) == 0) {
698
                if (run_length == 0) {
699
                    return pixels_read;
700
                }
701

    
702
                if (map_table)
703
                    bits = map_table[0];
704
                else
705
                    bits = 0;
706
                while (run_length-- > 0 && pixels_read < dbuf_len) {
707
                    *destbuf++ = bits;
708
                    pixels_read++;
709
                }
710
            } else {
711
                bits = *(*srcbuf)++;
712

    
713
                if (non_mod == 1 && bits == 1)
714
                    pixels_read += run_length;
715
                if (map_table)
716
                    bits = map_table[bits];
717
                else while (run_length-- > 0 && pixels_read < dbuf_len) {
718
                    *destbuf++ = bits;
719
                    pixels_read++;
720
                }
721
            }
722
        }
723
    }
724

    
725
    if (*(*srcbuf)++)
726
        av_log(0, AV_LOG_ERROR, "DVBSub error: line overflow\n");
727

    
728
    return pixels_read;
729
}
730

    
731

    
732

    
733
static void dvbsub_parse_pixel_data_block(AVCodecContext *avctx, DVBSubObjectDisplay *display,
734
                                          const uint8_t *buf, int buf_size, int top_bottom, int non_mod)
735
{
736
    DVBSubContext *ctx = avctx->priv_data;
737

    
738
    DVBSubRegion *region = get_region(ctx, display->region_id);
739
    const uint8_t *buf_end = buf + buf_size;
740
    uint8_t *pbuf;
741
    int x_pos, y_pos;
742
    int i;
743

    
744
    uint8_t map2to4[] = { 0x0,  0x7,  0x8,  0xf};
745
    uint8_t map2to8[] = {0x00, 0x77, 0x88, 0xff};
746
    uint8_t map4to8[] = {0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77,
747
                         0x88, 0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff};
748
    uint8_t *map_table;
749

    
750
    av_dlog(avctx, "DVB pixel block size %d, %s field:\n", buf_size,
751
            top_bottom ? "bottom" : "top");
752

    
753
#ifdef DEBUG_PACKET_CONTENTS
754
    for (i = 0; i < buf_size; i++) {
755
        if (i % 16 == 0)
756
            av_log(avctx, AV_LOG_INFO, "0x%08p: ", buf+i);
757

    
758
        av_log(avctx, AV_LOG_INFO, "%02x ", buf[i]);
759
        if (i % 16 == 15)
760
            av_log(avctx, AV_LOG_INFO, "\n");
761
    }
762

    
763
    if (i % 16)
764
        av_log(avctx, AV_LOG_INFO, "\n");
765

    
766
#endif
767

    
768
    if (region == 0)
769
        return;
770

    
771
    pbuf = region->pbuf;
772

    
773
    x_pos = display->x_pos;
774
    y_pos = display->y_pos;
775

    
776
    if ((y_pos & 1) != top_bottom)
777
        y_pos++;
778

    
779
    while (buf < buf_end) {
780
        if (x_pos > region->width || y_pos > region->height) {
781
            av_log(avctx, AV_LOG_ERROR, "Invalid object location!\n");
782
            return;
783
        }
784

    
785
        switch (*buf++) {
786
        case 0x10:
787
            if (region->depth == 8)
788
                map_table = map2to8;
789
            else if (region->depth == 4)
790
                map_table = map2to4;
791
            else
792
                map_table = NULL;
793

    
794
            x_pos += dvbsub_read_2bit_string(pbuf + (y_pos * region->width) + x_pos,
795
                                                region->width - x_pos, &buf, buf_size,
796
                                                non_mod, map_table);
797
            break;
798
        case 0x11:
799
            if (region->depth < 4) {
800
                av_log(avctx, AV_LOG_ERROR, "4-bit pixel string in %d-bit region!\n", region->depth);
801
                return;
802
            }
803

    
804
            if (region->depth == 8)
805
                map_table = map4to8;
806
            else
807
                map_table = NULL;
808

    
809
            x_pos += dvbsub_read_4bit_string(pbuf + (y_pos * region->width) + x_pos,
810
                                                region->width - x_pos, &buf, buf_size,
811
                                                non_mod, map_table);
812
            break;
813
        case 0x12:
814
            if (region->depth < 8) {
815
                av_log(avctx, AV_LOG_ERROR, "8-bit pixel string in %d-bit region!\n", region->depth);
816
                return;
817
            }
818

    
819
            x_pos += dvbsub_read_8bit_string(pbuf + (y_pos * region->width) + x_pos,
820
                                                region->width - x_pos, &buf, buf_size,
821
                                                non_mod, NULL);
822
            break;
823

    
824
        case 0x20:
825
            map2to4[0] = (*buf) >> 4;
826
            map2to4[1] = (*buf++) & 0xf;
827
            map2to4[2] = (*buf) >> 4;
828
            map2to4[3] = (*buf++) & 0xf;
829
            break;
830
        case 0x21:
831
            for (i = 0; i < 4; i++)
832
                map2to8[i] = *buf++;
833
            break;
834
        case 0x22:
835
            for (i = 0; i < 16; i++)
836
                map4to8[i] = *buf++;
837
            break;
838

    
839
        case 0xf0:
840
            x_pos = display->x_pos;
841
            y_pos += 2;
842
            break;
843
        default:
844
            av_log(avctx, AV_LOG_INFO, "Unknown/unsupported pixel block 0x%x\n", *(buf-1));
845
        }
846
    }
847

    
848
}
849

    
850
static void dvbsub_parse_object_segment(AVCodecContext *avctx,
851
                                        const uint8_t *buf, int buf_size)
852
{
853
    DVBSubContext *ctx = avctx->priv_data;
854

    
855
    const uint8_t *buf_end = buf + buf_size;
856
    const uint8_t *block;
857
    int object_id;
858
    DVBSubObject *object;
859
    DVBSubObjectDisplay *display;
860
    int top_field_len, bottom_field_len;
861

    
862
    int coding_method, non_modifying_color;
863

    
864
    object_id = AV_RB16(buf);
865
    buf += 2;
866

    
867
    object = get_object(ctx, object_id);
868

    
869
    if (!object)
870
        return;
871

    
872
    coding_method = ((*buf) >> 2) & 3;
873
    non_modifying_color = ((*buf++) >> 1) & 1;
874

    
875
    if (coding_method == 0) {
876
        top_field_len = AV_RB16(buf);
877
        buf += 2;
878
        bottom_field_len = AV_RB16(buf);
879
        buf += 2;
880

    
881
        if (buf + top_field_len + bottom_field_len > buf_end) {
882
            av_log(avctx, AV_LOG_ERROR, "Field data size too large\n");
883
            return;
884
        }
885

    
886
        for (display = object->display_list; display; display = display->object_list_next) {
887
            block = buf;
888

    
889
            dvbsub_parse_pixel_data_block(avctx, display, block, top_field_len, 0,
890
                                            non_modifying_color);
891

    
892
            if (bottom_field_len > 0)
893
                block = buf + top_field_len;
894
            else
895
                bottom_field_len = top_field_len;
896

    
897
            dvbsub_parse_pixel_data_block(avctx, display, block, bottom_field_len, 1,
898
                                            non_modifying_color);
899
        }
900

    
901
/*  } else if (coding_method == 1) {*/
902

    
903
    } else {
904
        av_log(avctx, AV_LOG_ERROR, "Unknown object coding %d\n", coding_method);
905
    }
906

    
907
}
908

    
909
static void dvbsub_parse_clut_segment(AVCodecContext *avctx,
910
                                        const uint8_t *buf, int buf_size)
911
{
912
    DVBSubContext *ctx = avctx->priv_data;
913

    
914
    const uint8_t *buf_end = buf + buf_size;
915
    int clut_id;
916
    DVBSubCLUT *clut;
917
    int entry_id, depth , full_range;
918
    int y, cr, cb, alpha;
919
    int r, g, b, r_add, g_add, b_add;
920

    
921
#ifdef DEBUG_PACKET_CONTENTS
922
    int i;
923

    
924
    av_log(avctx, AV_LOG_INFO, "DVB clut packet:\n");
925

    
926
    for (i=0; i < buf_size; i++) {
927
        av_log(avctx, AV_LOG_INFO, "%02x ", buf[i]);
928
        if (i % 16 == 15)
929
            av_log(avctx, AV_LOG_INFO, "\n");
930
    }
931

    
932
    if (i % 16)
933
        av_log(avctx, AV_LOG_INFO, "\n");
934

    
935
#endif
936

    
937
    clut_id = *buf++;
938
    buf += 1;
939

    
940
    clut = get_clut(ctx, clut_id);
941

    
942
    if (!clut) {
943
        clut = av_malloc(sizeof(DVBSubCLUT));
944

    
945
        memcpy(clut, &default_clut, sizeof(DVBSubCLUT));
946

    
947
        clut->id = clut_id;
948

    
949
        clut->next = ctx->clut_list;
950
        ctx->clut_list = clut;
951
    }
952

    
953
    while (buf + 4 < buf_end) {
954
        entry_id = *buf++;
955

    
956
        depth = (*buf) & 0xe0;
957

    
958
        if (depth == 0) {
959
            av_log(avctx, AV_LOG_ERROR, "Invalid clut depth 0x%x!\n", *buf);
960
            return;
961
        }
962

    
963
        full_range = (*buf++) & 1;
964

    
965
        if (full_range) {
966
            y = *buf++;
967
            cr = *buf++;
968
            cb = *buf++;
969
            alpha = *buf++;
970
        } else {
971
            y = buf[0] & 0xfc;
972
            cr = (((buf[0] & 3) << 2) | ((buf[1] >> 6) & 3)) << 4;
973
            cb = (buf[1] << 2) & 0xf0;
974
            alpha = (buf[1] << 6) & 0xc0;
975

    
976
            buf += 2;
977
        }
978

    
979
        if (y == 0)
980
            alpha = 0xff;
981

    
982
        YUV_TO_RGB1_CCIR(cb, cr);
983
        YUV_TO_RGB2_CCIR(r, g, b, y);
984

    
985
        av_dlog(avctx, "clut %d := (%d,%d,%d,%d)\n", entry_id, r, g, b, alpha);
986

    
987
        if (depth & 0x80)
988
            clut->clut4[entry_id] = RGBA(r,g,b,255 - alpha);
989
        if (depth & 0x40)
990
            clut->clut16[entry_id] = RGBA(r,g,b,255 - alpha);
991
        if (depth & 0x20)
992
            clut->clut256[entry_id] = RGBA(r,g,b,255 - alpha);
993
    }
994
}
995

    
996

    
997
static void dvbsub_parse_region_segment(AVCodecContext *avctx,
998
                                        const uint8_t *buf, int buf_size)
999
{
1000
    DVBSubContext *ctx = avctx->priv_data;
1001

    
1002
    const uint8_t *buf_end = buf + buf_size;
1003
    int region_id, object_id;
1004
    DVBSubRegion *region;
1005
    DVBSubObject *object;
1006
    DVBSubObjectDisplay *display;
1007
    int fill;
1008

    
1009
    if (buf_size < 10)
1010
        return;
1011

    
1012
    region_id = *buf++;
1013

    
1014
    region = get_region(ctx, region_id);
1015

    
1016
    if (!region) {
1017
        region = av_mallocz(sizeof(DVBSubRegion));
1018

    
1019
        region->id = region_id;
1020

    
1021
        region->next = ctx->region_list;
1022
        ctx->region_list = region;
1023
    }
1024

    
1025
    fill = ((*buf++) >> 3) & 1;
1026

    
1027
    region->width = AV_RB16(buf);
1028
    buf += 2;
1029
    region->height = AV_RB16(buf);
1030
    buf += 2;
1031

    
1032
    if (region->width * region->height != region->buf_size) {
1033
        av_free(region->pbuf);
1034

    
1035
        region->buf_size = region->width * region->height;
1036

    
1037
        region->pbuf = av_malloc(region->buf_size);
1038

    
1039
        fill = 1;
1040
    }
1041

    
1042
    region->depth = 1 << (((*buf++) >> 2) & 7);
1043
    if(region->depth<2 || region->depth>8){
1044
        av_log(avctx, AV_LOG_ERROR, "region depth %d is invalid\n", region->depth);
1045
        region->depth= 4;
1046
    }
1047
    region->clut = *buf++;
1048

    
1049
    if (region->depth == 8)
1050
        region->bgcolor = *buf++;
1051
    else {
1052
        buf += 1;
1053

    
1054
        if (region->depth == 4)
1055
            region->bgcolor = (((*buf++) >> 4) & 15);
1056
        else
1057
            region->bgcolor = (((*buf++) >> 2) & 3);
1058
    }
1059

    
1060
    av_dlog(avctx, "Region %d, (%dx%d)\n", region_id, region->width, region->height);
1061

    
1062
    if (fill) {
1063
        memset(region->pbuf, region->bgcolor, region->buf_size);
1064
        av_dlog(avctx, "Fill region (%d)\n", region->bgcolor);
1065
    }
1066

    
1067
    delete_region_display_list(ctx, region);
1068

    
1069
    while (buf + 5 < buf_end) {
1070
        object_id = AV_RB16(buf);
1071
        buf += 2;
1072

    
1073
        object = get_object(ctx, object_id);
1074

    
1075
        if (!object) {
1076
            object = av_mallocz(sizeof(DVBSubObject));
1077

    
1078
            object->id = object_id;
1079
            object->next = ctx->object_list;
1080
            ctx->object_list = object;
1081
        }
1082

    
1083
        object->type = (*buf) >> 6;
1084

    
1085
        display = av_mallocz(sizeof(DVBSubObjectDisplay));
1086

    
1087
        display->object_id = object_id;
1088
        display->region_id = region_id;
1089

    
1090
        display->x_pos = AV_RB16(buf) & 0xfff;
1091
        buf += 2;
1092
        display->y_pos = AV_RB16(buf) & 0xfff;
1093
        buf += 2;
1094

    
1095
        if ((object->type == 1 || object->type == 2) && buf+1 < buf_end) {
1096
            display->fgcolor = *buf++;
1097
            display->bgcolor = *buf++;
1098
        }
1099

    
1100
        display->region_list_next = region->display_list;
1101
        region->display_list = display;
1102

    
1103
        display->object_list_next = object->display_list;
1104
        object->display_list = display;
1105
    }
1106
}
1107

    
1108
static void dvbsub_parse_page_segment(AVCodecContext *avctx,
1109
                                        const uint8_t *buf, int buf_size)
1110
{
1111
    DVBSubContext *ctx = avctx->priv_data;
1112
    DVBSubRegionDisplay *display;
1113
    DVBSubRegionDisplay *tmp_display_list, **tmp_ptr;
1114

    
1115
    const uint8_t *buf_end = buf + buf_size;
1116
    int region_id;
1117
    int page_state;
1118

    
1119
    if (buf_size < 1)
1120
        return;
1121

    
1122
    ctx->time_out = *buf++;
1123
    page_state = ((*buf++) >> 2) & 3;
1124

    
1125
    av_dlog(avctx, "Page time out %ds, state %d\n", ctx->time_out, page_state);
1126

    
1127
    if (page_state == 2) {
1128
        delete_state(ctx);
1129
    }
1130

    
1131
    tmp_display_list = ctx->display_list;
1132
    ctx->display_list = NULL;
1133
    ctx->display_list_size = 0;
1134

    
1135
    while (buf + 5 < buf_end) {
1136
        region_id = *buf++;
1137
        buf += 1;
1138

    
1139
        display = tmp_display_list;
1140
        tmp_ptr = &tmp_display_list;
1141

    
1142
        while (display && display->region_id != region_id) {
1143
            tmp_ptr = &display->next;
1144
            display = display->next;
1145
        }
1146

    
1147
        if (!display)
1148
            display = av_mallocz(sizeof(DVBSubRegionDisplay));
1149

    
1150
        display->region_id = region_id;
1151

    
1152
        display->x_pos = AV_RB16(buf);
1153
        buf += 2;
1154
        display->y_pos = AV_RB16(buf);
1155
        buf += 2;
1156

    
1157
        *tmp_ptr = display->next;
1158

    
1159
        display->next = ctx->display_list;
1160
        ctx->display_list = display;
1161
        ctx->display_list_size++;
1162

    
1163
        av_dlog(avctx, "Region %d, (%d,%d)\n", region_id, display->x_pos, display->y_pos);
1164
    }
1165

    
1166
    while (tmp_display_list) {
1167
        display = tmp_display_list;
1168

    
1169
        tmp_display_list = display->next;
1170

    
1171
        av_free(display);
1172
    }
1173

    
1174
}
1175

    
1176

    
1177
#ifdef DEBUG_SAVE_IMAGES
1178
static void save_display_set(DVBSubContext *ctx)
1179
{
1180
    DVBSubRegion *region;
1181
    DVBSubRegionDisplay *display;
1182
    DVBSubCLUT *clut;
1183
    uint32_t *clut_table;
1184
    int x_pos, y_pos, width, height;
1185
    int x, y, y_off, x_off;
1186
    uint32_t *pbuf;
1187
    char filename[32];
1188
    static int fileno_index = 0;
1189

    
1190
    x_pos = -1;
1191
    y_pos = -1;
1192
    width = 0;
1193
    height = 0;
1194

    
1195
    for (display = ctx->display_list; display; display = display->next) {
1196
        region = get_region(ctx, display->region_id);
1197

    
1198
        if (x_pos == -1) {
1199
            x_pos = display->x_pos;
1200
            y_pos = display->y_pos;
1201
            width = region->width;
1202
            height = region->height;
1203
        } else {
1204
            if (display->x_pos < x_pos) {
1205
                width += (x_pos - display->x_pos);
1206
                x_pos = display->x_pos;
1207
            }
1208

    
1209
            if (display->y_pos < y_pos) {
1210
                height += (y_pos - display->y_pos);
1211
                y_pos = display->y_pos;
1212
            }
1213

    
1214
            if (display->x_pos + region->width > x_pos + width) {
1215
                width = display->x_pos + region->width - x_pos;
1216
            }
1217

    
1218
            if (display->y_pos + region->height > y_pos + height) {
1219
                height = display->y_pos + region->height - y_pos;
1220
            }
1221
        }
1222
    }
1223

    
1224
    if (x_pos >= 0) {
1225

    
1226
        pbuf = av_malloc(width * height * 4);
1227

    
1228
        for (display = ctx->display_list; display; display = display->next) {
1229
            region = get_region(ctx, display->region_id);
1230

    
1231
            x_off = display->x_pos - x_pos;
1232
            y_off = display->y_pos - y_pos;
1233

    
1234
            clut = get_clut(ctx, region->clut);
1235

    
1236
            if (clut == 0)
1237
                clut = &default_clut;
1238

    
1239
            switch (region->depth) {
1240
            case 2:
1241
                clut_table = clut->clut4;
1242
                break;
1243
            case 8:
1244
                clut_table = clut->clut256;
1245
                break;
1246
            case 4:
1247
            default:
1248
                clut_table = clut->clut16;
1249
                break;
1250
            }
1251

    
1252
            for (y = 0; y < region->height; y++) {
1253
                for (x = 0; x < region->width; x++) {
1254
                    pbuf[((y + y_off) * width) + x_off + x] =
1255
                        clut_table[region->pbuf[y * region->width + x]];
1256
                }
1257
            }
1258

    
1259
        }
1260

    
1261
        snprintf(filename, sizeof(filename), "dvbs.%d", fileno_index);
1262

    
1263
        png_save2(filename, pbuf, width, height);
1264

    
1265
        av_free(pbuf);
1266
    }
1267

    
1268
    fileno_index++;
1269
}
1270
#endif
1271

    
1272
static void dvbsub_parse_display_definition_segment(AVCodecContext *avctx,
1273
                                                    const uint8_t *buf,
1274
                                                    int buf_size)
1275
{
1276
    DVBSubContext *ctx = avctx->priv_data;
1277
    DVBSubDisplayDefinition *display_def = ctx->display_definition;
1278
    int dds_version, info_byte;
1279

    
1280
    if (buf_size < 5)
1281
        return;
1282

    
1283
    info_byte   = bytestream_get_byte(&buf);
1284
    dds_version = info_byte >> 4;
1285
    if (display_def && display_def->version == dds_version)
1286
        return; // already have this display definition version
1287

    
1288
    if (!display_def) {
1289
        display_def             = av_mallocz(sizeof(*display_def));
1290
        ctx->display_definition = display_def;
1291
    }
1292
    if (!display_def)
1293
        return;
1294

    
1295
    display_def->version = dds_version;
1296
    display_def->x       = 0;
1297
    display_def->y       = 0;
1298
    display_def->width   = bytestream_get_be16(&buf) + 1;
1299
    display_def->height  = bytestream_get_be16(&buf) + 1;
1300

    
1301
    if (buf_size < 13)
1302
        return;
1303

    
1304
    if (info_byte & 1<<3) { // display_window_flag
1305
        display_def->x = bytestream_get_be16(&buf);
1306
        display_def->y = bytestream_get_be16(&buf);
1307
        display_def->width  = bytestream_get_be16(&buf) - display_def->x + 1;
1308
        display_def->height = bytestream_get_be16(&buf) - display_def->y + 1;
1309
    }
1310
}
1311

    
1312
static int dvbsub_display_end_segment(AVCodecContext *avctx, const uint8_t *buf,
1313
                                        int buf_size, AVSubtitle *sub)
1314
{
1315
    DVBSubContext *ctx = avctx->priv_data;
1316
    DVBSubDisplayDefinition *display_def = ctx->display_definition;
1317

    
1318
    DVBSubRegion *region;
1319
    DVBSubRegionDisplay *display;
1320
    AVSubtitleRect *rect;
1321
    DVBSubCLUT *clut;
1322
    uint32_t *clut_table;
1323
    int i;
1324
    int offset_x=0, offset_y=0;
1325

    
1326
    sub->rects = NULL;
1327
    sub->start_display_time = 0;
1328
    sub->end_display_time = ctx->time_out * 1000;
1329
    sub->format = 0;
1330

    
1331
    if (display_def) {
1332
        offset_x = display_def->x;
1333
        offset_y = display_def->y;
1334
    }
1335

    
1336
    sub->num_rects = ctx->display_list_size;
1337

    
1338
    if (sub->num_rects > 0){
1339
        sub->rects = av_mallocz(sizeof(*sub->rects) * sub->num_rects);
1340
        for(i=0; i<sub->num_rects; i++)
1341
            sub->rects[i] = av_mallocz(sizeof(*sub->rects[i]));
1342
    }
1343

    
1344
    i = 0;
1345

    
1346
    for (display = ctx->display_list; display; display = display->next) {
1347
        region = get_region(ctx, display->region_id);
1348
        rect = sub->rects[i];
1349

    
1350
        if (!region)
1351
            continue;
1352

    
1353
        rect->x = display->x_pos + offset_x;
1354
        rect->y = display->y_pos + offset_y;
1355
        rect->w = region->width;
1356
        rect->h = region->height;
1357
        rect->nb_colors = 16;
1358
        rect->type      = SUBTITLE_BITMAP;
1359
        rect->pict.linesize[0] = region->width;
1360

    
1361
        clut = get_clut(ctx, region->clut);
1362

    
1363
        if (!clut)
1364
            clut = &default_clut;
1365

    
1366
        switch (region->depth) {
1367
        case 2:
1368
            clut_table = clut->clut4;
1369
            break;
1370
        case 8:
1371
            clut_table = clut->clut256;
1372
            break;
1373
        case 4:
1374
        default:
1375
            clut_table = clut->clut16;
1376
            break;
1377
        }
1378

    
1379
        rect->pict.data[1] = av_mallocz(AVPALETTE_SIZE);
1380
        memcpy(rect->pict.data[1], clut_table, (1 << region->depth) * sizeof(uint32_t));
1381

    
1382
        rect->pict.data[0] = av_malloc(region->buf_size);
1383
        memcpy(rect->pict.data[0], region->pbuf, region->buf_size);
1384

    
1385
        i++;
1386
    }
1387

    
1388
    sub->num_rects = i;
1389

    
1390
#ifdef DEBUG_SAVE_IMAGES
1391
    save_display_set(ctx);
1392
#endif
1393

    
1394
    return 1;
1395
}
1396

    
1397
static int dvbsub_decode(AVCodecContext *avctx,
1398
                         void *data, int *data_size,
1399
                         AVPacket *avpkt)
1400
{
1401
    const uint8_t *buf = avpkt->data;
1402
    int buf_size = avpkt->size;
1403
    DVBSubContext *ctx = avctx->priv_data;
1404
    AVSubtitle *sub = data;
1405
    const uint8_t *p, *p_end;
1406
    int segment_type;
1407
    int page_id;
1408
    int segment_length;
1409

    
1410
#ifdef DEBUG_PACKET_CONTENTS
1411
    int i;
1412

    
1413
    av_log(avctx, AV_LOG_INFO, "DVB sub packet:\n");
1414

    
1415
    for (i=0; i < buf_size; i++) {
1416
        av_log(avctx, AV_LOG_INFO, "%02x ", buf[i]);
1417
        if (i % 16 == 15)
1418
            av_log(avctx, AV_LOG_INFO, "\n");
1419
    }
1420

    
1421
    if (i % 16)
1422
        av_log(avctx, AV_LOG_INFO, "\n");
1423

    
1424
#endif
1425

    
1426
    if (buf_size <= 2)
1427
        return -1;
1428

    
1429
    p = buf;
1430
    p_end = buf + buf_size;
1431

    
1432
    while (p < p_end && *p == 0x0f) {
1433
        p += 1;
1434
        segment_type = *p++;
1435
        page_id = AV_RB16(p);
1436
        p += 2;
1437
        segment_length = AV_RB16(p);
1438
        p += 2;
1439

    
1440
        if (page_id == ctx->composition_id || page_id == ctx->ancillary_id ||
1441
            ctx->composition_id == -1 || ctx->ancillary_id == -1) {
1442
            switch (segment_type) {
1443
            case DVBSUB_PAGE_SEGMENT:
1444
                dvbsub_parse_page_segment(avctx, p, segment_length);
1445
                break;
1446
            case DVBSUB_REGION_SEGMENT:
1447
                dvbsub_parse_region_segment(avctx, p, segment_length);
1448
                break;
1449
            case DVBSUB_CLUT_SEGMENT:
1450
                dvbsub_parse_clut_segment(avctx, p, segment_length);
1451
                break;
1452
            case DVBSUB_OBJECT_SEGMENT:
1453
                dvbsub_parse_object_segment(avctx, p, segment_length);
1454
                break;
1455
            case DVBSUB_DISPLAYDEFINITION_SEGMENT:
1456
                dvbsub_parse_display_definition_segment(avctx, p, segment_length);
1457
            case DVBSUB_DISPLAY_SEGMENT:
1458
                *data_size = dvbsub_display_end_segment(avctx, p, segment_length, sub);
1459
                break;
1460
            default:
1461
                av_dlog(avctx, "Subtitling segment type 0x%x, page id %d, length %d\n",
1462
                        segment_type, page_id, segment_length);
1463
                break;
1464
            }
1465
        }
1466

    
1467
        p += segment_length;
1468
    }
1469

    
1470
    if (p != p_end) {
1471
        av_dlog(avctx, "Junk at end of packet\n");
1472
        return -1;
1473
    }
1474

    
1475
    return buf_size;
1476
}
1477

    
1478

    
1479
AVCodec ff_dvbsub_decoder = {
1480
    "dvbsub",
1481
    AVMEDIA_TYPE_SUBTITLE,
1482
    CODEC_ID_DVB_SUBTITLE,
1483
    sizeof(DVBSubContext),
1484
    dvbsub_init_decoder,
1485
    NULL,
1486
    dvbsub_close_decoder,
1487
    dvbsub_decode,
1488
    .long_name = NULL_IF_CONFIG_SMALL("DVB subtitles"),
1489
};