Fixed corruption when copying to the same surface (with the help of
Tony Lambregts and Lionel Ulmer).
diff --git a/dlls/ddraw/dsurface/dib.c b/dlls/ddraw/dsurface/dib.c
index 9298ebc..7a27f79 100644
--- a/dlls/ddraw/dsurface/dib.c
+++ b/dlls/ddraw/dsurface/dib.c
@@ -482,11 +482,39 @@
/* No stretching in either direction. This needs to be as
* fast as possible */
sbuf = sbase;
- for (y = 0; y < dstheight; y++) {
- memcpy(dbuf, sbuf, width);
- sbuf += sdesc.u1.lPitch;
- dbuf += ddesc.u1.lPitch;
- }
+
+ /* check for overlapping surfaces */
+ if (src != iface || xdst.top < xsrc.top ||
+ xdst.right <= xsrc.left || xsrc.right <= xdst.left)
+ {
+ /* no overlap, or dst above src, so copy from top downwards */
+ for (y = 0; y < dstheight; y++)
+ {
+ memcpy(dbuf, sbuf, width);
+ sbuf += sdesc.u1.lPitch;
+ dbuf += ddesc.u1.lPitch;
+ }
+ }
+ else if (xdst.top > xsrc.top) /* copy from bottom upwards */
+ {
+ sbuf += (sdesc.u1.lPitch*dstheight);
+ dbuf += (ddesc.u1.lPitch*dstheight);
+ for (y = 0; y < dstheight; y++)
+ {
+ sbuf -= sdesc.u1.lPitch;
+ dbuf -= ddesc.u1.lPitch;
+ memcpy(dbuf, sbuf, width);
+ }
+ }
+ else /* src and dst overlapping on the same line, use memmove */
+ {
+ for (y = 0; y < dstheight; y++)
+ {
+ memmove(dbuf, sbuf, width);
+ sbuf += sdesc.u1.lPitch;
+ dbuf += ddesc.u1.lPitch;
+ }
+ }
} else {
/* Stretching in Y direction only */
for (y = sy = 0; y < dstheight; y++, sy += yinc) {
@@ -559,7 +587,7 @@
} else {
keylow = lpbltfx->ddckDestColorkey.dwColorSpaceLowValue;
keyhigh = lpbltfx->ddckDestColorkey.dwColorSpaceHighValue;
- }
+ }
for (y = sy = 0; y < dstheight; y++, sy += yinc) {
sbuf = sbase + (sy >> 16) * sdesc.u1.lPitch;