summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorReinhard Nißl <rnissl@gmx.de>2007-07-26 23:35:19 +0200
committerReinhard Nißl <rnissl@gmx.de>2007-07-26 23:35:19 +0200
commit944fc07d1bfd33010a1a61e923d53b884f5a6359 (patch)
tree51bc07468824c82079e5d6e716b6c329d3137c5b
parent1028e44b958a7c1533e237c0f076d5adf9598b94 (diff)
downloadxine-lib-944fc07d1bfd33010a1a61e923d53b884f5a6359.tar.gz
xine-lib-944fc07d1bfd33010a1a61e923d53b884f5a6359.tar.bz2
propagate frame changes in xxmc_do_update_frame() to intercepted frames
XXMC doesn't work well with the way how intercepting frames is implemented for postprocessing as xxmc_do_update_frame() may change the native frame's format after the frame has been intercepted. As intercepting XXMC frames didn't work in the past, we can imply that postplugins which will support XXMC do know about this special behaviour. So the idea is to detect any changes on the native frame and propagate these changes to all intercepted frames. At the same time, we check that all intercepted frames still share the same data (which we are about to change) with the native frame and abort otherwise. --HG-- extra : transplant_source : c%D5%13%21jF%1E%D4%AB%D7%DB%22%27%0A%CB%0E%7F%CF%84v
-rw-r--r--src/video_out/video_out_xxmc.c34
1 files changed, 34 insertions, 0 deletions
diff --git a/src/video_out/video_out_xxmc.c b/src/video_out/video_out_xxmc.c
index 748d207ab..1f093070d 100644
--- a/src/video_out/video_out_xxmc.c
+++ b/src/video_out/video_out_xxmc.c
@@ -1230,6 +1230,13 @@ static void xxmc_do_update_frame(vo_driver_t *this_gen,
if ( XINE_IMGFMT_XXMC == format ) {
xine_xxmc_t *xxmc = &frame->xxmc_data;
+ vo_frame_t orig_frame_content;
+
+ if (frame_gen != &frame->vo_frame) {
+ /* this is an intercepted frame, so we need to detect and propagate any
+ * changes on the original vo_frame to all the intercepted frames */
+ xine_fast_memcpy(&orig_frame_content, &frame->vo_frame, sizeof (vo_frame_t));
+ }
xvmc_context_writer_lock( &this->xvmc_lock);
if (xxmc_accel_update(this, this->last_accel_request, xxmc->acceleration) ||
@@ -1259,6 +1266,33 @@ static void xxmc_do_update_frame(vo_driver_t *this_gen,
xvmc_context_writer_unlock( &this->xvmc_lock);
+ if (frame_gen != &frame->vo_frame) {
+ /* this is an intercepted frame, so we need to detect and propagate any
+ * changes on the original vo_frame to all the intercepted frames */
+ unsigned char *p0 = (unsigned char *)&orig_frame_content;
+ unsigned char *p1 = (unsigned char *)&frame->vo_frame;
+ int i;
+ for (i = 0; i < sizeof (vo_frame_t); i++) {
+ if (*p0 != *p1) {
+ /* propagate the change */
+ vo_frame_t *f = frame_gen;
+ while (f->next) {
+ /* serveral restrictions apply when intercepting XXMC frames. So let's check
+ * the intercepted frames before modifing them and fail otherwise. */
+ unsigned char *p = (unsigned char *)f + i;
+ if (*p != *p0) {
+ xprintf(this->xine, XINE_VERBOSITY_DEBUG, "xxmc_do_update_frame: a post plugin violates the restrictions on intercepting XXMC frames\n");
+ _x_abort();
+ }
+
+ *p = *p1;
+ f = f->next;
+ }
+ }
+ p0++;
+ p1++;
+ }
+ }
} else {
/* switch back to an unaccelerated context */
if (this->last_accel_request != 0xFFFFFFFF) {