Ejemplo n.º 1
0
static void fill_cache( cache_hnd_t *h, int frame )
{
    /* shift frames out of the cache as the frame request is beyond the filled cache */
    int shift = frame - LAST_FRAME;
    /* no frames to shift or no frames left to read */
    if( shift <= 0 || h->eof )
        return;
    /* the next frames to read are either
     * A) starting at the end of the current cache, or
     * B) starting at a new frame that has the end of the cache at the desired frame
     * and proceeding to fill the entire cache */
    int cur_frame = X264_MAX( h->first_frame + h->cur_size, frame - h->max_size + 1 );
    /* the new starting point is either
     * A) the current one shifted the number of frames entering/leaving the cache, or
     * B) at a new frame that has the end of the cache at the desired frame. */
    h->first_frame = X264_MIN( h->first_frame + shift, cur_frame );
    h->cur_size = X264_MAX( h->cur_size - shift, 0 );
    while( h->cur_size < h->max_size )
    {
        cli_pic_t temp;
        /* the old front frame is going to shift off, overwrite it with the new frame */
        cli_pic_t *cache = h->cache[0];
        if( h->prev_filter.get_frame( h->prev_hnd, &temp, cur_frame ) ||
            x264_cli_pic_copy( cache, &temp ) ||
            h->prev_filter.release_frame( h->prev_hnd, &temp, cur_frame ) )
        {
            h->eof = cur_frame;
            return;
        }
        /* the read was successful, shift the frame off the front to the end */
        x264_frame_push( (void*)h->cache, x264_frame_shift( (void*)h->cache ) );
        cur_frame++;
        h->cur_size++;
    }
}
Ejemplo n.º 2
0
static int get_frame( hnd_t handle, cli_pic_t *output, int frame )
{
    fix_vfr_pts_hnd_t *h = handle;
    /* if we want the holder picture and it errored, return the error. */
    if( frame == h->holder_frame )
    {
        if( h->holder_ret )
            return h->holder_ret;
    }
    else
    {
        /* if we have a holder frame and we don't want it, release the frame */
        if( h->holder_frame > 0 && h->holder_frame < frame && h->prev_filter.release_frame( h->prev_hnd, &h->holder, h->holder_frame ) )
            return -1;
        h->holder_frame = -1;
        if( h->prev_filter.get_frame( h->prev_hnd, &h->holder, frame ) )
            return -1;
    }

    /* if the frame's duration is not set already, read the next frame to set it. */
    if( !h->holder.duration )
    {
        /* allocate a buffer picture if we didn't already */
        if( !h->buffer_allocated )
        {
            if( x264_cli_pic_alloc( &h->buffer, h->holder.img.csp, h->holder.img.width, h->holder.img.height ) )
                return -1;
            h->buffer_allocated = 1;
        }
        h->holder_frame = frame+1;
        /* copy the current frame to the buffer, release it, and then read in the next frame to the placeholder */
        if( x264_cli_pic_copy( &h->buffer, &h->holder ) || h->prev_filter.release_frame( h->prev_hnd, &h->holder, frame ) )
            return -1;
        h->holder_ret = h->prev_filter.get_frame( h->prev_hnd, &h->holder, h->holder_frame );
        /* suppress non-monotonic pts warnings by setting the duration to be at least 1 */
        if( !h->holder_ret )
            h->last_duration = X264_MAX( h->holder.pts - h->buffer.pts, 1 );
        h->buffer.duration = h->last_duration;
        *output = h->buffer;
    }
    else
        *output = h->holder;

    output->pts = h->pts;
    h->pts += output->duration;

    return 0;
}