Revision b6a17df4 libavformat/mov.c

View differences:

libavformat/mov.c
79 79
	   (unsigned int)size);
80 80
    assert((unsigned int)size < 0x7fffffff);// catching errors
81 81
}
82
#else
83
#define print_atom(a,b,c,d)
82 84
#endif
83 85

  
84 86
/* some streams in QT (and in MP4 mostly) aren't either video nor audio */
85 87
/* so we first list them as this, then clean up the list of streams we give back, */
86 88
/* getting rid of these */
87
#define CODEC_TYPE_MOV_OTHER 2
89
#define CODEC_TYPE_MOV_OTHER	(enum CodecType) 2
88 90

  
89 91
static const CodecTag mov_video_tags[] = {
90 92
/*  { CODEC_ID_, MKTAG('c', 'v', 'i', 'd') }, *//* Cinepak */
......
197 199
    uint8_t *sl_config;
198 200
} MOV_esds_t;
199 201

  
202
struct MOVParseTableEntry;
203

  
200 204
typedef struct MOVStreamContext {
201 205
    int ffindex; /* the ffmpeg stream id */
202 206
    int is_ff_stream; /* Is this stream presented to ffmpeg ? i.e. is this an audio or video stream ? */
......
235 239

  
236 240
    int64_t next_chunk_offset;
237 241
    MOVStreamContext *partial; /* != 0 : there is still to read in the current chunk */
242
    const struct MOVParseTableEntry *parse_table; /* could be eventually used to change the table */
243
    /* NOTE: for recursion save to/ restore from local variable! */
238 244
} MOVContext;
239 245

  
240 246

  
241
struct MOVParseTableEntry;
242

  
243 247
/* XXX: it's the first time I make a recursive parser I think... sorry if it's ugly :P */
244 248

  
245 249
/* those functions parse an atom */
......
248 252
 0: continue to parse next atom
249 253
 -1: error occured, exit
250 254
 */
251
typedef int (*mov_parse_function)(const struct MOVParseTableEntry *parse_table,
255
typedef int (*mov_parse_function)(MOVContext *ctx,
252 256
                                  ByteIOContext *pb,
253 257
                                  uint32_t atom_type,
254 258
                                  int64_t atom_offset, /* after the size and type field (and eventually the extended size) */
255
                                  int64_t atom_size, /* total size (excluding the size and type fields) */
256
                                  void *param);
259
                                  int64_t atom_size); /* total size (excluding the size and type fields) */
