⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 avi.c

📁 uclinux 下的vlc播放器源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
            }            else            {                stream_Seek( p_demux->s, p_sys->i_movi_begin + 12 );            }            for( ;; )            {                avi_packet_t avi_pk;                if( AVI_PacketGetHeader( p_demux, &avi_pk ) )                {                    msg_Warn( p_demux,                             "cannot get packet header, track disabled" );                    return( AVI_TrackStopFinishedStreams( p_demux ) ? 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_demux ) )                    {                        msg_Warn( p_demux,                                  "cannot skip packet, track disabled" );                        return( AVI_TrackStopFinishedStreams( p_demux ) ? 0 : 1 );                    }                    /* Prevents from eating all the CPU with broken files.                     * This value should be low enough so that it doesn't                     * affect the reading speed too much. */                    if( !(++i_loop_count % 1024) )                    {                        if( p_demux->b_die ) return -1;                        msleep( 10000 );                        if( !(i_loop_count % (1024 * 10)) )                            msg_Warn( p_demux,                                      "don't seem to find any data..." );                    }                    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_demux ) )                        {                            msg_Warn( p_demux,                                      "cannot skip packet, track disabled" );                            return( AVI_TrackStopFinishedStreams( p_demux ) ? 0 : 1 );                        }                    }                }            }        }        else        {            stream_Seek( p_demux->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 = AVI_PTSToByte( tk, 20 * 1000 );                    i_toread = __MAX( i_toread, 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_demux->s, __EVEN( i_size ) ) )==NULL )        {            msg_Warn( p_demux, "failed 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 ) + 1;        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 */        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_demux->stream.control.i_rate;        es_out_Send( p_demux->out, tk->p_es, p_frame );    }}/***************************************************************************** * Demux_UnSeekable: reads and demuxes data packets for unseekable file ***************************************************************************** * Returns -1 in case of error, 0 in case of EOF, 1 otherwise *****************************************************************************/static int Demux_UnSeekable( demux_t *p_demux ){    demux_sys_t     *p_sys = p_demux->p_sys;    avi_track_t *p_stream_master = NULL;    unsigned int i_stream;    unsigned int i_packet;    es_out_Control( p_demux->out, ES_OUT_SET_PCR, p_sys->i_time + 1 );    /* *** find master stream for data packet skipping algo *** */    /* *** -> first video, if any, or first audio ES *** */    for( i_stream = 0; i_stream < p_sys->i_track; i_stream++ )    {        avi_track_t *tk = p_sys->track[i_stream];        vlc_bool_t  b;        es_out_Control( p_demux->out, ES_OUT_GET_ES_STATE, tk->p_es, &b );        if( b && tk->i_cat == VIDEO_ES )        {            p_stream_master = tk;        }        else if( b )        {            p_stream_master = tk;        }    }    if( !p_stream_master )    {        msg_Warn( p_demux, "no more stream selected" );        return( 0 );    }    p_sys->i_time = AVI_GetPTS( p_stream_master );    for( i_packet = 0; i_packet < 10; i_packet++)    {#define p_stream    p_sys->track[avi_pk.i_stream]        avi_packet_t    avi_pk;        if( AVI_PacketGetHeader( p_demux, &avi_pk ) )        {            return( 0 );        }        if( avi_pk.i_stream >= p_sys->i_track ||            ( avi_pk.i_cat != AUDIO_ES && avi_pk.i_cat != VIDEO_ES ) )        {            /* we haven't found an audio or video packet:             *  - we have seek, found first next packet             *  - others packets could be found, skip them             */            switch( avi_pk.i_fourcc )            {                case AVIFOURCC_JUNK:                case AVIFOURCC_LIST:                case AVIFOURCC_RIFF:                    return( !AVI_PacketNext( p_demux ) ? 1 : 0 );                case AVIFOURCC_idx1:                    if( p_sys->b_odml )                    {                        return( !AVI_PacketNext( p_demux ) ? 1 : 0 );                    }                    return( 0 );    /* eof */                default:                    msg_Warn( p_demux,                              "seems to have lost position, resync" );                    if( AVI_PacketSearch( p_demux ) )                    {                        msg_Err( p_demux, "resync failed" );                        return( -1 );                    }            }        }        else        {            /* check for time */            if( __ABS( AVI_GetPTS( p_stream ) -                        AVI_GetPTS( p_stream_master ) )< 600*1000 )            {                /* load it and send to decoder */                block_t *p_frame;                if( AVI_PacketRead( p_demux, &avi_pk, &p_frame ) || p_frame == NULL )                {                    return( -1 );                }                p_frame->i_pts = AVI_GetPTS( p_stream ) + 1;                if( avi_pk.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_demux->stream.control.i_rate;                es_out_Send( p_demux->out, p_stream->p_es, p_frame );            }            else            {                if( AVI_PacketNext( p_demux ) )                {                    return( 0 );                }            }            /* *** update stream time position *** */            if( p_stream->i_samplesize )            {                p_stream->i_idxposb += avi_pk.i_size;            }            else            {                if( p_stream->i_cat == AUDIO_ES )                {                    p_stream->i_blockno += p_stream->i_blocksize > 0 ? ( avi_pk.i_size + p_stream->i_blocksize - 1 ) / p_stream->i_blocksize : 1;                }                p_stream->i_idxposc++;            }        }#undef p_stream    }    return( 1 );}/***************************************************************************** * Seek: goto to i_date or i_percent *****************************************************************************/static int Seek( demux_t *p_demux, mtime_t i_date, int i_percent ){    demux_sys_t *p_sys = p_demux->p_sys;    unsigned int i_stream;    msg_Dbg( p_demux, "seek requested: "I64Fd" secondes %d%%",             i_date / 1000000, i_percent );    if( p_sys->b_seekable )    {        if( !p_sys->i_length )        {            avi_track_t *p_stream;            int64_t i_pos;            /* use i_percent to create a true i_date */            msg_Warn( p_demux, "seeking without index at %d%%"                      " only works for interleaved files", i_percent );            if( i_percent >= 100 )            {                msg_Warn( p_demux, "cannot seek so far !" );                return VLC_EGENERIC;            }            i_percent = __MAX( i_percent, 0 );            /* try to find chunk that is at i_percent or the file */            i_pos = __MAX( i_percent * stream_Size( p_demux->s ) / 100,                           p_sys->i_movi_begin );            /* search first selected stream */            for( i_stream = 0, p_stream = NULL;                        i_stream < p_sys->i_track; i_stream++ )            {                p_stream = p_sys->track[i_stream];                if( p_stream->b_activated )                {                    break;                }            }            if( !p_stream || !p_stream->b_activated )            {                msg_Warn( p_demux, "cannot find any selected stream" );                return VLC_EGENERIC;            }            /* be sure that the index exist */            if( AVI_StreamChunkSet( p_demux, i_stream, 0 ) )            {                msg_Warn( p_demux, "cannot seek" );                return VLC_EGENERIC;            }            while( i_pos >= p_stream->p_index[p_stream->i_idxposc].i_pos +               p_stream->p_index[p_stream->i_idxposc].i_length + 8 )            {                /* search after i_idxposc */                if( AVI_StreamChunkSet( p_demux,                                        i_stream, p_stream->i_idxposc + 1 ) )                {                    msg_Warn( p_demux, "cannot seek" );                    return VLC_EGENERIC;                }            }            i_date = AVI_GetPTS( p_stream );            /* TODO better support for i_samplesize != 0 */            msg_Dbg( p_demux, "estimate date "I64Fd, i_date );        }#define p_stream    p_sys->track[i_stream]        p_sys->i_time = 0;        /* seek for chunk based streams */        for( i_stream = 0; i_stream < p_sys->i_track; i_stream++ )        {            if( p_stream->b_activated && !p_stream->i_samplesize )/*            if( p_stream->b_activated ) */            {                AVI_TrackSeek( p_demux, i_stream, i_date );

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -