Changeset 36bde12633aa3997e24a121db8cf1fb56f936f96
- Timestamp:
- 24/05/08 00:49:22 (6 months ago)
- git-parent:
- Files:
-
- modules/demux/real.c (modified) (24 diffs)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
modules/demux/real.c
r13ae40b r36bde12 96 96 int i_subpackets; 97 97 block_t **p_subpackets; 98 int64_t *p_subpackets_timecode; 98 99 int i_out_subpacket; 99 100 100 101 } real_track_t; 102 103 typedef struct 104 { 105 uint32_t file_offset; 106 uint32_t time_offset; 107 uint32_t frame_index; 108 } rm_index_t; 101 109 102 110 struct demux_sys_t … … 122 130 123 131 int64_t i_pcr; 132 vlc_meta_t *p_meta; 133 134 int64_t i_index_offset; 135 int b_seek; 136 rm_index_t * p_index; 124 137 }; 125 138 … … 164 177 p_sys->i_pcr = 1; 165 178 179 p_sys->b_seek = 0; 166 180 167 181 /* Parse the headers */ … … 213 227 block_Release( tk->p_subpackets[ j ] ); 214 228 } 215 if( tk->i_subpackets ) free( tk->p_subpackets ); 229 if( tk->i_subpackets ) 230 { 231 free( tk->p_subpackets ); 232 free( tk->p_subpackets_timecode ); 233 } 216 234 217 235 free( tk ); … … 222 240 free( p_sys->psz_copyright ); 223 241 free( p_sys->psz_description ); 242 free( p_sys->p_index ); 224 243 225 244 if( p_sys->i_track > 0 ) free( p_sys->track ); … … 517 536 518 537 /* Sanity check */ 519 if( i_flags & 2 ) y = tk->i_subpacket = 0; 538 if( i_flags & 2 || ( p_sys->b_seek ) ) 539 { 540 y = tk->i_subpacket = 0; 541 tk->i_out_subpacket = 0; 542 p_sys->b_seek = 0; 543 } 520 544 521 545 if( tk->fmt.i_codec == VLC_FOURCC( 'c', 'o', 'o', 'k' ) || 522 546 tk->fmt.i_codec == VLC_FOURCC( 'a', 't', 'r', 'c' )) 523 for( i = 0; i < tk->i_frame_size / tk->i_subpacket_size; i++ ) 524 { 525 block_t *p_block = block_New( p_demux, tk->i_subpacket_size ); 526 memcpy( p_block->p_buffer, p_buf, tk->i_subpacket_size ); 527 p_buf += tk->i_subpacket_size; 528 529 i_index = tk->i_subpacket_h * i + 530 ((tk->i_subpacket_h + 1) / 2) * (y&1) + (y>>1); 547 { 548 int num = tk->i_frame_size / tk->i_subpacket_size; 549 for( i = 0; i < num; i++ ) 550 { 551 block_t *p_block = block_New( p_demux, tk->i_subpacket_size ); 552 memcpy( p_block->p_buffer, p_buf, tk->i_subpacket_size ); 553 p_buf += tk->i_subpacket_size; 554 555 i_index = tk->i_subpacket_h * i + 556 ((tk->i_subpacket_h + 1) / 2) * (y&1) + (y>>1); 557 558 if ( tk->p_subpackets[i_index] != NULL ) 559 { 560 msg_Dbg(p_demux, "p_subpackets[ %d ] not null!", i_index ); 561 free( tk->p_subpackets[i_index] ); 562 } 563 564 tk->p_subpackets[i_index] = p_block; 565 tk->i_subpacket++; 566 p_block->i_dts = p_block->i_pts = 0; 567 } 568 tk->p_subpackets_timecode[tk->i_subpacket - num] = i_pts; 569 } 570 571 if( tk->fmt.i_codec == VLC_FOURCC( '2', '8', '_', '8' ) || 572 tk->fmt.i_codec == VLC_FOURCC( 's', 'i', 'p', 'r' ) ) 573 for( i = 0; i < tk->i_subpacket_h / 2; i++ ) 574 { 575 block_t *p_block = block_New( p_demux, tk->i_coded_frame_size); 576 memcpy( p_block->p_buffer, p_buf, tk->i_coded_frame_size ); 577 p_buf += tk->i_coded_frame_size; 578 579 i_index = (i * 2 * tk->i_frame_size) / 580 tk->i_coded_frame_size + y; 531 581 532 582 p_block->i_dts = p_block->i_pts = i_pts; … … 535 585 } 536 586 537 if( tk->fmt.i_codec == VLC_FOURCC( '2', '8', '_', '8' ) ||538 tk->fmt.i_codec == VLC_FOURCC( 's', 'i', 'p', 'r' ) )539 for( i = 0; i < tk->i_subpacket_h / 2; i++ )540 {541 block_t *p_block = block_New( p_demux, tk->i_coded_frame_size);542 memcpy( p_block->p_buffer, p_buf, tk->i_coded_frame_size );543 p_buf += tk->i_coded_frame_size;544 545 i_index = (i * 2 * tk->i_frame_size) /546 tk->i_coded_frame_size + y;547 548 p_block->i_dts = p_block->i_pts = i_pts;549 tk->p_subpackets[i_index] = p_block;550 tk->i_subpacket++;551 }552 553 587 while( tk->i_out_subpacket != tk->i_subpackets && 554 588 tk->p_subpackets[tk->i_out_subpacket] ) 555 589 { 556 590 /* Set the PCR */ 591 #if 0 557 592 if (tk->i_out_subpacket == 0) 558 593 { … … 566 601 567 602 if( tk->i_out_subpacket ) p_block->i_dts = p_block->i_pts = 0; 603 #endif 604 605 block_t *p_block = tk->p_subpackets[tk->i_out_subpacket]; 606 tk->p_subpackets[tk->i_out_subpacket] = 0; 607 //if ( p_block->i_dts ) 608 if ( tk->p_subpackets_timecode[tk->i_out_subpacket] ) 609 { 610 p_block->i_dts = p_block->i_pts = 611 tk->p_subpackets_timecode[tk->i_out_subpacket]; 612 tk->p_subpackets_timecode[tk->i_out_subpacket] = 0; 613 614 p_sys->i_pcr = p_block->i_dts; 615 es_out_Control( p_demux->out, ES_OUT_SET_PCR, 616 (int64_t)p_sys->i_pcr ); 617 } 568 618 es_out_Send( p_demux->out, tk->p_es, p_block ); 569 619 … … 654 704 { 655 705 demux_sys_t *p_sys = p_demux->p_sys; 656 #if 0657 706 double f, *pf; 658 707 int64_t i64; 659 #endif 708 rm_index_t * p_index; 660 709 int64_t *pi64; 661 710 662 711 switch( i_query ) 663 712 { 664 #if 0665 713 case DEMUX_GET_POSITION: 666 714 pf = (double*) va_arg( args, double* ); 715 716 if( p_sys->i_our_duration > 0 ) 717 { 718 *pf = (double)p_sys->i_pcr / 1000.0 / p_sys->i_our_duration; 719 return VLC_SUCCESS; 720 } 721 722 /* read stream size maybe failed in rtsp streaming, 723 so use duration to determin the position at first */ 667 724 i64 = stream_Size( p_demux->s ); 668 725 if( i64 > 0 ) 669 726 { 670 *pf = (double) stream_Tell( p_demux->s ) / (double)i64;727 *pf = (double)1.0*stream_Tell( p_demux->s ) / (double)i64; 671 728 } 672 729 else … … 675 732 } 676 733 return VLC_SUCCESS; 734 735 case DEMUX_GET_TIME: 736 pi64 = (int64_t*)va_arg( args, int64_t * ); 737 738 if( p_sys->i_our_duration > 0 ) 739 { 740 *pi64 = p_sys->i_pcr; 741 return VLC_SUCCESS; 742 } 743 744 /* same as GET_POSTION */ 745 i64 = stream_Size( p_demux->s ); 746 if( p_sys->i_our_duration > 0 && i64 > 0 ) 747 { 748 *pi64 = (int64_t)( 1000.0 * p_sys->i_our_duration * stream_Tell( p_demux->s ) / i64 ); 749 return VLC_SUCCESS; 750 } 751 752 *pi64 = 0; 753 return VLC_EGENERIC; 677 754 678 755 case DEMUX_SET_POSITION: 679 756 f = (double) va_arg( args, double ); 680 i64 = stream_Size( p_demux->s ); 681 682 es_out_Control( p_demux->out, ES_OUT_RESET_PCR ); 683 684 return stream_Seek( p_demux->s, (int64_t)(i64 * f) ); 685 686 case DEMUX_GET_TIME: 687 pi64 = (int64_t*)va_arg( args, int64_t * ); 688 if( p_sys->i_mux_rate > 0 ) 689 { 690 *pi64 = (int64_t)1000000 * ( stream_Tell( p_demux->s ) / 50 ) / p_sys->i_mux_rate; 691 return VLC_SUCCESS; 692 } 693 *pi64 = 0; 694 return VLC_EGENERIC; 695 #endif 757 i64 = (int64_t) ( stream_Size( p_demux->s ) * f ); 758 759 //msg_Dbg(p_demux,"Seek Real DEMUX_SET_POSITION : %f file_offset :"I64Fd" p_sys->i_pcr "I64Fd" ", f, i64 , p_sys->i_pcr ); 760 761 if ( p_sys->i_index_offset == 0 && i64 != 0 ) 762 { 763 msg_Err(p_demux,"Seek No Index Real File failed!" ); 764 return VLC_EGENERIC; // no index! 765 } 766 if ( i64 == 0 ) 767 { 768 /* it is a rtsp stream , it is specials in access/rtsp/... */ 769 770 msg_Dbg(p_demux, "Seek in real rtsp stream!"); 771 p_sys->i_pcr = (int64_t)1000 * ( p_sys->i_our_duration * f ); 772 773 es_out_Control( p_demux->out, ES_OUT_RESET_PCR , p_sys->i_pcr ); 774 p_sys->b_seek = 1; 775 776 return stream_Seek( p_demux->s, p_sys->i_pcr ); 777 } 778 779 if ( p_sys->i_index_offset > 0 ) 780 { 781 p_index = p_sys->p_index; 782 while( p_index->file_offset !=0 ) 783 { 784 if ( p_index->file_offset > i64 ) 785 { 786 /* 787 msg_Dbg(p_demux, "Seek Real find! %d %d %d", p_index->time_offset, p_index->file_offset ,(uint32_t) i64); 788 */ 789 if ( p_index != p_sys->p_index ) p_index --; 790 i64 = p_index->file_offset; 791 break; 792 } 793 p_index++; 794 } 795 796 //msg_Dbg(p_demux, "Seek Real pcr from :"I64Fd" to "I64Fd" ", p_sys->i_pcr , 1000 * (int64_t) p_index->time_offset ); 797 p_sys->i_pcr = 1000 * (int64_t) p_index->time_offset; 798 799 es_out_Control( p_demux->out, ES_OUT_RESET_PCR , p_sys->i_pcr ); 800 801 return stream_Seek( p_demux->s, i64 ); 802 } 803 case DEMUX_SET_TIME: 804 i64 = (int64_t) va_arg( args, int64_t ) / 1000; 805 //msg_Dbg(p_demux,"DEMUX_SET_TIME :OK "I64Fd" ",i64); 806 807 p_index = p_sys->p_index; 808 while( p_index->file_offset !=0 ) 809 { 810 if ( p_index->time_offset > i64 ) 811 { 812 if ( p_index != p_sys->p_index ) 813 p_index --; 814 i64 = p_index->file_offset; 815 break; 816 } 817 p_index++; 818 } 819 820 p_sys->i_pcr = 1000 * (int64_t) p_index->time_offset; 821 es_out_Control( p_demux->out, ES_OUT_RESET_PCR , p_sys->i_pcr ); 822 823 return stream_Seek( p_demux->s, i64 ); 696 824 697 825 case DEMUX_GET_LENGTH: … … 732 860 } 733 861 734 case DEMUX_SET_TIME:735 862 case DEMUX_GET_FPS: 736 863 default: … … 738 865 } 739 866 return VLC_EGENERIC; 867 } 868 869 /***************************************************************************** 870 * ReadRealIndex: 871 *****************************************************************************/ 872 873 static void ReadRealIndex( demux_t *p_demux ) 874 { 875 demux_sys_t *p_sys = p_demux->p_sys; 876 uint8_t buffer[100]; 877 uint32_t i_id; 878 uint32_t i_size; 879 int i_version; 880 int i; 881 882 uint32_t i_index_count; 883 884 if ( p_sys->i_index_offset == 0 ) 885 return; 886 887 stream_Seek( p_demux->s, p_sys->i_index_offset ); 888 889 if ( stream_Read( p_demux->s, buffer, 20 ) < 20 ) 890 return ; 891 892 i_id = VLC_FOURCC( buffer[0], buffer[1], buffer[2], buffer[3] ); 893 i_size = GetDWBE( &buffer[4] ); 894 i_version = GetWBE( &buffer[8] ); 895 896 msg_Dbg( p_demux, "Real index %4.4s size=%d version=%d", 897 (char*)&i_id, i_size, i_version ); 898 899 if( (i_size < 20) && (i_id != VLC_FOURCC('I','N','D','X')) ) 900 return; 901 902 i_index_count = GetDWBE( &buffer[10] ); 903 904 msg_Dbg( p_demux, "Real Index : num : %d ", i_index_count ); 905 906 if ( i_index_count == 0 ) 907 return; 908 909 if ( GetDWBE( &buffer[16] ) > 0 ) 910 msg_Dbg( p_demux, "Real Index: next index is exist? %d ", GetDWBE( &buffer[16] ) ); 911 912 p_sys->p_index = ( rm_index_t *) malloc( sizeof(rm_index_t) * (i_index_count+1) ); 913 if ( p_sys->p_index == NULL ) 914 { 915 msg_Err( p_demux, "Real Index: Error , fail to malloc index buffer " ); 916 return; 917 } 918 919 memset( p_sys->p_index, 0, sizeof(rm_index_t) * (i_index_count+1) ); 920 921 for( i=0; i<i_index_count; i++ ) 922 { 923 if ( stream_Read( p_demux->s, buffer, 14 ) < 14 ) 924 return ; 925 926 if ( GetWBE( &buffer[0] ) != 0 ) 927 { 928 msg_Dbg( p_demux, "Real Index: invaild version of index entry %d ", GetWBE( &buffer[0] ) ); 929 return; 930 } 931 932 p_sys->p_index[i].time_offset = GetDWBE( &buffer[2] ); 933 p_sys->p_index[i].file_offset = GetDWBE( &buffer[6] ); 934 p_sys->p_index[i].frame_index = GetDWBE( &buffer[10] ); 935 #if 0 936 msg_Dbg( p_demux, "Real Index: time %d file %d frame %d ", p_sys->p_index[i].time_offset, p_sys->p_index[i].file_offset , p_sys->p_index[i].frame_index ); 937 #endif 938 939 } 940 740 941 } 741 942 … … 752 953 int64_t i_skip; 753 954 int i_version; 955 p_sys->p_meta = vlc_meta_New(); 754 956 755 957 for( ;; ) … … 802 1004 p_sys->i_our_duration = (int)GetDWBE(&header[20]); 803 1005 1006 p_sys->i_index_offset = GetDWBE(&header[28]); 1007 804 1008 i_flags = GetWBE(&header[38]); 805 1009 msg_Dbg( p_demux, " - flags=0x%x %s%s%s", … … 828 1032 msg_Dbg( p_demux, " - title=`%s'", psz ); 829 1033 p_sys->psz_title = psz; 1034 vlc_meta_Add( p_sys->p_meta, VLC_META_TITLE, psz ); 1035 free( psz ); 830 1036 i_skip -= i_len; 831 1037 } … … 842 1048 msg_Dbg( p_demux, " - author=`%s'", psz ); 843 1049 p_sys->psz_artist = psz; 1050 vlc_meta_Add( p_sys->p_meta, VLC_META_ARTIST, psz ); 1051 free( psz ); 844 1052 i_skip -= i_len; 845 1053 } … … 856 1064 msg_Dbg( p_demux, " - copyright=`%s'", psz ); 857 1065 p_sys->psz_copyright = psz; 1066 vlc_meta_Add( p_sys->p_meta, VLC_META_COPYRIGHT, psz ); 1067 free( psz ); 858 1068 i_skip -= i_len; 859 1069 } … … 870 1080 msg_Dbg( p_demux, " - comment=`%s'", psz ); 871 1081 p_sys->psz_description = psz; 1082 vlc_meta_Add( p_sys->p_meta, VLC_META_DESCRIPTION, psz ); 1083 free( psz ); 872 1084 i_skip -= i_len; 873 1085 } … … 959 1171 /* TODO read index if possible */ 960 1172 1173 if ( p_sys->i_index_offset > 0 ) 1174 { 1175 int64_t pos; 1176 pos = stream_Tell( p_demux->s ); 1177 ReadRealIndex( p_demux ); 1178 stream_Seek( p_demux->s, pos ); 1179 } 1180 961 1181 return VLC_SUCCESS; 962 1182 } … … 1015 1235 tk->i_subpackets = 0; 1016 1236 tk->p_subpackets = NULL; 1237 tk->p_subpackets_timecode = NULL; 1017 1238 tk->i_id = i_num; 1018 1239 tk->fmt = fmt; … … 1025 1246 else if( !strncmp( (char *)p_peek, ".ra\xfd", 4 ) ) 1026 1247 { 1027 int i_header_size, i_flavor, i_coded_frame_size, i_subpacket_h; 1028 int i_frame_size, i_subpacket_size; 1248 int i_header_size = 0; 1249 int i_flavor = 0; 1250 int i_coded_frame_size = 0; 1251 int i_subpacket_h = 0; 1252 int i_frame_size = 0; 1253 int i_subpacket_size = 0; 1029 1254 char p_genr[4]; 1030 1255 int i_version = GetWBE( &p_peek[4] ); /* [0..3] = '.','r','a',0xfd */ … … 1247 1472 tk->i_subpackets = 0; 1248 1473 tk->p_subpackets = NULL; 1474 tk->p_subpackets_timecode = NULL; 1249 1475 if( fmt.i_codec == VLC_FOURCC('c','o','o','k') 1250 1476 || fmt.i_codec == VLC_FOURCC('a','t','r','c') ) … … 1254 1480 tk->p_subpackets = 1255 1481 calloc( tk->i_subpackets, sizeof(block_t *) ); 1482 tk->p_subpackets_timecode = 1483 calloc( tk->i_subpackets , sizeof( int64_t ) ); 1256 1484 } 1257 1485 else if( fmt.i_codec == VLC_FOURCC('2','8','_','8') ) … … 1261 1489 tk->p_subpackets = 1262 1490 calloc( tk->i_subpackets, sizeof(block_t *) ); 1491 tk->p_subpackets_timecode = 1492 calloc( tk->i_subpackets , sizeof( int64_t ) ); 1263 1493 } 1264 1494