257 260

  
258 261
/* links atom IDs to parse functions */
259 262
typedef struct MOVParseTableEntry {
260 263
    uint32_t type;
261 264
    mov_parse_function func;
262 265
} MOVParseTableEntry;
263
static const MOVParseTableEntry mov_default_parse_table[];
264 266

  
265
static int parse_leaf(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
267
static int parse_leaf(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
266 268
{
267
#ifdef DEBUG
268 269
    print_atom("leaf", atom_type, atom_offset, atom_size);
269
#endif
270

  
270 271
    if(atom_size>1)
271 272
        url_fskip(pb, atom_size);
272 273
/*        url_seek(pb, atom_offset+atom_size, SEEK_SET); */
273 274
    return 0;
274 275
}
275 276

  
276

  
277
static int parse_default(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
277
static int parse_default(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
278 278
{
279 279
    uint32_t type, foo=0;
280 280
    uint64_t offset, size;
281
    uint64_t total_size = 0;
281
    int64_t total_size = 0;
282 282
    int i;
283 283
    int err = 0;
284 284
    foo=0;
......
311 311
	    if (size <= 8)
312 312
                break;
313 313
	}
314
	for (i=0; parse_table[i].type != 0L && parse_table[i].type != type; i++)
314
	for (i=0; c->parse_table[i].type != 0L && c->parse_table[i].type != type; i++)
315 315
	    /* empty */;
316 316

  
317 317
        size -= 8;
318 318
//        printf(" i=%ld\n", i);
319
	if (parse_table[i].type == 0) { /* skip leaf atoms data */
319
	if (c->parse_table[i].type == 0) { /* skip leaf atoms data */
320 320
//            url_seek(pb, atom_offset+atom_size, SEEK_SET);
321 321
#ifdef DEBUG
322 322
            print_atom("unknown", type, offset, size);
323 323
#endif
324 324
            url_fskip(pb, size);
325
        } else
326
            err = (parse_table[i].func)(parse_table, pb, type, offset, size, param);
325
	} else {
326
#ifdef DEBUG
327
	    //char b[5] = { type & 0xff, (type >> 8) & 0xff, (type >> 16) & 0xff, (type >> 24) & 0xff, 0 };
328
	    //print_atom(b, type, offset, size);
329
#endif
330
	    err = (c->parse_table[i].func)(c, pb, type, offset, size);
331
	}
327 332

  
328 333
        offset+=size;
329 334
        total_size+=size;
......
340 345
    return err;
341 346
}
342 347

  
343
static int parse_ctab(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
348
static int parse_ctab(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
344 349
{
345 350
    url_fskip(pb, atom_size); // for now
346 351
    return 0;
347 352
}
348 353

  
349
static int parse_mvhd(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
354
static int parse_mvhd(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
350 355
{
351
    MOVContext *c;
352
#ifdef DEBUG
353 356
    print_atom("mvhd", atom_type, atom_offset, atom_size);
354
#endif
355
    c = (MOVContext *)param;
356 357

  
357 358
    get_byte(pb); /* version */
358 359
    get_byte(pb); get_byte(pb); get_byte(pb); /* flags */
......
384 385
}
385 386

  
386 387
/* this atom should contain all header atoms */
387
static int parse_moov(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
388
static int parse_moov(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
388 389
{
389 390
    int err;
390
    MOVContext *c;
391
#ifdef DEBUG
391

  
392 392
    print_atom("moov", atom_type, atom_offset, atom_size);
393
#endif
394
    c = (MOVContext *)param;
395 393

  
396
    err = parse_default(parse_table, pb, atom_type, atom_offset, atom_size, param);
394
    err = parse_default(c, pb, atom_type, atom_offset, atom_size);
397 395
    /* we parsed the 'moov' atom, we can terminate the parsing as soon as we find the 'mdat' */
398 396
    /* so we don't parse the whole file if over a network */
399 397
    c->found_moov=1;
......
403 401
}
404 402

  
405 403
/* this atom contains actual media data */
406
static int parse_mdat(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
404
static int parse_mdat(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
407 405
{
408
    MOVContext *c;
409
#ifdef DEBUG
410 406
    print_atom("mdat", atom_type, atom_offset, atom_size);
411
#endif
412
    c = (MOVContext *)param;
413 407

  
414 408
    if(atom_size == 0) /* wrong one (MP4) */
415 409
        return 0;
......
425 419
/* this atom should be null (from specs), but some buggy files put the 'moov' atom inside it... */
426 420
/* like the files created with Adobe Premiere 5.0, for samples see */
427 421
/* http://graphics.tudelft.nl/~wouter/publications/soundtests/ */
428
static int parse_wide(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
422
static int parse_wide(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
429 423
{
430 424
    int err;
431 425
    uint32_t type;
426

  
432 427
#ifdef DEBUG
433 428
    print_atom("wide", atom_type, atom_offset, atom_size);
434 429
    debug_indent++;
......
444 439
        url_fskip(pb, atom_size - 8);
445 440
        return 0;
446 441
    }
447
    err = parse_mdat(parse_table, pb, type, atom_offset + 8, atom_size - 8, param);
442
    err = parse_mdat(c, pb, type, atom_offset + 8, atom_size - 8);
448 443
#ifdef DEBUG
449 444
    debug_indent--;
450 445
#endif
451 446
    return err;
452 447
}
453 448

  
454
static int parse_trak(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
449
static int parse_trak(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
455 450
{
456
    MOVContext *c;
457 451
    AVStream *st;
458 452
    MOVStreamContext *sc;
459
#ifdef DEBUG
453

  
460 454
    print_atom("trak", atom_type, atom_offset, atom_size);
461
#endif
462 455

  
463
    c = (MOVContext *)param;
464 456
    st = av_new_stream(c->fc, c->fc->nb_streams);
465 457
    if (!st) return -2;
466
    sc = av_malloc(sizeof(MOVStreamContext));
467
    memset(sc, 0, sizeof(MOVStreamContext));
458
    sc = (MOVStreamContext*) av_mallocz(sizeof(MOVStreamContext));
459
    if (!sc) {
460
	av_free(st);
461
        return -1;
462
    }
463

  
468 464
    sc->sample_to_chunk_index = -1;
469 465
    st->priv_data = sc;
470 466
    st->codec.codec_type = CODEC_TYPE_MOV_OTHER;
471 467
    st->time_length = (c->duration * 1000) / c->time_scale; // time in miliseconds
472 468
    c->streams[c->fc->nb_streams-1] = sc;
473
    return parse_default(parse_table, pb, atom_type, atom_offset, atom_size, param);
469
    return parse_default(c, pb, atom_type, atom_offset, atom_size);
474 470
}
475 471

  
476
static int parse_tkhd(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
472
static int parse_tkhd(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
477 473
{
478
    MOVContext *c;
479 474
    AVStream *st;
480
#ifdef DEBUG
475

  
481 476
    print_atom("tkhd", atom_type, atom_offset, atom_size);
482
#endif
483 477

  
484
    c = (MOVContext *)param;
485 478
    st = c->fc->streams[c->fc->nb_streams-1];
486 479

  
487 480
    get_byte(pb); /* version */
......
517 510
    return 0;
518 511
}
519 512

  
520
static int parse_mdhd(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
513
static int parse_mdhd(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
521 514
{
522
    MOVContext *c;
523 515
    AVStream *st;
524
#ifdef DEBUG
516

  
525 517
    print_atom("mdhd", atom_type, atom_offset, atom_size);
526
#endif
527 518

  
528
    c = (MOVContext *)param;
529 519
    st = c->fc->streams[c->fc->nb_streams-1];
530 520

  
531 521
    get_byte(pb); /* version */
......
549 539
    return 0;
550 540
}
551 541

  
552
static int parse_hdlr(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
542
static int parse_hdlr(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
553 543
{
554
    MOVContext *c;
555 544
    int len = 0;
556
    char *buf;
545
    uint8_t *buf;
557 546
    uint32_t type;
558 547
    AVStream *st;
559 548
    uint32_t ctype;
560
#ifdef DEBUG
549

  
561 550
    print_atom("hdlr", atom_type, atom_offset, atom_size);
562
#endif
563
    c = (MOVContext *)param;
551

  
564 552
    st = c->fc->streams[c->fc->nb_streams-1];
565 553

  
566 554
    get_byte(pb); /* version */
......
623 611
    } else {
624 612
        /* .mov: PASCAL string */
625 613
        len = get_byte(pb);
626
        buf = av_malloc(len+1);
627
        get_buffer(pb, buf, len);
628
        buf[len] = '\0';
614
	buf = (uint8_t*) av_malloc(len+1);
615
	if (buf) {
616
	    get_buffer(pb, buf, len);
629 617
#ifdef DEBUG
630
        printf("**buf='%s'\n", buf);
618
	    buf[len] = '\0';
619
	    printf("**buf='%s'\n", buf);
631 620
#endif
632
        av_free(buf);
621
	    av_free(buf);
622
	} else
623
	    url_fskip(pb, len);
633 624
    }
634 625
#if 0
635 626
    len = get_byte(pb);
636 627
    /* XXX: use a better heuristic */
637 628
    if(len < 32) {
638 629
        /* assume that it is a Pascal like string */
639
        buf = av_malloc(len+1);
640
        get_buffer(pb, buf, len);
641
        buf[len] = '\0';
630
	buf = av_malloc(len+1);
631
	if (buf) {
632
	    get_buffer(pb, buf, len);
633
	    buf[len] = '\0';
642 634
#ifdef DEBUG
643
        printf("**buf='%s'\n", buf);
635
	    printf("**buf='%s'\n", buf);
644 636
#endif
645
        av_free(buf);
637
	    av_free(buf);
638
	} else
639
            url_fskip(pb, len)l
646 640
    } else {
647 641
        /* MP4 string */
648 642
        for(;;) {
......
691 685
    return val;
692 686
}
693 687

  
694
static int parse_esds(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
688
static int parse_esds(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
695 689
{
696 690

  
697 691
    int64_t start_pos = url_ftell(pb);
698
    MOVContext *c = (MOVContext *)param;
699 692
    AVStream *st = c->fc->streams[c->fc->nb_streams-1];
700 693
    MOVStreamContext *sc = (MOVStreamContext *)st->priv_data;
701 694
    int tag, len;
702
#ifdef DEBUG
695

  
703 696
    print_atom("esds", atom_type, atom_offset, atom_size);
704
#endif
705 697

  
706 698
    /* Well, broken but suffisant for some MP4 streams */
707 699
    get_be32(pb); /* version + flags */
......
725 717
#ifdef DEBUG
726 718
	    printf("Specific MPEG4 header len=%d\n", len);
727 719
#endif
728
	    sc->header_data = av_mallocz(len);
720
	    sc->header_data = (uint8_t*) av_mallocz(len);
729 721
	    if (sc->header_data) {
730 722
		get_buffer(pb, sc->header_data, len);
731 723
		sc->header_len = len;
......
737 729
    return 0;
738 730
}
739 731

  
740
static int parse_stsd(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
732
static int parse_stsd(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
741 733
{
742
    MOVContext *c;
743
    int entries, size, frames_per_sample, id;
734
    int entries, size, frames_per_sample;
744 735
    uint32_t format;
745 736
    AVStream *st;
746 737
    MOVStreamContext *sc;
747
#ifdef DEBUG
738

  
748 739
    print_atom("stsd", atom_type, atom_offset, atom_size);
749
#endif
750
    c = (MOVContext *)param;
740

  
751 741
    st = c->fc->streams[c->fc->nb_streams-1];
752 742
    sc = (MOVStreamContext *)st->priv_data;
753 743

  
......
757 747
    entries = get_be32(pb);
758 748

  
759 749
    while(entries--) {
750
        enum CodecID id;
760 751
	size = get_be32(pb); /* size */
761 752
        format = get_le32(pb); /* data format */
762 753

  
......
768 759
        id = codec_get_id(mov_video_tags, format);
769 760
        if (id >= 0) {
770 761
            AVCodec *codec;
771
            codec = avcodec_find_decoder(id);
762
	    codec = avcodec_find_decoder(id);
772 763
            if (codec)
773
                st->codec.codec_type = codec->type;
764
		st->codec.codec_type = codec->type;
774 765
        }
775 766
#ifdef DEBUG
776 767
        printf("size=%d 4CC= %c%c%c%c codec_type=%d\n",
......
806 797
#ifdef DEBUG
807 798
	    printf("frames/samples = %d\n", frames_per_sample);
808 799
#endif
809
	    get_buffer(pb, st->codec.codec_name, 32); /* codec name */
800
	    get_buffer(pb, (uint8_t *)st->codec.codec_name, 32); /* codec name */
810 801

  
811 802
	    st->codec.bits_per_sample = get_be16(pb); /* depth */
812 803
            st->codec.color_table_id = get_be16(pb); /* colortable id */
......
886 877
                url_fskip(pb, size);
887 878
            }
888 879
#else
889
	    parse_default(mov_default_parse_table, pb, 0L, 0LL, size, param);
880
	    parse_default(c, pb, 0L, 0LL, size);
890 881
#endif
891 882
	} else {
892 883
            get_be16(pb); /* version */
......
902 893
            get_be16(pb); /* packet size = 0 */
903 894

  
904 895
            st->codec.sample_rate = ((get_be32(pb) >> 16));
896
	    printf("CODECID %d  %d  %.4s\n", st->codec.codec_id, CODEC_ID_PCM_S16BE, (char*)&format);
905 897

  
906
	    if (st->codec.codec_id == CODEC_ID_PCM_S16BE) {
898
	    switch (st->codec.codec_id) {
899
	    case CODEC_ID_PCM_S16BE:
907 900
		if (st->codec.bits_per_sample == 8)
908 901
		    st->codec.codec_id = CODEC_ID_PCM_S8;
909
                st->codec.bit_rate = st->codec.sample_rate;
902
                /* fall */
903
	    case CODEC_ID_PCM_U8:
904
		st->codec.bit_rate = st->codec.sample_rate * 8;
905
		break;
906
	    default:
907
                ;
910 908
	    }
911 909
	    get_be32(pb); /* samples per packet */
912 910
	    get_be32(pb); /* bytes per packet */
......
921 919
		fcc = get_le32(pb); // evaw
922 920
		//printf("%x  %.4s  %d\n", fcc, (char*)&fcc, st->codec.extradata_size);
923 921
		st->codec.extradata = av_mallocz(st->codec.extradata_size);
924
                get_buffer(pb, st->codec.extradata, st->codec.extradata_size);
922
                if (st->codec.extradata)
923
		    get_buffer(pb, st->codec.extradata, st->codec.extradata_size); // FIXME url_fskip
925 924
		url_fskip(pb, size-(16 + 20 + 16 + 8 + st->codec.extradata_size));
926 925
	    }
927 926
            else
928 927
		url_fskip(pb, size-(16 + 20 + 16));
929 928
#else
930
	    parse_default(mov_default_parse_table, pb, 0L, 0LL, size - (16 + 20 + 16 + 8), param);
929
	    parse_default(c, pb, 0L, 0LL, size - (16 + 20 + 16 + 8));
931 930
#endif
932 931
        }
933 932
    }
......
943 942
    return 0;
944 943
}
945 944

  
946
static int parse_stco(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
945
static int parse_stco(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
947 946
{
948
    MOVContext *c;
949 947
    int entries, i;
950 948
    AVStream *st;
951 949
    MOVStreamContext *sc;
952
#ifdef DEBUG
950

  
953 951
    print_atom("stco", atom_type, atom_offset, atom_size);
954
#endif
955
    c = (MOVContext *)param;
952

  
956 953
    st = c->fc->streams[c->fc->nb_streams-1];
957 954
    sc = (MOVStreamContext *)st->priv_data;
958 955

  
......
961 958

  
962 959
    entries = get_be32(pb);
963 960
    sc->chunk_count = entries;
964
    sc->chunk_offsets = av_malloc(entries * sizeof(int64_t));
961
    sc->chunk_offsets = (int64_t*) av_malloc(entries * sizeof(int64_t));
962
    if (!sc->chunk_offsets)
963
        return -1;
965 964
    if(atom_type == MKTAG('s', 't', 'c', 'o')) {
966 965
        for(i=0; i<entries; i++) {
967 966
            sc->chunk_offsets[i] = get_be32(pb);
......
982 981
    return 0;
983 982
}
984 983

  
985
static int parse_stsc(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
984
static int parse_stsc(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
986 985
{
987
    MOVContext *c;
988 986
    int entries, i;
989 987
    AVStream *st;
990 988
    MOVStreamContext *sc;
991
#ifdef DEBUG
989

  
992 990
    print_atom("stsc", atom_type, atom_offset, atom_size);
993
#endif
994
    c = (MOVContext *)param;
991

  
995 992
    st = c->fc->streams[c->fc->nb_streams-1];
996 993
    sc = (MOVStreamContext *)st->priv_data;
997 994

  
......
1003 1000
printf("track[%i].stsc.entries = %i\n", c->fc->nb_streams-1, entries);
1004 1001
#endif
1005 1002
    sc->sample_to_chunk_sz = entries;
1006
    sc->sample_to_chunk = av_malloc(entries * sizeof(MOV_sample_to_chunk_tbl));
1003
    sc->sample_to_chunk = (MOV_sample_to_chunk_tbl*) av_malloc(entries * sizeof(MOV_sample_to_chunk_tbl));
1004
    if (!sc->sample_to_chunk)
1005
        return -1;
1007 1006
    for(i=0; i<entries; i++) {
1008 1007
        sc->sample_to_chunk[i].first = get_be32(pb);
1009 1008
        sc->sample_to_chunk[i].count = get_be32(pb);
......
1015 1014
    return 0;
1016 1015
}
1017 1016

  
1018
static int parse_stsz(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
1017
static int parse_stsz(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
1019 1018
{
1020
    MOVContext *c;
1021 1019
    int entries, i;
1022 1020
    AVStream *st;
1023 1021
    MOVStreamContext *sc;
1024
#ifdef DEBUG
1022

  
1025 1023
    print_atom("stsz", atom_type, atom_offset, atom_size);
1026
#endif
1027
    c = (MOVContext *)param;
1024

  
1028 1025
    st = c->fc->streams[c->fc->nb_streams-1];
1029 1026
    sc = (MOVStreamContext *)st->priv_data;
1030 1027

  
......
1039 1036
#endif
1040 1037
    if(sc->sample_size)
1041 1038
        return 0; /* there isn't any table following */
1042
    sc->sample_sizes = av_malloc(entries * sizeof(long));
1039
    sc->sample_sizes = (long*) av_malloc(entries * sizeof(long));
1040
    if (!sc->sample_sizes)
1041
        return -1;
1043 1042
    for(i=0; i<entries; i++) {
1044 1043
        sc->sample_sizes[i] = get_be32(pb);
1045 1044
#ifdef DEBUG
......
1049 1048
    return 0;
1050 1049
}
1051 1050

  
1052
static int parse_stts(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
1051
static int parse_stts(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
1053 1052
{
1054
    MOVContext *c;
1055 1053
    int entries, i;
1056 1054
    AVStream *st;
1057 1055
    MOVStreamContext *sc;
1058
#ifdef DEBUG
1056

  
1059 1057
    print_atom("stts", atom_type, atom_offset, atom_size);
1060
#endif
1061
    c = (MOVContext *)param;
1058

  
1062 1059
    st = c->fc->streams[c->fc->nb_streams-1];
1063 1060
    sc = (MOVStreamContext *)st->priv_data;
1064 1061

  
......
1091 1088
    return -1;
1092 1089
}
1093 1090

  
1094
static int parse_cmov(const MOVParseTableEntry *parse_table, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size, void *param)
1091
static int parse_cmov(MOVContext *c, ByteIOContext *pb, uint32_t atom_type, int64_t atom_offset, int64_t atom_size)
1095 1092
{
1096
    MOVContext *c;
1097 1093
    ByteIOContext ctx;
1098
    char *cmov_data;
1099
    unsigned char *moov_data; /* uncompressed data */
1094
    uint8_t *cmov_data;
1095
    uint8_t *moov_data; /* uncompressed data */
1100 1096
    long cmov_len, moov_len;
1101 1097
    int ret;
1102
#ifdef DEBUG
1098

  
1103 1099
    print_atom("cmov", atom_type, atom_offset, atom_size);
1104
#endif
1105
    c = (MOVContext *)param;
1106 1100

  
1107 1101
    get_be32(pb); /* dcom atom */
1108 1102
    if (get_le32(pb) != MKTAG( 'd', 'c', 'o', 'm' ))
......
1117 1111
    moov_len = get_be32(pb); /* uncompressed size */
1118 1112
    cmov_len = atom_size - 6 * 4;
1119 1113

  
1120
    cmov_data = av_malloc(cmov_len);
1114
    cmov_data = (uint8_t *) av_malloc(cmov_len);
1121 1115
    if (!cmov_data)
1122 1116
        return -1;
1123
    moov_data = av_malloc(moov_len);
1117
    moov_data = (uint8_t *) av_malloc(moov_len);
1124 1118
    if (!moov_data) {
1125 1119
        av_free(cmov_data);
1126 1120
        return -1;
1127 1121
    }
1128 1122
    get_buffer(pb, cmov_data, cmov_len);
1129
    if(uncompress (moov_data, &moov_len, (const Bytef *)cmov_data, cmov_len) != Z_OK)
1123
    if(uncompress (moov_data, (uLongf *) &moov_len, (const Bytef *)cmov_data, cmov_len) != Z_OK)
1130 1124
        return -1;
1131 1125
    if(init_put_byte(&ctx, moov_data, moov_len, 0, NULL, null_read_packet, NULL, NULL) != 0)
1132 1126
        return -1;
1133 1127
    ctx.buf_end = ctx.buffer + moov_len;
1134
    ret = parse_default(parse_table, &ctx, MKTAG( 'm', 'o', 'o', 'v' ), 0, moov_len, param);
1128
    ret = parse_default(c, &ctx, MKTAG( 'm', 'o', 'o', 'v' ), 0, moov_len);
1135 1129
    av_free(moov_data);
1136 1130
    av_free(cmov_data);
1137 1131
    return ret;
......
1235 1229
    return (buf[0] << 24) | (buf[1] << 16) | (buf[2] << 8) | buf[3];
1236 1230
}
1237 1231

  
1238
/* XXX: is it suffisant ? */
1232
/* XXX: is it sufficient ? */
1239 1233
static int mov_probe(AVProbeData *p)
1240 1234
{
1241 1235
    unsigned int offset;
......
1271 1265

  
1272 1266
static int mov_read_header(AVFormatContext *s, AVFormatParameters *ap)
1273 1267
{
1274
    MOVContext *mov = s->priv_data;
1268
    MOVContext *mov = (MOVContext *) s->priv_data;
1275 1269
    ByteIOContext *pb = &s->pb;
1276 1270
    int i, j, nb, err;
1277 1271
    int64_t size;
1278 1272

  
1279 1273
    mov->fc = s;
1274
    mov->parse_table = mov_default_parse_table;
1280 1275
#if 0
1281 1276
    /* XXX: I think we should auto detect */
1282 1277
    if(s->iformat->name[1] == 'p')
......
1292 1287
#endif
1293 1288

  
1294 1289
    /* check MOV header */
1295
    err = parse_default(mov_default_parse_table, pb, 0L, 0LL, size, mov);
1290
    err = parse_default(mov, pb, 0L, 0LL, size);
1296 1291
    if(err<0 || (!mov->found_moov || !mov->found_mdat)) {
1297 1292
        puts("header not found !!!");
1298 1293
        exit(1);
......
1342 1337
/* XXX:remove useless commented code sometime */
1343 1338
static int mov_read_packet(AVFormatContext *s, AVPacket *pkt)
1344 1339
{
1345
    MOVContext *mov = s->priv_data;
1340
    MOVContext *mov = (MOVContext *) s->priv_data;
1346 1341
    MOVStreamContext *sc;
1347 1342
    int64_t offset = 0x0FFFFFFFFFFFFFFF;
1348 1343
    int i;
......
1472 1467
static int mov_read_close(AVFormatContext *s)
1473 1468
{
1474 1469
    int i;
1475
    MOVContext *mov = s->priv_data;
1470
    MOVContext *mov = (MOVContext *) s->priv_data;
1476 1471
    for(i=0; i<mov->total_streams; i++)
1477 1472
        mov_free_stream_context(mov->streams[i]);
1478 1473
    for(i=0; i<s->nb_streams; i++)

Also available in: Unified diff