diff options
author | Miguel Freitas <miguelfreitas@users.sourceforge.net> | 2002-03-25 01:02:51 +0000 |
---|---|---|
committer | Miguel Freitas <miguelfreitas@users.sourceforge.net> | 2002-03-25 01:02:51 +0000 |
commit | 8f1bca49ef90081e67ce29bb01b2a8d9fafb7d07 (patch) | |
tree | 0c818f1283e6e3e358fd2562852147f210e58940 | |
parent | fceae5849b57feab320e768696564b3b93bcddc7 (diff) | |
download | xine-lib-8f1bca49ef90081e67ce29bb01b2a8d9fafb7d07.tar.gz xine-lib-8f1bca49ef90081e67ce29bb01b2a8d9fafb7d07.tar.bz2 |
- fix frames leaking
- big video_out locking cleanup: no more decoder_locked, display_locked,
driver_locked madness!
CVS patchset: 1630
CVS date: 2002/03/25 01:02:51
-rw-r--r-- | src/libmpeg2/decode.c | 10 | ||||
-rw-r--r-- | src/xine-engine/video_out.c | 136 | ||||
-rw-r--r-- | src/xine-engine/video_out.h | 7 |
3 files changed, 29 insertions, 124 deletions
diff --git a/src/libmpeg2/decode.c b/src/libmpeg2/decode.c index b78b178d5..866a7b1b0 100644 --- a/src/libmpeg2/decode.c +++ b/src/libmpeg2/decode.c @@ -510,7 +510,6 @@ void mpeg2_flush (mpeg2dec_t * mpeg2dec) { img = picture->backward_reference_frame->instance->duplicate_frame(picture->backward_reference_frame->instance, picture->backward_reference_frame); img->pts = 0; - img->scr = 0; img->bad_frame = 0; img->drawn = 1; @@ -537,21 +536,12 @@ void mpeg2_close (mpeg2dec_t * mpeg2dec) leak, and we only have about 15 of them. */ if (picture->forward_reference_frame) { - /* - printf ("libmpeg2: blasting out forward reference frame on close\n"); -// picture->forward_reference_frame->PTS = 0; - picture->forward_reference_frame->bad_frame = 0; - get_frame_duration(mpeg2dec, picture->forward_reference_frame); - picture->forward_reference_frame->draw (picture->forward_reference_frame); - */ - picture->forward_reference_frame->displayed (picture->forward_reference_frame); picture->forward_reference_frame->free (picture->forward_reference_frame); } if (picture->throwaway_frame) { printf ("libmpeg2: blasting out throwaway frame on close\n"); picture->throwaway_frame->pts = 0; - picture->throwaway_frame->scr = 0; get_frame_duration(mpeg2dec, picture->throwaway_frame); picture->throwaway_frame->draw (picture->throwaway_frame); picture->throwaway_frame->free (picture->throwaway_frame); diff --git a/src/xine-engine/video_out.c b/src/xine-engine/video_out.c index 002ce4982..3127f0045 100644 --- a/src/xine-engine/video_out.c +++ b/src/xine-engine/video_out.c @@ -17,7 +17,7 @@ * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA * - * $Id: video_out.c,v 1.86 2002/03/22 17:38:21 miguelfreitas Exp $ + * $Id: video_out.c,v 1.87 2002/03/25 01:02:51 miguelfreitas Exp $ * * frame allocation / queuing / scheduling / output functions */ @@ -167,16 +167,23 @@ static vo_frame_t *vo_remove_from_img_buf_queue (img_buf_fifo_t *queue) { } /* - * function called by video output driver + * functions to maintain lock_counter */ +static void vo_frame_inc_lock (vo_frame_t *img) { + + pthread_mutex_lock (&img->mutex); -static void vo_frame_displayed (vo_frame_t *img) { + img->lock_counter++; - pthread_mutex_lock (&img->mutex); + pthread_mutex_unlock (&img->mutex); +} - img->driver_locked = 0; +static void vo_frame_dec_lock (vo_frame_t *img) { + + pthread_mutex_lock (&img->mutex); - if (!img->decoder_locked) { + img->lock_counter--; + if (!img->lock_counter) { vos_t *this = (vos_t *) img->instance; vo_append_to_img_buf_queue (this->free_img_buf_queue, img); } @@ -184,6 +191,7 @@ static void vo_frame_displayed (vo_frame_t *img) { pthread_mutex_unlock (&img->mutex); } + /* * * functions called by video decoder: @@ -215,9 +223,7 @@ static vo_frame_t *vo_get_frame (vo_instance_t *this_gen, #endif pthread_mutex_lock (&img->mutex); - img->display_locked = 0; - img->decoder_locked = 1; - img->driver_locked = 0; + img->lock_counter = 1; img->width = width; img->height = height; img->ratio = ratio; @@ -270,7 +276,7 @@ static int vo_frame_draw (vo_frame_t *img) { diff, cur_vpts, frames_to_skip); #endif - if (img->display_locked) { + if (img->lock_counter > 1) { printf ("video_out: ALERT! frame is already locked for displaying\n"); return frames_to_skip; } @@ -286,10 +292,7 @@ static int vo_frame_draw (vo_frame_t *img) { this->last_frame = img; - pthread_mutex_lock (&img->mutex); - img->display_locked = 1; - pthread_mutex_unlock (&img->mutex); - + vo_frame_inc_lock( img ); vo_append_to_img_buf_queue (this->display_img_buf_queue, img); } else { @@ -298,12 +301,6 @@ static int vo_frame_draw (vo_frame_t *img) { #endif this->num_frames_skipped++; - - pthread_mutex_lock (&img->mutex); - img->display_locked = 0; - pthread_mutex_unlock (&img->mutex); - - vo_frame_displayed (img); } /* @@ -324,21 +321,6 @@ static int vo_frame_draw (vo_frame_t *img) { return frames_to_skip; } -static void vo_frame_free (vo_frame_t *img) { - - pthread_mutex_lock (&img->mutex); - img->decoder_locked = 0; - - if (!img->display_locked && !img->driver_locked ) { - vos_t *this = (vos_t *) img->instance; - vo_append_to_img_buf_queue (this->free_img_buf_queue, img); - } - - pthread_mutex_unlock (&img->mutex); -} - - - /* * * video out loop related functions @@ -380,21 +362,13 @@ static void expire_frames (vos_t *this, int64_t cur_vpts) { if (!this->display_img_buf_queue->first) { if (this->img_backup) { - pthread_mutex_lock (&this->img_backup->mutex); #ifdef LOG printf("video_out: overwriting frame backup\n"); #endif - this->img_backup->display_locked = 0; - if (!img->decoder_locked) - vo_append_to_img_buf_queue (this->free_img_buf_queue, - this->img_backup); - - pthread_mutex_unlock (&this->img_backup->mutex); + vo_frame_dec_lock( this->img_backup ); } printf("video_out: possible still frame (old)\n"); - /* we must not clear display_locked from img_backup. - without it decoder may try to free our backup. */ this->img_backup = img; this->backup_is_logo = 0; @@ -402,13 +376,7 @@ static void expire_frames (vos_t *this, int64_t cur_vpts) { this allow slower systems to recover. */ this->redraw_needed = 4; } else { - pthread_mutex_lock (&img->mutex); - - img->display_locked = 0; - if (!img->decoder_locked) - vo_append_to_img_buf_queue (this->free_img_buf_queue, img); - - pthread_mutex_unlock (&img->mutex); + vo_frame_dec_lock( img ); } img = this->display_img_buf_queue->first; @@ -441,16 +409,10 @@ static vo_frame_t *get_next_frame (vos_t *this, int64_t cur_vpts) { if (!this->video_opened && (!this->img_backup || !this->backup_is_logo)) { if (this->img_backup) { - pthread_mutex_lock (&this->img_backup->mutex); #ifdef LOG printf("video_out: overwriting frame backup\n"); #endif - this->img_backup->display_locked = 0; - if (!this->img_backup->decoder_locked) - vo_append_to_img_buf_queue (this->free_img_buf_queue, - this->img_backup); - - pthread_mutex_unlock (&this->img_backup->mutex); + vo_frame_dec_lock( this->img_backup ); } printf("video_out: copying logo image\n"); @@ -458,9 +420,6 @@ static vo_frame_t *get_next_frame (vos_t *this, int64_t cur_vpts) { this->img_backup = vo_get_frame (&this->vo, this->logo_w, this->logo_h, 42, IMGFMT_YUY2, VO_BOTH_FIELDS); - this->img_backup->decoder_locked = 0; - this->img_backup->display_locked = 1; - this->img_backup->driver_locked = 0; this->img_backup->duration = 3000; xine_fast_memcpy(this->img_backup->base[0], this->logo_yuy2, @@ -479,7 +438,6 @@ static vo_frame_t *get_next_frame (vos_t *this, int64_t cur_vpts) { /* keep playing still frames */ img = this->vo.duplicate_frame (&this->vo, this->img_backup ); - img->display_locked = 1; do { /* always restore duration so drift correction shouldn't cause any trouble */ @@ -518,14 +476,8 @@ static vo_frame_t *get_next_frame (vos_t *this, int64_t cur_vpts) { } if (this->img_backup) { - pthread_mutex_lock (&this->img_backup->mutex); printf("video_out: freeing frame backup\n"); - - this->img_backup->display_locked = 0; - if( !this->img_backup->decoder_locked ) - vo_append_to_img_buf_queue (this->free_img_buf_queue, - this->img_backup); - pthread_mutex_unlock (&this->img_backup->mutex); + vo_frame_dec_lock( this->img_backup ); this->img_backup = NULL; } @@ -561,22 +513,6 @@ static void overlay_and_display_frame (vos_t *this, img->vpts); #endif - pthread_mutex_lock (&img->mutex); - img->driver_locked = 1; - -#ifdef LOG - if (!img->display_locked) - printf ("video_out: ALERT! frame was not locked for display queue\n"); -#endif - - img->display_locked = 0; - pthread_mutex_unlock (&img->mutex); - -#ifdef LOG - printf ("video_out: passing to video driver image with pts = %lld\n", - img->vpts); -#endif - if (this->overlay_source) { /* This is the only way for the overlay manager to get pts values * for flushing its buffers. So don't remove it! */ @@ -713,25 +649,14 @@ static void *video_out_loop (void *this_gen) { while (img) { img = vo_remove_from_img_buf_queue (this->display_img_buf_queue); - pthread_mutex_lock (&img->mutex); - - img->display_locked = 0; - if (!img->decoder_locked) - vo_append_to_img_buf_queue (this->free_img_buf_queue, img); - - pthread_mutex_unlock (&img->mutex); + vo_frame_dec_lock( img ); img = this->display_img_buf_queue->first; } if (this->img_backup) { - pthread_mutex_lock (&this->img_backup->mutex); - - this->img_backup->display_locked = 0; - if (!this->img_backup->decoder_locked) - vo_append_to_img_buf_queue (this->free_img_buf_queue, this->img_backup); - - pthread_mutex_unlock (&this->img_backup->mutex); + vo_frame_dec_lock( this->img_backup ); + this->img_backup = NULL; } pthread_exit(NULL); @@ -750,12 +675,6 @@ static vo_frame_t * vo_duplicate_frame( vo_instance_t *this_gen, vo_frame_t *img dupl = vo_get_frame (this_gen, img->width, img->height, img->ratio, img->format, VO_BOTH_FIELDS ); - - pthread_mutex_lock (&dupl->mutex); - - dupl->display_locked = 0; - dupl->decoder_locked = 0; - dupl->driver_locked = 0; image_size = img->width * img->height; @@ -776,7 +695,6 @@ static vo_frame_t * vo_duplicate_frame( vo_instance_t *this_gen, vo_frame_t *img dupl->bad_frame = 0; dupl->pts = 0; dupl->vpts = 0; - dupl->scr = 0; dupl->duration = img->duration; /* Support copy; Dangerous, since some decoders may use a source that's @@ -812,8 +730,6 @@ static vo_frame_t * vo_duplicate_frame( vo_instance_t *this_gen, vo_frame_t *img } } - pthread_mutex_unlock (&dupl->mutex); - return dupl; } @@ -968,8 +884,8 @@ vo_instance_t *vo_new_instance (vo_driver_t *driver, xine_t *xine) { img->id = i; img->instance = &this->vo; - img->free = vo_frame_free ; - img->displayed = vo_frame_displayed; + img->free = vo_frame_dec_lock; + img->displayed = vo_frame_dec_lock; img->draw = vo_frame_draw; vo_append_to_img_buf_queue (this->free_img_buf_queue, diff --git a/src/xine-engine/video_out.h b/src/xine-engine/video_out.h index 58fc2c397..bdfb51b08 100644 --- a/src/xine-engine/video_out.h +++ b/src/xine-engine/video_out.h @@ -17,7 +17,7 @@ * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA * - * $Id: video_out.h,v 1.51 2002/03/21 16:21:02 miguelfreitas Exp $ + * $Id: video_out.h,v 1.52 2002/03/25 01:02:51 miguelfreitas Exp $ * * * xine version of video_out.h @@ -75,7 +75,6 @@ struct vo_frame_s { int64_t pts; /* presentation time stamp (1/90000 sec) */ int64_t vpts; /* virtual pts, generated by metronom */ - int64_t scr; /* system clock reference (discont. detection) */ int bad_frame; /* e.g. frame skipped or based on skipped frame */ int duration; /* frame length in time, in 1/90000 sec */ @@ -98,8 +97,8 @@ struct vo_frame_s { int drawn; /* used by decoder, frame has already been drawn */ - int display_locked, decoder_locked, driver_locked; - pthread_mutex_t mutex; /* so the various locks will be serialized */ + int lock_counter; + pthread_mutex_t mutex; /* protect access to lock_count */ /* "backward" references to where this frame originates from */ vo_instance_t *instance; |