+
+ if( b_done )
+ {
+ return( 1 );
+ }
+
+ if( i_pos == -1 )
+ {
+ /* no valid index, we will parse directly the stream
+ * in case we fail we will disable all finished stream */
+ if( p_sys->i_movi_lastchunk_pos >= p_sys->i_movi_begin + 12 )
+ {
+ stream_Seek( p_input->s, p_sys->i_movi_lastchunk_pos );
+ if( AVI_PacketNext( p_input ) )
+ {
+ return( AVI_TrackStopFinishedStreams( p_input ) ? 0 : 1 );
+ }
+ }
+ else
+ {
+ stream_Seek( p_input->s, p_sys->i_movi_begin + 12 );
+ }
+
+ for( ;; )
+ {
+ avi_packet_t avi_pk;
+
+ if( AVI_PacketGetHeader( p_input, &avi_pk ) )
+ {
+ msg_Warn( p_input,
+ "cannot get packet header, track disabled" );
+ return( AVI_TrackStopFinishedStreams( p_input ) ? 0 : 1 );
+ }
+ if( avi_pk.i_stream >= p_sys->i_track ||
+ ( avi_pk.i_cat != AUDIO_ES && avi_pk.i_cat != VIDEO_ES ) )
+ {
+ if( AVI_PacketNext( p_input ) )
+ {
+ msg_Warn( p_input,
+ "cannot skip packet, track disabled" );
+ return( AVI_TrackStopFinishedStreams( p_input ) ? 0 : 1 );
+ }
+ continue;
+ }
+ else
+ {
+ /* add this chunk to the index */
+ avi_entry_t index;
+
+ index.i_id = avi_pk.i_fourcc;
+ index.i_flags =
+ AVI_GetKeyFlag(p_sys->track[avi_pk.i_stream]->i_codec,
+ avi_pk.i_peek);
+ index.i_pos = avi_pk.i_pos;
+ index.i_length = avi_pk.i_size;
+ AVI_IndexAddEntry( p_sys, avi_pk.i_stream, &index );
+
+ i_track = avi_pk.i_stream;
+ tk = p_sys->track[i_track];
+ /* do we will read this data ? */
+ if( AVI_GetDPTS( tk, toread[i_track].i_toread ) > -25*1000 )
+ {
+ break;
+ }
+ else
+ {
+ if( AVI_PacketNext( p_input ) )
+ {
+ msg_Warn( p_input,
+ "cannot skip packet, track disabled" );
+ return( AVI_TrackStopFinishedStreams( p_input ) ? 0 : 1 );
+ }
+ }
+ }
+ }
+
+ }
+ else
+ {
+ stream_Seek( p_input->s, i_pos );
+ }
+
+ /* Set the track to use */
+ tk = p_sys->track[i_track];
+
+ /* read thoses data */
+ if( tk->i_samplesize )
+ {
+ unsigned int i_toread;
+
+ if( ( i_toread = toread[i_track].i_toread ) <= 0 )
+ {
+ if( tk->i_samplesize > 1 )
+ {
+ i_toread = tk->i_samplesize;
+ }
+ else
+ {
+ i_toread = __MAX( AVI_PTSToByte( tk, 20 * 1000 ), 100 );
+ }
+ }
+ i_size = __MIN( tk->p_index[tk->i_idxposc].i_length -
+ tk->i_idxposb,
+ i_toread );
+ }
+ else
+ {
+ i_size = tk->p_index[tk->i_idxposc].i_length;
+ }
+
+ if( tk->i_idxposb == 0 )
+ {
+ i_size += 8; /* need to read and skip header */
+ }
+
+ if( ( p_frame = stream_Block( p_input->s, __EVEN( i_size ) ) )==NULL )
+ {
+ msg_Warn( p_input, "failled reading data" );
+ tk->b_activated = VLC_FALSE;
+ toread[i_track].b_ok = VLC_FALSE;
+ continue;
+ }
+ if( i_size % 2 ) /* read was padded on word boundary */
+ {
+ p_frame->i_buffer--;
+ }
+ /* skip header */
+ if( tk->i_idxposb == 0 )
+ {
+ p_frame->p_buffer += 8;
+ p_frame->i_buffer -= 8;
+ }
+ p_frame->i_pts = AVI_GetPTS( tk );
+ if( tk->p_index[tk->i_idxposc].i_flags&AVIIF_KEYFRAME )
+ {
+ p_frame->i_flags = BLOCK_FLAG_TYPE_I;
+ }
+ else
+ {
+ p_frame->i_flags = BLOCK_FLAG_TYPE_PB;
+ }
+
+ /* read data */
+ if( tk->i_samplesize )
+ {
+ if( tk->i_idxposb == 0 )
+ {
+ i_size -= 8;
+ }
+ toread[i_track].i_toread -= i_size;
+ tk->i_idxposb += i_size;
+ if( tk->i_idxposb >=
+ tk->p_index[tk->i_idxposc].i_length )
+ {
+ tk->i_idxposb = 0;
+ tk->i_idxposc++;
+ }
+ }
+ else
+ {
+ int i_length = tk->p_index[tk->i_idxposc].i_length;
+
+ tk->i_idxposc++;
+ if( tk->i_cat == AUDIO_ES )
+ {
+ tk->i_blockno += tk->i_blocksize > 0 ? ( i_length + tk->i_blocksize - 1 ) / tk->i_blocksize : 1;
+ }
+ toread[i_track].i_toread--;
+ }
+
+ if( tk->i_idxposc < tk->i_idxnb)
+ {
+ toread[i_track].i_posf =
+ tk->p_index[tk->i_idxposc].i_pos;
+ if( tk->i_idxposb > 0 )
+ {
+ toread[i_track].i_posf += 8 + tk->i_idxposb;
+ }
+
+ }
+ else
+ {
+ toread[i_track].i_posf = -1;
+ }
+
+ b_stream = VLC_TRUE; /* at least one read succeed */
+
+ p_frame->i_pts =
+ input_ClockGetTS( p_input,
+ p_input->stream.p_selected_program,
+ p_frame->i_pts * 9/100);
+
+ if( tk->i_cat != VIDEO_ES )
+ p_frame->i_dts = p_frame->i_pts;
+ else
+ {
+ p_frame->i_dts = p_frame->i_pts;
+ p_frame->i_pts = 0;
+ }
+
+ //p_pes->i_rate = p_input->stream.control.i_rate;
+ es_out_Send( p_input->p_es_out, tk->p_es, p_frame );