diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/video_dec/libvdpau/vdpau_h264.c | 13 | ||||
-rw-r--r-- | src/video_dec/libvdpau/vdpau_mpeg12.c | 20 | ||||
-rw-r--r-- | src/video_out/video_out_vdpau.c | 40 |
3 files changed, 64 insertions, 9 deletions
diff --git a/src/video_dec/libvdpau/vdpau_h264.c b/src/video_dec/libvdpau/vdpau_h264.c index c9ef68ebf..2a6ef564c 100644 --- a/src/video_dec/libvdpau/vdpau_h264.c +++ b/src/video_dec/libvdpau/vdpau_h264.c @@ -1,6 +1,8 @@ /* * Copyright (C) 2008 Julian Scheel * + * kate: space-indent on; indent-width 2; mixedindent off; indent-mode cstyle; remove-trailing-space on; + * * This file is part of xine, a free video player. * * xine is free software; you can redistribute it and/or modify @@ -85,6 +87,8 @@ typedef struct vdpau_h264_decoder_s { int vdp_runtime_nr; + int reset; + } vdpau_h264_decoder_t; static void vdpau_h264_reset (video_decoder_t *this_gen); @@ -349,7 +353,8 @@ static int vdpau_decoder_init(video_decoder_t *this_gen) img = this->stream->video_out->get_frame (this->stream->video_out, this->width, this->height, this->ratio, - XINE_IMGFMT_VDPAU, VO_BOTH_FIELDS); + XINE_IMGFMT_VDPAU, VO_BOTH_FIELDS | this->reset); + this->reset = 0; img->duration = this->video_step; img->pts = this->completed_pic->pts; @@ -688,6 +693,7 @@ static void vdpau_h264_flush (video_decoder_t *this_gen) { dpb_set_output_picture(&(this->nal_parser->dpb), decoded_pic); } dpb_free_all(&this->nal_parser->dpb); + this->reset = VO_NEW_SEQUENCE_FLAG; } /* @@ -726,6 +732,8 @@ static void vdpau_h264_reset (video_decoder_t *this_gen) { } this->last_img = NULL; + + this->reset = VO_NEW_SEQUENCE_FLAG; } /* @@ -735,6 +743,7 @@ static void vdpau_h264_discontinuity (video_decoder_t *this_gen) { vdpau_h264_decoder_t *this = (vdpau_h264_decoder_t *) this_gen; dpb_clear_all_pts(&this->nal_parser->dpb); + this->reset = VO_NEW_SEQUENCE_FLAG; } /* @@ -804,6 +813,8 @@ static video_decoder_t *open_plugin (video_decoder_class_t *class_gen, xine_stre this->vdp_runtime_nr = runtime_nr; this->color_standard = VDP_COLOR_STANDARD_ITUR_BT_601; + this->reset = VO_NEW_SEQUENCE_FLAG; + this->nal_parser = init_parser(); (this->stream->video_out->open) (this->stream->video_out, this->stream); diff --git a/src/video_dec/libvdpau/vdpau_mpeg12.c b/src/video_dec/libvdpau/vdpau_mpeg12.c index 1b53b9cbe..a44f84cdd 100644 --- a/src/video_dec/libvdpau/vdpau_mpeg12.c +++ b/src/video_dec/libvdpau/vdpau_mpeg12.c @@ -152,6 +152,7 @@ typedef struct { bits_reader_t br; int vdp_runtime_nr; + int reset; } sequence_t; @@ -231,6 +232,7 @@ static void reset_sequence( sequence_t *sequence, int free_refs ) sequence->backward_ref->free( sequence->backward_ref ); sequence->backward_ref = NULL; sequence->top_field_first = 0; + sequence->reset = VO_NEW_SEQUENCE_FLAG; } @@ -701,7 +703,8 @@ static void decode_picture( vdpau_mpeg12_decoder_t *vd, uint8_t end_of_sequence } vo_frame_t *img = vd->stream->video_out->get_frame( vd->stream->video_out, seq->coded_width, seq->coded_height, - seq->ratio, XINE_IMGFMT_VDPAU, VO_BOTH_FIELDS|seq->chroma ); + seq->ratio, XINE_IMGFMT_VDPAU, VO_BOTH_FIELDS|seq->chroma|seq->reset ); + seq->reset = 0; vdpau_accel_t *accel = (vdpau_accel_t*)img->accel_data; if ( !seq->accel_vdpau ) seq->accel_vdpau = accel; @@ -721,16 +724,16 @@ static void decode_picture( vdpau_mpeg12_decoder_t *vd, uint8_t end_of_sequence #ifdef MAKE_DAT if ( nframes==0 ) { - fwrite( &seq->coded_width, 1, sizeof(seq->coded_width), outfile ); - fwrite( &seq->coded_height, 1, sizeof(seq->coded_height), outfile ); - fwrite( &seq->ratio, 1, sizeof(seq->ratio), outfile ); - fwrite( &seq->profile, 1, sizeof(seq->profile), outfile ); + fwrite( &seq->coded_width, 1, sizeof(seq->coded_width), outfile ); + fwrite( &seq->coded_height, 1, sizeof(seq->coded_height), outfile ); + fwrite( &seq->ratio, 1, sizeof(seq->ratio), outfile ); + fwrite( &seq->profile, 1, sizeof(seq->profile), outfile ); } if ( nframes++ < 25 ) { - fwrite( &pic->vdp_infos, 1, sizeof(pic->vdp_infos), outfile ); - fwrite( &pic->slices_pos, 1, sizeof(pic->slices_pos), outfile ); - fwrite( pic->slices, 1, pic->slices_pos, outfile ); + fwrite( &pic->vdp_infos, 1, sizeof(pic->vdp_infos), outfile ); + fwrite( &pic->slices_pos, 1, sizeof(pic->slices_pos), outfile ); + fwrite( pic->slices, 1, pic->slices_pos, outfile ); } #endif @@ -942,6 +945,7 @@ static video_decoder_t *open_plugin (video_decoder_class_t *class_gen, xine_stre this->sequence.vdp_runtime_nr = runtime_nr; free_sequence( &this->sequence ); this->sequence.ratio = 1; + this->sequence.reset = VO_NEW_SEQUENCE_FLAG; init_picture( &this->sequence.picture ); diff --git a/src/video_out/video_out_vdpau.c b/src/video_out/video_out_vdpau.c index 4a8758bdb..86eaa168e 100644 --- a/src/video_out/video_out_vdpau.c +++ b/src/video_out/video_out_vdpau.c @@ -261,6 +261,8 @@ typedef struct { int width, height, format, flags; double ratio; + int surface_cleared_nr; + vdpau_accel_t vdpau_accel_data; } vdpau_frame_t; @@ -357,6 +359,8 @@ typedef struct { int vdp_runtime_nr; int reinit_needed; + int surface_cleared_nr; + int allocated_surfaces; int zoom_x; int zoom_y; @@ -835,6 +839,8 @@ static vo_frame_t *vdpau_alloc_frame (vo_driver_t *this_gen) frame->vo_frame.dispose = vdpau_frame_dispose; frame->vo_frame.driver = this_gen; + frame->surface_cleared_nr = 0; + frame->vdpau_accel_data.vo_frame = &frame->vo_frame; frame->vdpau_accel_data.vdp_device = vdp_device; frame->vdpau_accel_data.surface = VDP_INVALID_HANDLE; @@ -979,6 +985,11 @@ static void vdpau_update_frame_format (vo_driver_t *this_gen, vo_frame_t *frame_ vdpau_driver_t *this = (vdpau_driver_t *) this_gen; vdpau_frame_t *frame = VDPAU_FRAME(frame_gen); + int clear = 0; + + if ( flags & VO_NEW_SEQUENCE_FLAG ) + ++this->surface_cleared_nr; + VdpChromaType chroma = (flags & VO_CHROMA_422) ? VDP_CHROMA_TYPE_422 : VDP_CHROMA_TYPE_420; vo_frame_t orig_frame_content; @@ -1035,6 +1046,7 @@ static void vdpau_update_frame_format (vo_driver_t *this_gen, vo_frame_t *frame_ if ( st!=VDP_STATUS_OK ) printf( "vo_vdpau: failed to create surface !! %s\n", vdp_get_error_string( st ) ); else { + clear = 1; frame->vdpau_accel_data.chroma = chroma; ++this->allocated_surfaces; frame->vo_frame.proc_duplicate_frame_data = vdpau_duplicate_frame_data; @@ -1050,6 +1062,32 @@ static void vdpau_update_frame_format (vo_driver_t *this_gen, vo_frame_t *frame_ vdpau_frame_field ((vo_frame_t *)frame, flags); } + if ( (format == XINE_IMGFMT_VDPAU) && (clear || (frame->surface_cleared_nr != this->surface_cleared_nr)) ) { + printf( "clear surface\n" ); + if ( frame->vdpau_accel_data.chroma == VDP_CHROMA_TYPE_422 ) { + uint8_t *cb = malloc( frame->width * frame->height * 2 ); + memset( cb, 127, frame->width * frame->height * 2 ); + uint32_t pitches[] = { frame->width }; + void* data[] = { cb }; + VdpStatus st = vdp_video_surface_putbits_ycbcr( frame->vdpau_accel_data.surface, VDP_YCBCR_FORMAT_YUYV, &data, pitches ); + if ( st!=VDP_STATUS_OK ) + printf( "vo_vdpau: failed to clear surface: %s\n", vdp_get_error_string( st ) ); + free( cb ); + } + else { + uint8_t *cb = malloc( frame->width * frame->height ); + memset( cb, 127, frame->width * frame->height ); + uint32_t pitches[] = { frame->width, frame->height, frame->height }; + void* data[] = { cb, cb, cb }; + VdpStatus st = vdp_video_surface_putbits_ycbcr( frame->vdpau_accel_data.surface, VDP_YCBCR_FORMAT_YV12, &data, pitches ); + if ( st!=VDP_STATUS_OK ) + printf( "vo_vdpau: failed to clear surface: %s\n", vdp_get_error_string( st ) ); + free( cb ); + } + if ( frame->surface_cleared_nr != this->surface_cleared_nr ) + frame->surface_cleared_nr = this->surface_cleared_nr; + } + frame->vdpau_accel_data.color_standard = VDP_COLOR_STANDARD_ITUR_BT_601; frame->ratio = ratio; frame->vo_frame.future_frame = NULL; @@ -2211,6 +2249,8 @@ static vo_driver_t *vdpau_open_plugin (video_driver_class_t *class_gen, const vo this->vo_driver.dispose = vdpau_dispose; this->vo_driver.redraw_needed = vdpau_redraw_needed; + this->surface_cleared_nr = 0; + this->video_mixer = VDP_INVALID_HANDLE; for ( i=0; i<NOUTPUTSURFACE; ++i ) this->output_surface[i] = VDP_INVALID_HANDLE; |