diff --git a/dlls/Makefile.in b/dlls/Makefile.in
index b1857cb533dc6acf71b5c15215eb4d0cc23a881d..5e80166e797525c116af399fab400592a5bc0049 100644
--- a/dlls/Makefile.in
+++ b/dlls/Makefile.in
@@ -461,7 +461,7 @@ wininet/libwininet.@LIBEXT@: libshlwapi.@LIBEXT@ libuser32.@LIBEXT@ libkernel32.
 winmm/joystick/libjoystick.drv.@LIBEXT@: libwinmm.@LIBEXT@ libuser32.@LIBEXT@ libntdll.@LIBEXT@
 winmm/libwinmm.@LIBEXT@: libuser32.@LIBEXT@ libadvapi32.@LIBEXT@ libkernel32.@LIBEXT@ libntdll.@LIBEXT@
 winmm/mcianim/libmcianim.drv.@LIBEXT@: libwinmm.@LIBEXT@ libuser32.@LIBEXT@ libkernel32.@LIBEXT@ libntdll.@LIBEXT@
-winmm/mciavi/libmciavi.drv.@LIBEXT@: libwinmm.@LIBEXT@ libuser32.@LIBEXT@ libkernel32.@LIBEXT@ libntdll.@LIBEXT@
+winmm/mciavi/libmciavi.drv.@LIBEXT@: libmsvfw32.@LIBEXT@ libwinmm.@LIBEXT@ libuser32.@LIBEXT@ libgdi32.@LIBEXT@ libkernel32.@LIBEXT@ libntdll.@LIBEXT@
 winmm/mcicda/libmcicda.drv.@LIBEXT@: libwinmm.@LIBEXT@ libuser32.@LIBEXT@ libkernel32.@LIBEXT@ libntdll.@LIBEXT@
 winmm/mciseq/libmciseq.drv.@LIBEXT@: libwinmm.@LIBEXT@ libuser32.@LIBEXT@ libkernel32.@LIBEXT@ libntdll.@LIBEXT@
 winmm/mciwave/libmciwave.drv.@LIBEXT@: libwinmm.@LIBEXT@ libuser32.@LIBEXT@ libkernel32.@LIBEXT@ libntdll.@LIBEXT@
diff --git a/dlls/winmm/mciavi/.cvsignore b/dlls/winmm/mciavi/.cvsignore
index d90e8676f46fc35905252a27df84be278370b0f3..886492c204631f5e4efc7b2c0c6b5db6a5cc4711 100644
--- a/dlls/winmm/mciavi/.cvsignore
+++ b/dlls/winmm/mciavi/.cvsignore
@@ -1,2 +1,3 @@
 *.spec.c
 Makefile
+mciavi_res.res
diff --git a/dlls/winmm/mciavi/Makefile.in b/dlls/winmm/mciavi/Makefile.in
index 020f367b50a62b29f0704c5ef371e14ccd410882..54cfefa095c99f089be953b77885d5f132276671 100644
--- a/dlls/winmm/mciavi/Makefile.in
+++ b/dlls/winmm/mciavi/Makefile.in
@@ -8,7 +8,13 @@ LDDLLFLAGS = @LDDLLFLAGS@
 SYMBOLFILE = $(MODULE).tmp.o
 
 C_SRCS = \
-	mciavi.c
+	info.c \
+	mciavi.c \
+	mmoutput.c \
+	wnd.c
+
+RC_SRCS = \
+	mciavi_res.rc
 
 @MAKE_DLL_RULES@
 
diff --git a/dlls/winmm/mciavi/info.c b/dlls/winmm/mciavi/info.c
new file mode 100644
index 0000000000000000000000000000000000000000..4c232a44141390d170d09826cde416ee8ce74715
--- /dev/null
+++ b/dlls/winmm/mciavi/info.c
@@ -0,0 +1,440 @@
+/* -*- tab-width: 8; c-basic-offset: 4 -*- */
+
+/*
+ * Digital video MCI Wine Driver
+ *
+ * Copyright 1999, 2000 Eric POUECH
+ */
+
+#include <string.h>
+#include "private_mciavi.h"
+#include "debugtools.h"
+
+DEFAULT_DEBUG_CHANNEL(mciavi);
+
+/**************************************************************************
+ * 				MCIAVI_ConvertFrameToTimeFormat	[internal]	
+ */
+DWORD 	MCIAVI_ConvertFrameToTimeFormat(WINE_MCIAVI* wma, DWORD val, LPDWORD lpRet)
+{
+    DWORD	   ret = 0;
+    
+    switch (wma->dwMciTimeFormat) {
+    case MCI_FORMAT_MILLISECONDS:
+        ret = (val * wma->mah.dwMicroSecPerFrame) / 1000;
+	break;
+    case MCI_FORMAT_FRAMES:
+	ret = val;
+	break;
+    default:
+	WARN("Bad time format %lu!\n", wma->dwMciTimeFormat);
+    }
+    TRACE("val=%lu=0x%08lx [tf=%lu] => ret=%lu\n", val, val, wma->dwMciTimeFormat, ret);
+    *lpRet = 0;
+    return ret;
+}
+
+/**************************************************************************
+ * 				MCIAVI_ConvertTimeFormatToFrame	[internal]	
+ */
+DWORD 	MCIAVI_ConvertTimeFormatToFrame(WINE_MCIAVI* wma, DWORD val)
+{
+    DWORD	ret = 0;
+    
+    switch (wma->dwMciTimeFormat) {
+    case MCI_FORMAT_MILLISECONDS:
+	ret = (val * 1000) / wma->mah.dwMicroSecPerFrame;
+	break;
+    case MCI_FORMAT_FRAMES:
+	ret = val;
+	break;
+    default:
+	WARN("Bad time format %lu!\n", wma->dwMciTimeFormat);
+    }
+    TRACE("val=%lu=0x%08lx [tf=%lu] => ret=%lu\n", val, val, wma->dwMciTimeFormat, ret);
+    return ret;
+}
+
+/***************************************************************************
+ * 				MCIAVI_mciGetDevCaps		[internal]
+ */
+DWORD	MCIAVI_mciGetDevCaps(UINT wDevID, DWORD dwFlags,  LPMCI_GETDEVCAPS_PARMS lpParms)
+{
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+    DWORD		ret;
+    
+    TRACE("(%04x, %08lX, %p)\n", wDevID, dwFlags, lpParms);
+    
+    if (lpParms == NULL) 	return MCIERR_NULL_PARAMETER_BLOCK;
+    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
+    
+    if (dwFlags & MCI_GETDEVCAPS_ITEM) {
+	switch (lpParms->dwItem) {
+	case MCI_GETDEVCAPS_DEVICE_TYPE:
+	    TRACE("MCI_GETDEVCAPS_DEVICE_TYPE !\n");
+	    lpParms->dwReturn = MAKEMCIRESOURCE(MCI_DEVTYPE_DIGITAL_VIDEO, MCI_DEVTYPE_DIGITAL_VIDEO);
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+	case MCI_GETDEVCAPS_HAS_AUDIO:
+	    TRACE("MCI_GETDEVCAPS_HAS_AUDIO !\n");
+	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+	case MCI_GETDEVCAPS_HAS_VIDEO:
+	    TRACE("MCI_GETDEVCAPS_HAS_VIDEO !\n");
+	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+	case MCI_GETDEVCAPS_USES_FILES:
+	    TRACE("MCI_GETDEVCAPS_USES_FILES !\n");
+	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+	case MCI_GETDEVCAPS_COMPOUND_DEVICE:
+	    TRACE("MCI_GETDEVCAPS_COMPOUND_DEVICE !\n");
+	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+	case MCI_GETDEVCAPS_CAN_EJECT:
+	    TRACE("MCI_GETDEVCAPS_CAN_EJECT !\n");
+	    lpParms->dwReturn = MAKEMCIRESOURCE(FALSE, MCI_FALSE);
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+	case MCI_GETDEVCAPS_CAN_PLAY:
+	    TRACE("MCI_GETDEVCAPS_CAN_PLAY !\n");
+	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+	case MCI_GETDEVCAPS_CAN_RECORD:
+	    TRACE("MCI_GETDEVCAPS_CAN_RECORD !\n");
+	    lpParms->dwReturn = MAKEMCIRESOURCE(FALSE, MCI_FALSE);
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+	case MCI_GETDEVCAPS_CAN_SAVE:
+	    TRACE("MCI_GETDEVCAPS_CAN_SAVE !\n");
+	    lpParms->dwReturn = MAKEMCIRESOURCE(FALSE, MCI_FALSE);
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+	default:
+	    FIXME("Unknown capability (%08lx) !\n", lpParms->dwItem);
+	    return MCIERR_UNRECOGNIZED_COMMAND;
+	}
+    } else {
+	WARN("No GetDevCaps-Item !\n");
+	return MCIERR_UNRECOGNIZED_COMMAND;
+    }
+    return ret;
+}
+
+/***************************************************************************
+ * 				MCIAVI_mciInfo			[internal]
+ */
+DWORD	MCIAVI_mciInfo(UINT wDevID, DWORD dwFlags, LPMCI_DGV_INFO_PARMSA lpParms)
+{
+    LPSTR		str = 0;
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+    DWORD		ret = 0;
+    
+    if (lpParms == NULL || lpParms->lpstrReturn == NULL)
+	return MCIERR_NULL_PARAMETER_BLOCK;
+    if (wma == NULL) return MCIERR_INVALID_DEVICE_ID;
+    
+    TRACE("buf=%p, len=%lu\n", lpParms->lpstrReturn, lpParms->dwRetSize);
+    
+    switch (dwFlags) {
+    case MCI_INFO_PRODUCT:
+	str = "Wine's AVI player";
+	break;
+    case MCI_INFO_FILE:
+	str = wma->openParms.lpstrElementName;
+	break;
+    default:
+	WARN("Don't know this info command (%lu)\n", dwFlags);
+	return MCIERR_UNRECOGNIZED_COMMAND;
+    }
+    if (str) {
+	if (strlen(str) + 1 > lpParms->dwRetSize) {
+	    ret = MCIERR_PARAM_OVERFLOW;
+	} else {
+	    lstrcpynA(lpParms->lpstrReturn, str, lpParms->dwRetSize);
+	}
+    } else {
+	lpParms->lpstrReturn[0] = 0;
+    }
+    return ret;
+}
+
+/***************************************************************************
+ * 				MCIAVI_mciSet			[internal]
+ */
+DWORD	MCIAVI_mciSet(UINT wDevID, DWORD dwFlags, LPMCI_DGV_SET_PARMS lpParms)
+{
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+    
+    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
+    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
+    
+    if (dwFlags & MCI_SET_TIME_FORMAT) {
+	switch (lpParms->dwTimeFormat) {
+	case MCI_FORMAT_MILLISECONDS:
+	    TRACE("MCI_FORMAT_MILLISECONDS !\n");
+	    wma->dwMciTimeFormat = MCI_FORMAT_MILLISECONDS;
+	    break;
+	case MCI_FORMAT_FRAMES:
+	    TRACE("MCI_FORMAT_FRAMES !\n");
+	    wma->dwMciTimeFormat = MCI_FORMAT_FRAMES;
+	    break;
+	default:
+	    WARN("Bad time format %lu!\n", lpParms->dwTimeFormat);
+	    return MCIERR_BAD_TIME_FORMAT;
+	}
+    }
+    
+    if (dwFlags & MCI_SET_DOOR_OPEN) {
+	TRACE("No support for door open !\n");
+	return MCIERR_UNSUPPORTED_FUNCTION;
+    }
+    if (dwFlags & MCI_SET_DOOR_CLOSED) {
+	TRACE("No support for door close !\n");
+	return MCIERR_UNSUPPORTED_FUNCTION;
+    }
+    if (dwFlags & MCI_SET_ON) {
+	char	buffer[256];
+	
+	strcpy(buffer, "MCI_SET_ON:");
+	
+	if (dwFlags & MCI_SET_VIDEO) {
+	    strncat(buffer, " video", sizeof(buffer));
+	    wma->dwSet |= 4;
+	}
+	if (dwFlags & MCI_SET_AUDIO) {
+	    strncat(buffer, " audio", sizeof(buffer));
+	    switch (lpParms->dwAudio) {
+	    case MCI_SET_AUDIO_ALL:
+		strncat(buffer, " all", sizeof(buffer));
+		wma->dwSet |= 3;
+		break;
+	    case MCI_SET_AUDIO_LEFT:
+		strncat(buffer, " left", sizeof(buffer));
+		wma->dwSet |= 1;
+		break;
+	    case MCI_SET_AUDIO_RIGHT:
+		strncat(buffer, " right", sizeof(buffer));
+		wma->dwSet |= 2;
+		break;
+	    default:
+		WARN("Unknown audio chanel %lu\n", lpParms->dwAudio);
+		break;
+	    }
+	}
+	if (dwFlags & MCI_DGV_SET_SEEK_EXACTLY) {
+	    strncat(buffer, " seek_exactly", sizeof(buffer));
+	}
+	FIXME("%s\n", buffer);
+    }
+    
+    if (dwFlags & MCI_SET_OFF) {
+	char	buffer[256];
+	
+	strcpy(buffer, "MCI_SET_OFF:");
+	if (dwFlags & MCI_SET_VIDEO) {
+	    strncat(buffer, " video", sizeof(buffer));
+	    wma->dwSet &= ~4;
+	}
+	if (dwFlags & MCI_SET_AUDIO) {
+	    strncat(buffer, " audio", sizeof(buffer));
+	    switch (lpParms->dwAudio) {
+	    case MCI_SET_AUDIO_ALL:
+		strncat(buffer, " all", sizeof(buffer));
+		wma->dwSet &= ~3;
+		break;
+	    case MCI_SET_AUDIO_LEFT:
+		strncat(buffer, " left", sizeof(buffer));
+		wma->dwSet &= ~2;
+		break;
+	    case MCI_SET_AUDIO_RIGHT:
+		strncat(buffer, " right", sizeof(buffer));
+		wma->dwSet &= ~2;
+		break;
+	    default:
+		WARN("Unknown audio chanel %lu\n", lpParms->dwAudio);
+		break;
+	    }
+	}
+	if (dwFlags & MCI_DGV_SET_SEEK_EXACTLY) {
+	    strncat(buffer, " seek_exactly", sizeof(buffer));
+	}
+	FIXME("%s\n", buffer);
+    }
+    if (dwFlags & MCI_DGV_SET_FILEFORMAT) {
+	LPSTR	str = "save";
+	if (dwFlags & MCI_DGV_SET_STILL)	
+	    str = "capture";
+	
+	switch (lpParms->dwFileFormat) {
+	case MCI_DGV_FF_AVI: 	FIXME("Setting file format (%s) to 'AVI'\n", str); 	break;
+	case MCI_DGV_FF_AVSS: 	FIXME("Setting file format (%s) to 'AVSS'\n", str);	break;
+	case MCI_DGV_FF_DIB: 	FIXME("Setting file format (%s) to 'DIB'\n", str);	break;
+	case MCI_DGV_FF_JFIF: 	FIXME("Setting file format (%s) to 'JFIF'\n", str);	break;
+	case MCI_DGV_FF_JPEG: 	FIXME("Setting file format (%s) to 'JPEG'\n", str);	break;
+	case MCI_DGV_FF_MPEG: 	FIXME("Setting file format (%s) to 'MPEG'\n", str); 	break;
+	case MCI_DGV_FF_RDIB:	FIXME("Setting file format (%s) to 'RLE DIB'\n", str);	break;
+	case MCI_DGV_FF_RJPEG: 	FIXME("Setting file format (%s) to 'RJPEG'\n", str);	break;
+	default:		FIXME("Setting unknown file format (%s): %ld\n", str, lpParms->dwFileFormat);
+	}
+    }
+    
+    if (dwFlags & MCI_DGV_SET_SPEED) {
+	FIXME("Setting speed to %ld\n", lpParms->dwSpeed);
+    }
+    
+    return 0;
+}
+
+/***************************************************************************
+ * 				MCIAVI_mciStatus			[internal]
+ */
+DWORD	MCIAVI_mciStatus(UINT wDevID, DWORD dwFlags, LPMCI_DGV_STATUS_PARMSA lpParms)
+{
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+    DWORD		ret = 0;
+    
+    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
+    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
+    
+    if (dwFlags & MCI_STATUS_ITEM) {
+	switch (lpParms->dwItem) {
+	case MCI_STATUS_CURRENT_TRACK:
+	    lpParms->dwReturn = 1;
+	    TRACE("MCI_STATUS_CURRENT_TRACK => %lu\n", lpParms->dwReturn);
+	    break;
+	case MCI_STATUS_LENGTH:
+	    if (!wma->hFile) {
+		lpParms->dwReturn = 0;
+		return MCIERR_UNSUPPORTED_FUNCTION;
+	    }
+	    /* only one track in file is currently handled, so don't take care of MCI_TRACK flag */
+	    lpParms->dwReturn = MCIAVI_ConvertFrameToTimeFormat(wma, wma->mah.dwTotalFrames, &ret);
+	    TRACE("MCI_STATUS_LENGTH => %lu\n", lpParms->dwReturn);
+	    break;
+	case MCI_STATUS_MODE:
+ 	    lpParms->dwReturn = MAKEMCIRESOURCE(wma->dwStatus, wma->dwStatus);
+	    ret = MCI_RESOURCE_RETURNED;
+	    TRACE("MCI_STATUS_MODE => %u\n", LOWORD(lpParms->dwReturn));
+	    break;
+	case MCI_STATUS_MEDIA_PRESENT:
+	    TRACE("MCI_STATUS_MEDIA_PRESENT => TRUE\n");
+	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+	case MCI_STATUS_NUMBER_OF_TRACKS:
+	    lpParms->dwReturn = 1;
+	    TRACE("MCI_STATUS_NUMBER_OF_TRACKS => %lu\n", lpParms->dwReturn);
+	    break;
+	case MCI_STATUS_POSITION:
+	    if (!wma->hFile) {
+		lpParms->dwReturn = 0;
+		return MCIERR_UNSUPPORTED_FUNCTION;
+	    }
+	    /* only one track in file is currently handled, so don't take care of MCI_TRACK flag */
+	    lpParms->dwReturn = MCIAVI_ConvertFrameToTimeFormat(wma, 
+							     (dwFlags & MCI_STATUS_START) ? 0 : wma->dwCurrVideoFrame,
+							     &ret);
+	    TRACE("MCI_STATUS_POSITION %s => %lu\n", 
+		  (dwFlags & MCI_STATUS_START) ? "start" : "current", lpParms->dwReturn);
+	    break;
+	case MCI_STATUS_READY:
+	    lpParms->dwReturn = (wma->dwStatus == MCI_MODE_NOT_READY) ?
+		MAKEMCIRESOURCE(FALSE, MCI_FALSE) : MAKEMCIRESOURCE(TRUE, MCI_TRUE);
+	    ret = MCI_RESOURCE_RETURNED;
+	    TRACE("MCI_STATUS_READY = %u\n", LOWORD(lpParms->dwReturn));
+	    break;
+	case MCI_STATUS_TIME_FORMAT:
+	    lpParms->dwReturn = MAKEMCIRESOURCE(wma->dwMciTimeFormat, wma->dwMciTimeFormat);
+	    TRACE("MCI_STATUS_TIME_FORMAT => %u\n", LOWORD(lpParms->dwReturn));
+	    ret = MCI_RESOURCE_RETURNED;
+	    break;
+#if 0
+	case MCI_AVI_STATUS_AUDIO_BREAKS:
+	case MCI_AVI_STATUS_FRAMES_SKIPPED:
+	case MCI_AVI_STATUS_LAST_PLAY_SPEED:
+	case MCI_DGV_STATUS_AUDIO:
+	case MCI_DGV_STATUS_AUDIO_INPUT:
+	case MCI_DGV_STATUS_AUDIO_RECORD:
+	case MCI_DGV_STATUS_AUDIO_SOURCE:
+	case MCI_DGV_SETAUDIO_AVERAGE:
+	case MCI_DGV_SETAUDIO_LEFT:
+	case MCI_DGV_SETAUDIO_RIGHT:
+	case MCI_DGV_SETAUDIO_STEREO:
+	case MCI_DGV_STATUS_AUDIO_STREAM:
+	case MCI_DGV_STATUS_AVGBYTESPERSEC:
+	case MCI_DGV_STATUS_BASS:
+	case MCI_DGV_STATUS_BITSPERPEL:
+	case MCI_DGV_STATUS_BITSPERSAMPLE:
+	case MCI_DGV_STATUS_BLOCKALIGN:
+	case MCI_DGV_STATUS_BRIGHTNESS:
+	case MCI_DGV_STATUS_COLOR:
+	case MCI_DGV_STATUS_CONTRAST:
+	case MCI_DGV_STATUS_FILEFORMAT:
+	case MCI_DGV_STATUS_FILE_MODE:
+	case MCI_DGV_STATUS_FILE_COMPLETION:
+	case MCI_DGV_STATUS_FORWARD:
+	case MCI_DGV_STATUS_FRAME_RATE:
+	case MCI_DGV_STATUS_GAMMA:
+#endif
+	case MCI_DGV_STATUS_HPAL:
+	    lpParms->dwReturn = 0;
+	    TRACE("MCI_DGV_STATUS_HPAL => %lx\n", lpParms->dwReturn);
+	    break;
+	case MCI_DGV_STATUS_HWND:
+	    lpParms->dwReturn = wma->hWnd;
+	    TRACE("MCI_DGV_STATUS_HWND => %u\n", wma->hWnd);
+	    break;
+#if 0
+	case MCI_DGV_STATUS_KEY_COLOR:
+	case MCI_DGV_STATUS_KEY_INDEX:
+	case MCI_DGV_STATUS_MONITOR:
+	case MCI_DGV_MONITOR_FILE:
+	case MCI_DGV_MONITOR_INPUT:
+	case MCI_DGV_STATUS_MONITOR_METHOD:
+	case MCI_DGV_STATUS_PAUSE_MODE:
+	case MCI_DGV_STATUS_SAMPLESPERSECOND:
+	case MCI_DGV_STATUS_SEEK_EXACTLY:
+	case MCI_DGV_STATUS_SHARPNESS:
+	case MCI_DGV_STATUS_SIZE:
+	case MCI_DGV_STATUS_SMPTE:
+	case MCI_DGV_STATUS_SPEED:
+	case MCI_DGV_STATUS_STILL_FILEFORMAT:
+	case MCI_DGV_STATUS_TINT:
+	case MCI_DGV_STATUS_TREBLE:
+	case MCI_DGV_STATUS_UNSAVED:
+	case MCI_DGV_STATUS_VIDEO:
+	case MCI_DGV_STATUS_VIDEO_RECORD:
+	case MCI_DGV_STATUS_VIDEO_SOURCE:
+	case MCI_DGV_STATUS_VIDEO_SRC_NUM:
+	case MCI_DGV_STATUS_VIDEO_STREAM:
+	case MCI_DGV_STATUS_VOLUME:
+	case MCI_DGV_STATUS_WINDOW_VISIBLE:
+	case MCI_DGV_STATUS_WINDOW_MINIMIZED:
+	case MCI_DGV_STATUS_WINDOW_MAXIMIZED:
+	case MCI_STATUS_MEDIA_PRESENT:
+#endif
+	default:
+	    FIXME("Unknowm command %08lX !\n", lpParms->dwItem);
+	    TRACE("(%04x, %08lX, %p)\n", wDevID, dwFlags, lpParms);
+    	    return MCIERR_UNRECOGNIZED_COMMAND;
+	}
+    } else {
+	WARN("No Status-Item!\n");
+	return MCIERR_UNRECOGNIZED_COMMAND;
+    }
+    if (dwFlags & MCI_NOTIFY) {
+	TRACE("MCI_NOTIFY_SUCCESSFUL %08lX !\n", lpParms->dwCallback);
+	mciDriverNotify((HWND)LOWORD(lpParms->dwCallback),
+			wma->openParms.wDeviceID, MCI_NOTIFY_SUCCESSFUL);
+    }
+    
+    return ret;
+}
+
+
diff --git a/dlls/winmm/mciavi/mciavi.c b/dlls/winmm/mciavi/mciavi.c
index 284a1c44767d4607a362eab78a1fc0f45368c42d..c8dce658999f4ce2ebf1ebe38251b3e41e1061ca 100644
--- a/dlls/winmm/mciavi/mciavi.c
+++ b/dlls/winmm/mciavi/mciavi.c
@@ -3,50 +3,132 @@
 /*
  * Digital video MCI Wine Driver
  *
- * Copyright 1999 Eric POUECH
+ * Copyright 1999, 2000 Eric POUECH
+ */
+
+/* TODO list :
+ *	- handling of palettes
+ *	- recording (which input devices ?), a cam recorder ?
+ *	- lots of messages still need to be handled (cf FIXME)
+ *	- synchronization between audio and video (especially for interleaved
+ *	  files)
+ *	- synchronization (as in all the Wine MCI drivers (MCI_WAIT) messages)
+ *	- robustness when reading file can be enhanced
+ *	- better move the AVI handling part to avifile DLL and make use of it
+ *	- some files appear to have more than one audio stream (we only play the
+ *	  first one)
+ *	- some files contain an index of audio/video frame. Better use it, 
+ *	  instead of rebuilding it
+ *	- mciWindow (for setting the hWnd) is broken with media player
+ *	- stopping while playing a file with sound blocks until all buffered
+ *        audio is played... still should be stopped ASAP
  */
 
 #include <string.h>
-
-#include "windef.h"
-#include "winbase.h"
-#include "wingdi.h"
-#include "winuser.h"
-#include "mmddk.h"
-#include "digitalv.h"
+#include "private_mciavi.h"
 #include "debugtools.h"
 
 DEFAULT_DEBUG_CHANNEL(mciavi);
 
-typedef struct {
-    UINT		wDevID;
-    int			nUseCount;          	/* Incremented for each shared open          */
-    BOOL16  		fShareable;         	/* TRUE if first open was shareable 	     */
-    WORD		wNotifyDeviceID;    	/* MCI device ID with a pending notification */
-    HANDLE16 		hCallback;         	/* Callback handle for pending notification  */
-    HMMIO		hFile;	            	/* mmio file handle open as Element          */
-    WORD		wStatus;		/* One of MCI_MODE_XXX			     */
-    MCI_OPEN_PARMSA 	openParms;
-    DWORD		dwTimeFormat;
-} WINE_MCIAVI;
+/* ===================================================================
+ * ===================================================================
+ * FIXME: should be using the new mmThreadXXXX functions from WINMM
+ * instead of those
+ * it would require to add a wine internal flag to mmThreadCreate
+ * in order to pass a 32 bit function instead of a 16 bit one
+ * ===================================================================
+ * =================================================================== */
+
+struct SCA {
+    UINT 	wDevID;
+    UINT 	wMsg;
+    DWORD 	dwParam1;
+    DWORD 	dwParam2;
+};
+
+/**************************************************************************
+ * 				MCI_SCAStarter			[internal]
+ */
+static DWORD CALLBACK	MCI_SCAStarter(LPVOID arg)
+{
+    struct SCA*	sca = (struct SCA*)arg;
+    DWORD	ret;
+    
+    TRACE("In thread before async command (%08x,%u,%08lx,%08lx)\n",
+	  sca->wDevID, sca->wMsg, sca->dwParam1, sca->dwParam2);
+    ret = mciSendCommandA(sca->wDevID, sca->wMsg, sca->dwParam1 | MCI_WAIT, sca->dwParam2);
+    TRACE("In thread after async command (%08x,%u,%08lx,%08lx)\n",
+	  sca->wDevID, sca->wMsg, sca->dwParam1, sca->dwParam2);
+    HeapFree(GetProcessHeap(), 0, sca);
+    ExitThread(ret);
+    WARN("Should not happen ? what's wrong \n");
+    /* should not go after this point */
+    return ret;
+}
+
+/**************************************************************************
+ * 				MCI_SendCommandAsync		[internal]
+ */
+static	DWORD MCI_SendCommandAsync(UINT wDevID, UINT wMsg, DWORD dwParam1, 
+				   DWORD dwParam2, UINT size)
+{
+    struct SCA*	sca = HeapAlloc(GetProcessHeap(), 0, sizeof(struct SCA) + size);
+    
+    if (sca == 0)
+	return MCIERR_OUT_OF_MEMORY;
+    
+    sca->wDevID   = wDevID;
+    sca->wMsg     = wMsg;
+    sca->dwParam1 = dwParam1;
+    
+    if (size && dwParam2) {
+	sca->dwParam2 = (DWORD)sca + sizeof(struct SCA);
+	/* copy structure passed by program in dwParam2 to be sure 
+	 * we can still use it whatever the program does 
+	 */
+	memcpy((LPVOID)sca->dwParam2, (LPVOID)dwParam2, size);
+    } else {
+	sca->dwParam2 = dwParam2;
+    }
+    
+    if (CreateThread(NULL, 0, MCI_SCAStarter, sca, 0, NULL) == 0) {
+	WARN("Couldn't allocate thread for async command handling, sending synchronously\n");
+	return MCI_SCAStarter(&sca);
+    }
+    return 0;
+}
 
 /*======================================================================*
  *                  	    MCI AVI implemantation			*
  *======================================================================*/
 
+HINSTANCE MCIAVI_hInstance = 0;
+
+BOOL WINAPI MCIAVI_LibMain(HINSTANCE hInstDLL, DWORD fdwReason, LPVOID fImpLoad)
+{
+    switch (fdwReason) {
+    case DLL_PROCESS_ATTACH:
+	MCIAVI_hInstance = hInstDLL;
+	break;
+    }
+    return TRUE;
+}
+
 /**************************************************************************
- * 				AVI_drvOpen			[internal]	
+ * 				MCIAVI_drvOpen			[internal]	
  */
-static	DWORD	AVI_drvOpen(LPSTR str, LPMCI_OPEN_DRIVER_PARMSA modp)
+static	DWORD	MCIAVI_drvOpen(LPSTR str, LPMCI_OPEN_DRIVER_PARMSA modp)
 {
     WINE_MCIAVI*	wma = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(WINE_MCIAVI));
+    static WCHAR	mciAviWStr[] = {'M','C','I','A','V','I',0};
 
     if (!wma)
 	return 0;
-
+    
     wma->wDevID = modp->wDeviceID;
     mciSetDriverData(wma->wDevID, (DWORD)wma);
-    modp->wCustomCommandTable = MCI_NO_COMMAND_TABLE;
+    wma->wCommandTable = mciLoadCommandResource(MCIAVI_hInstance, mciAviWStr, 0);
+    modp->wCustomCommandTable = wma->wCommandTable;
     modp->wType = MCI_DEVTYPE_DIGITAL_VIDEO;
     return modp->wDeviceID;
 }
@@ -54,22 +136,37 @@ static	DWORD	AVI_drvOpen(LPSTR str, LPMCI_OPEN_DRIVER_PARMSA modp)
 /**************************************************************************
  * 				MCIAVI_drvClose		[internal]	
  */
-static	DWORD	AVI_drvClose(DWORD dwDevID)
+static	DWORD	MCIAVI_drvClose(DWORD dwDevID)
 {
     WINE_MCIAVI*  wma = (WINE_MCIAVI*)mciGetDriverData(dwDevID);
-
+    
     if (wma) {
-	HeapFree(GetProcessHeap(), 0, wma);	
 	mciSetDriverData(dwDevID, 0);
+	mciFreeCommandResource(wma->wCommandTable);
+	HeapFree(GetProcessHeap(), 0, wma);	
+	return 1;
+    }
+    return 0;
+}
+
+/**************************************************************************
+ * 				MCIAVI_drvConfigure		[internal]	
+ */
+static	DWORD	MCIAVI_drvConfigure(DWORD dwDevID)
+{
+    WINE_MCIAVI*  wma = (WINE_MCIAVI*)mciGetDriverData(dwDevID);
+
+    if (wma) {
+	MessageBoxA(0, "Sample AVI Wine Driver !", "MM-Wine Driver", MB_OK); 
 	return 1;
     }
     return 0;
 }
 
 /**************************************************************************
- * 				AVI_mciGetOpenDev		[internal]	
+ * 				MCIAVI_mciGetOpenDev		[internal]	
  */
-static WINE_MCIAVI*  AVI_mciGetOpenDev(UINT16 wDevID)
+WINE_MCIAVI*  MCIAVI_mciGetOpenDev(UINT wDevID)
 {
     WINE_MCIAVI*	wma = (WINE_MCIAVI*)mciGetDriverData(wDevID);
     
@@ -80,18 +177,56 @@ static WINE_MCIAVI*  AVI_mciGetOpenDev(UINT16 wDevID)
     return wma;
 }
 
-static	DWORD	AVI_mciStop(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms);
+static void MCIAVI_CleanUp(WINE_MCIAVI* wma)
+{
+    /* to prevent handling in WindowProc */
+    wma->dwStatus = MCI_MODE_NOT_READY;
+    if (wma->hFile) {
+	mmioClose(wma->hFile, 0);
+	wma->hFile = 0;
+	if (wma->lpVideoIndex)	HeapFree(GetProcessHeap(), 0, wma->lpVideoIndex);
+	wma->lpVideoIndex = NULL;
+	if (wma->lpAudioIndex)	HeapFree(GetProcessHeap(), 0, wma->lpAudioIndex);
+	wma->lpAudioIndex = NULL;
+	if (wma->hic)		ICClose(wma->hic);
+	wma->hic = 0;
+	if (wma->inbih)		HeapFree(GetProcessHeap(), 0, wma->inbih);
+	wma->inbih = NULL;
+	if (wma->outbih)	HeapFree(GetProcessHeap(), 0, wma->outbih);
+	wma->outbih = NULL;
+        if (wma->indata)	HeapFree(GetProcessHeap(), 0, wma->indata);
+	wma->indata = NULL;
+    	if (wma->outdata)	HeapFree(GetProcessHeap(), 0, wma->outdata);
+	wma->outdata = NULL;
+    	if (wma->hbmFrame)	DeleteObject(wma->hbmFrame);
+	wma->hbmFrame = 0;
+	if (wma->hWnd)		DestroyWindow(wma->hWnd);
+	wma->hWnd = 0;
+	
+	if (wma->lpWaveFormat)	HeapFree(GetProcessHeap(), 0, wma->lpWaveFormat);
+	wma->lpWaveFormat = 0;
+
+	memset(&wma->mah, 0, sizeof(wma->mah));
+	memset(&wma->ash_video, 0, sizeof(wma->ash_video));
+	memset(&wma->ash_audio, 0, sizeof(wma->ash_audio));
+	wma->dwCurrVideoFrame = wma->dwCurrAudioBlock = 0;
+    }
+}
+
+static	DWORD	MCIAVI_mciStop(UINT wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms);
 
 /***************************************************************************
- * 				AVI_mciOpen			[internal]
+ * 				MCIAVI_mciOpen			[internal]
  */
-static	DWORD	AVI_mciOpen(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_OPEN_PARMSA lpParms)
+static	DWORD	MCIAVI_mciOpen(UINT wDevID, DWORD dwFlags, 
+			    LPMCI_DGV_OPEN_PARMSA lpOpenParms)
 {
     WINE_MCIAVI*	wma = (WINE_MCIAVI*)mciGetDriverData(wDevID);
+    LRESULT		dwRet = 0;
     
-    TRACE("(%04x, %08lX, %p) : semi-stub\n", wDevID, dwFlags, lpParms);
+    TRACE("(%04x, %08lX, %p)\n", wDevID, dwFlags, lpOpenParms);
     
-    if (lpParms == NULL) 		return MCIERR_NULL_PARAMETER_BLOCK;
+    if (lpOpenParms == NULL) 		return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)			return MCIERR_INVALID_DEVICE_ID;
     
     if (wma->nUseCount > 0) {
@@ -106,537 +241,337 @@ static	DWORD	AVI_mciOpen(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_OPEN_PARMSA lpP
 	wma->nUseCount = 1;
 	wma->fShareable = dwFlags & MCI_OPEN_SHAREABLE;
     }
+    
+    wma->dwStatus = MCI_MODE_NOT_READY;	
+    InitializeCriticalSection(&wma->cs);
+    
     if (dwFlags & MCI_OPEN_ELEMENT) {
-	TRACE("MCI_OPEN_ELEMENT !\n");
-	/*		return MCIERR_NO_ELEMENT_ALLOWED; */
+	if (dwFlags & MCI_OPEN_ELEMENT_ID) {
+	    /* could it be that (DWORD)lpOpenParms->lpstrElementName 
+	     * contains the hFile value ? 
+	     */
+	    dwRet = MCIERR_UNRECOGNIZED_COMMAND;
+	} else if (strlen(lpOpenParms->lpstrElementName) > 0) {
+	    /* FIXME : what should be done id wma->hFile is already != 0, or the driver is playin' */
+	    TRACE("MCI_OPEN_ELEMENT '%s' !\n", lpOpenParms->lpstrElementName);
+	    
+	    if (lpOpenParms->lpstrElementName && (strlen(lpOpenParms->lpstrElementName) > 0)) {
+		wma->hFile = mmioOpenA(lpOpenParms->lpstrElementName, NULL, 
+				       MMIO_ALLOCBUF | MMIO_DENYWRITE | MMIO_READWRITE);
+		
+		if (wma->hFile == 0) {
+		    WARN("can't find file='%s' !\n", lpOpenParms->lpstrElementName);
+		    dwRet = MCIERR_FILE_NOT_FOUND;
+		} else {
+		    if (!MCIAVI_GetInfo(wma)) 
+			dwRet = MCIERR_INVALID_FILE;
+		    else if (!MCIAVI_OpenVideo(wma))
+			dwRet = MCIERR_CANNOT_LOAD_DRIVER;
+		    else if (!MCIAVI_CreateWindow(wma, dwFlags, lpOpenParms))
+			dwRet = MCIERR_CREATEWINDOW;
+		} 
+	    }
+	} else {
+	    FIXME("Don't record yet\n");
+	    dwRet = MCIERR_UNSUPPORTED_FUNCTION;
+	}
     }
     
-    wma->openParms.dwCallback = lpParms->dwCallback;
-    wma->openParms.wDeviceID  = (WORD)lpParms->wDeviceID;
-    wma->openParms.lpstrDeviceType = lpParms->lpstrDeviceType;
-    wma->openParms.lpstrElementName = lpParms->lpstrElementName;
-    wma->openParms.lpstrAlias = lpParms->lpstrAlias;
+    memcpy(&wma->openParms, lpOpenParms, sizeof(MCI_WAVE_OPEN_PARMSA));
     
-    wma->wNotifyDeviceID = lpParms->wDeviceID;
-    /* FIXME: do real open */
-    wma->wStatus = MCI_MODE_STOP;
-    wma->dwTimeFormat = MCI_FORMAT_TMSF;
-    
-    return 0;
+    if (dwRet == 0) {
+	wma->dwStatus = MCI_MODE_STOP;
+	wma->dwMciTimeFormat = MCI_FORMAT_FRAMES;
+    } else {
+	MCIAVI_CleanUp(wma);
+    }
+    return dwRet;
     
 }
 
 /***************************************************************************
- * 				AVI_mciClose			[internal]
+ * 				MCIAVI_mciClose			[internal]
  */
-static	DWORD	AVI_mciClose(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
+static	DWORD	MCIAVI_mciClose(UINT wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+    DWORD		dwRet = 0;
     
-    TRACE("(%04x, %08lX, %p) : semi-stub\n", wDevID, dwFlags, lpParms);    
+    TRACE("(%04x, %08lX, %p)\n", wDevID, dwFlags, lpParms);    
     
     if (wma == NULL) 	return MCIERR_INVALID_DEVICE_ID;
     
     if (wma->nUseCount == 1) {
-	AVI_mciStop(wDevID, 0, NULL);
-	/* FIXME: do real closing */
+	if (wma->dwStatus != MCI_MODE_STOP)
+	    dwRet = MCIAVI_mciStop(wDevID, MCI_WAIT, lpParms);
+    	MCIAVI_CleanUp(wma);
+	
+	if ((dwFlags & MCI_NOTIFY) && lpParms) {
+	    mciDriverNotify((HWND)LOWORD(lpParms->dwCallback), 
+			    wma->openParms.wDeviceID,
+			    MCI_NOTIFY_SUCCESSFUL);
+	}
+	HeapFree(GetProcessHeap(), 0, wma);
+	return dwRet;
     }
     wma->nUseCount--;
-    return 0;
+    return dwRet;
 }
 
 /***************************************************************************
- * 				AVI_mciPlay			[internal]
+ * 				MCIAVI_mciPlay			[internal]
  */
-static	DWORD	AVI_mciPlay(UINT16 wDevID, DWORD dwFlags, LPMCI_PLAY_PARMS lpParms)
+static	DWORD	MCIAVI_mciPlay(UINT wDevID, DWORD dwFlags, LPMCI_PLAY_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
-    
-    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
-    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
-    
-    wma->wStatus = MCI_MODE_PLAY;
-    if (lpParms && (dwFlags & MCI_NOTIFY)) {
-	TRACE("MCI_NOTIFY_SUCCESSFUL %08lX !\n", lpParms->dwCallback);
-	mciDriverNotify((HWND)LOWORD(lpParms->dwCallback),
-			  wma->wNotifyDeviceID, MCI_NOTIFY_SUCCESSFUL);
-    }
-    return 0;
-}
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+    DWORD		tc;
+    DWORD		frameTime;
+    DWORD		delta;
+    DWORD		dwRet;
+    LPWAVEHDR		waveHdr = NULL;
+    unsigned		i, nHdr = 0;
+    DWORD		dwFromFrame, dwToFrame;
 
-/***************************************************************************
- * 				AVI_mciRecord			[internal]
- */
-static	DWORD	AVI_mciRecord(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RECORD_PARMS lpParms)
-{
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
+    TRACE("(%04x, %08lX, %p)\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
     
-    wma->wStatus = MCI_MODE_RECORD;
-    return 0;
-}
-
-/***************************************************************************
- * 				AVI_mciStop			[internal]
- */
-static	DWORD	AVI_mciStop(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
-{
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
+    if (!wma->hFile)		return MCIERR_FILE_NOT_FOUND;
+    if (!wma->hWnd) 		return MCIERR_NO_WINDOW;
     
-    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
-    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
+    wma->dwStatus = MCI_MODE_PLAY;
     
-    wma->wStatus = MCI_MODE_STOP;
-    return 0;
-}
-
-/***************************************************************************
- * 				AVI_mciPause			[internal]
- */
-static	DWORD	AVI_mciPause(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
-{
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    if (!(dwFlags & MCI_WAIT)) {
+	return MCI_SendCommandAsync(wma->openParms.wDeviceID, MCI_PLAY, dwFlags, 
+				    (DWORD)lpParms, sizeof(MCI_PLAY_PARMS));
+    }
     
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
+    ShowWindow(wma->hWnd, SW_SHOW);
     
-    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
-    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
+    dwFromFrame = wma->dwCurrVideoFrame;
+    dwToFrame = wma->dwPlayableVideoFrames - 1;
     
-    wma->wStatus = MCI_MODE_PAUSE;
-    return 0;
-}
+    if (lpParms && (dwFlags & MCI_FROM)) {
+	dwFromFrame = MCIAVI_ConvertTimeFormatToFrame(wma, lpParms->dwFrom); 
+    }
+    if (lpParms && (dwFlags & MCI_TO)) {
+	dwToFrame = MCIAVI_ConvertTimeFormatToFrame(wma, lpParms->dwTo);
+    }
+    if (dwToFrame >= wma->dwPlayableVideoFrames)
+	dwToFrame = wma->dwPlayableVideoFrames - 1;
 
-/***************************************************************************
- * 				AVI_mciResume			[internal]
- */
-static	DWORD	AVI_mciResume(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
-{
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
-    
-    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
-    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
+    TRACE("Playing from frame=%lu to frame=%lu\n", dwFromFrame, dwToFrame);
     
-    wma->wStatus = MCI_MODE_PLAY;
-    return 0;
-}
+    if (dwToFrame <= wma->dwCurrVideoFrame)
+	return TRUE;
+    wma->dwCurrVideoFrame = dwFromFrame;
 
-/***************************************************************************
- * 				AVI_mciSeek			[internal]
- */
-static	DWORD	AVI_mciSeek(UINT16 wDevID, DWORD dwFlags, LPMCI_SEEK_PARMS lpParms)
-{
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
+    if (dwFlags & (MCI_DGV_PLAY_REPEAT|MCI_DGV_PLAY_REVERSE|MCI_MCIAVI_PLAY_WINDOW|MCI_MCIAVI_PLAY_FULLSCREEN))
+	FIXME("Unsupported flag %08lx\n", dwFlags);
     
-    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
-    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
-    
-    return 0;
-}
+    /* time is in microseconds, we should convert it to milliseconds */
+    frameTime = (wma->mah.dwMicroSecPerFrame + 500) / 1000;
 
-/***************************************************************************
- * 				AVI_mciSet			[internal]
- */
-static	DWORD	AVI_mciSet(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_SET_PARMS lpParms)
-{
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
-    
-    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
-    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
-    
-    if (dwFlags & MCI_SET_TIME_FORMAT) {
-	switch (lpParms->dwTimeFormat) {
-	case MCI_FORMAT_MILLISECONDS:
-	    TRACE("MCI_FORMAT_MILLISECONDS !\n");
-	    wma->dwTimeFormat = MCI_FORMAT_MILLISECONDS;
-	    break;
-	case MCI_FORMAT_FRAMES:
-	    TRACE("MCI_FORMAT_FRAMES !\n");
-	    wma->dwTimeFormat = MCI_FORMAT_FRAMES;
-	    break;
-	default:
-	    WARN("Bad time format %lu!\n", lpParms->dwTimeFormat);
-	    return MCIERR_BAD_TIME_FORMAT;
-	}
+    if (wma->lpWaveFormat) {
+	if ((dwRet = MCIAVI_OpenAudio(wma, &nHdr, &waveHdr)) != 0)
+	    goto cleanUp;
+	/* fill the queue with as many wave headers as possible */
+	MCIAVI_PlayAudioBlocks(wma, nHdr, waveHdr);
     }
-    
-    if (dwFlags & MCI_SET_DOOR_OPEN) {
-	TRACE("No support for door open !\n");
-	return MCIERR_UNSUPPORTED_FUNCTION;
-    }
-    if (dwFlags & MCI_SET_DOOR_CLOSED) {
-	TRACE("No support for door close !\n");
-	return MCIERR_UNSUPPORTED_FUNCTION;
-    }
-    if (dwFlags & MCI_SET_ON) {
-	char	buffer[256];
-	
-	strcpy(buffer, "MCI_SET_ON:");
+
+    while (wma->dwStatus != MCI_MODE_STOP && wma->dwStatus != MCI_MODE_NOT_READY) {
+	tc = GetTickCount();
 	
-	if (dwFlags & MCI_SET_VIDEO) {
-	    strncat(buffer, " video", sizeof(buffer));
-	}
-	if (dwFlags & MCI_SET_AUDIO) {
-	    strncat(buffer, " audio", sizeof(buffer));
-	    if (lpParms->dwAudio & MCI_SET_AUDIO_ALL)
-		strncat(buffer, " all", sizeof(buffer));
-	    if (lpParms->dwAudio & MCI_SET_AUDIO_LEFT)
-		strncat(buffer, " left", sizeof(buffer));
-	    if (lpParms->dwAudio & MCI_SET_AUDIO_RIGHT)
-		strncat(buffer, " right", sizeof(buffer));
+	MCIAVI_DrawFrame(wma);
+
+	if (wma->lpWaveFormat) {
+	    MCIAVI_PlayAudioBlocks(wma, nHdr, waveHdr);
+	    delta = GetTickCount() - tc;
+	    WaitForSingleObject(wma->hEvent, (delta >= frameTime) ? 0 : frameTime - delta);
 	}
-	if (dwFlags & MCI_DGV_SET_SEEK_EXACTLY) {
-	    strncat(buffer, " seek_exactly", sizeof(buffer));
+
+	delta = GetTickCount() - tc;
+	if (delta < frameTime)
+	    Sleep(frameTime - delta);
+
+	if (wma->dwCurrVideoFrame++ >= dwToFrame) {
+	    wma->dwCurrVideoFrame--;
+	    wma->dwStatus = MCI_MODE_STOP;
 	}
-	TRACE("%s\n", buffer);
     }
-    
-    if (dwFlags & MCI_SET_OFF) {
-	char	buffer[256];
-	
-	strcpy(buffer, "MCI_SET_OFF:");
-	if (dwFlags & MCI_SET_VIDEO) {
-	    strncat(buffer, " video", sizeof(buffer));
-	}
-	if (dwFlags & MCI_SET_AUDIO) {
-	    strncat(buffer, " audio", sizeof(buffer));
-	    if (lpParms->dwAudio & MCI_SET_AUDIO_ALL)
-		strncat(buffer, " all", sizeof(buffer));
-	    if (lpParms->dwAudio & MCI_SET_AUDIO_LEFT)
-		strncat(buffer, " left", sizeof(buffer));
-	    if (lpParms->dwAudio & MCI_SET_AUDIO_RIGHT)
-		strncat(buffer, " right", sizeof(buffer));
-	}
-	if (dwFlags & MCI_DGV_SET_SEEK_EXACTLY) {
-	    strncat(buffer, " seek_exactly", sizeof(buffer));
+
+    if (wma->lpWaveFormat) {
+	while (*(volatile DWORD*)&wma->dwEventCount != nHdr - 1) {
+	    Sleep(100);
 	}
-	TRACE("%s\n", buffer);
-    }
-    if (dwFlags & MCI_DGV_SET_FILEFORMAT) {
-	LPSTR	str = "save";
-	if (dwFlags & MCI_DGV_SET_STILL)	
-	    str = "capture";
 	
-	switch (lpParms->dwFileFormat) {
-	case MCI_DGV_FF_AVI: 	TRACE("Setting file format (%s) to 'AVI'\n", str); 	break;
-	case MCI_DGV_FF_AVSS: 	TRACE("Setting file format (%s) to 'AVSS'\n", str);	break;
-	case MCI_DGV_FF_DIB: 	TRACE("Setting file format (%s) to 'DIB'\n", str);	break;
-	case MCI_DGV_FF_JFIF: 	TRACE("Setting file format (%s) to 'JFIF'\n", str);	break;
-	case MCI_DGV_FF_JPEG: 	TRACE("Setting file format (%s) to 'JPEG'\n", str);	break;
-	case MCI_DGV_FF_MPEG: 	TRACE("Setting file format (%s) to 'MPEG'\n", str); 	break;
-	case MCI_DGV_FF_RDIB:	TRACE("Setting file format (%s) to 'RLE DIB'\n", str);	break;
-	case MCI_DGV_FF_RJPEG: 	TRACE("Setting file format (%s) to 'RJPEG'\n", str);	break;
-	default:		TRACE("Setting unknown file format (%s): %ld\n", str, lpParms->dwFileFormat);
-	}
-    }
-    
-    if (dwFlags & MCI_DGV_SET_SPEED) {
-	TRACE("Setting speed to %ld\n", lpParms->dwSpeed);
+	/* just to get rid of some race conditions between play, stop and pause */
+	waveOutReset(wma->hWave);
+
+	for (i = 0; i < nHdr; i++)
+	    waveOutUnprepareHeader(wma->hWave, &waveHdr[i], sizeof(WAVEHDR));
     }
-    
-    return 0;
-}
 
-/***************************************************************************
- * 				AVI_mciStatus			[internal]
- */
-static	DWORD	AVI_mciStatus(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_STATUS_PARMSA lpParms)
-{
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    DWORD		ret = 0;
+    dwRet = 0;
+cleanUp:
+    if (wma->lpWaveFormat) {
+	HeapFree(GetProcessHeap(), 0, waveHdr);
 
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
-    
-    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
-    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
-    
-    if (dwFlags & MCI_STATUS_ITEM) {
-	switch (lpParms->dwItem) {
-	case MCI_STATUS_CURRENT_TRACK:
-	    lpParms->dwReturn = 1;
-	    TRACE("MCI_STATUS_CURRENT_TRACK => %lu\n", lpParms->dwReturn);
-	    break;
-	case MCI_STATUS_LENGTH:
-	    if (dwFlags & MCI_TRACK) {
-		/* lpParms->dwTrack contains track # */
-		lpParms->dwReturn = 0x1234;
-	    } else {
-		lpParms->dwReturn = 0x4321;
-	    }
-	    TRACE("MCI_STATUS_LENGTH => %lu\n", lpParms->dwReturn);
-	    break;
-	case MCI_STATUS_MODE:
- 	    lpParms->dwReturn = MAKEMCIRESOURCE(wma->wStatus, wma->wStatus);
-	    ret = MCI_RESOURCE_RETURNED;
-	    TRACE("MCI_STATUS_MODE => %u\n", LOWORD(lpParms->dwReturn));
-	    break;
-	case MCI_STATUS_MEDIA_PRESENT:
-	    TRACE("MCI_STATUS_MEDIA_PRESENT => TRUE\n");
-	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	case MCI_STATUS_NUMBER_OF_TRACKS:
-	    lpParms->dwReturn = 3;
-	    TRACE("MCI_STATUS_NUMBER_OF_TRACKS => %lu\n", lpParms->dwReturn);
-	    break;
-	case MCI_STATUS_POSITION:
-	    /* FIXME: do I need to use MCI_TRACK ? */
-	    lpParms->dwReturn = 0x0123;
-	    TRACE("MCI_STATUS_POSITION %s => %lu\n", 
-		  (dwFlags & MCI_STATUS_START) ? "start" : "current", lpParms->dwReturn);
-	    break;
-	case MCI_STATUS_READY:
-	    lpParms->dwReturn = (wma->wStatus == MCI_MODE_NOT_READY) ?
-		MAKEMCIRESOURCE(FALSE, MCI_FALSE) : MAKEMCIRESOURCE(TRUE, MCI_TRUE);
-	    ret = MCI_RESOURCE_RETURNED;
-	    TRACE("MCI_STATUS_READY = %u\n", LOWORD(lpParms->dwReturn));
-	    break;
-	case MCI_STATUS_TIME_FORMAT:
-	    lpParms->dwReturn = MAKEMCIRESOURCE(wma->dwTimeFormat, wma->dwTimeFormat);
-	    TRACE("MCI_STATUS_TIME_FORMAT => %u\n", LOWORD(lpParms->dwReturn));
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	default:
-	    FIXME("Unknowm command %08lX !\n", lpParms->dwItem);
-	    return MCIERR_UNRECOGNIZED_COMMAND;
+	if (wma->hWave) {
+	    waveOutClose(wma->hWave);
+	    wma->hWave = 0;
 	}
-    } else {
-	WARN("No Status-Item!\n");
-	return MCIERR_UNRECOGNIZED_COMMAND;
+	CloseHandle(wma->hEvent);
     }
-    if (dwFlags & MCI_NOTIFY) {
+
+    if (lpParms && (dwFlags & MCI_NOTIFY)) {
 	TRACE("MCI_NOTIFY_SUCCESSFUL %08lX !\n", lpParms->dwCallback);
 	mciDriverNotify((HWND)LOWORD(lpParms->dwCallback),
-			  wma->wNotifyDeviceID, MCI_NOTIFY_SUCCESSFUL);
+			wma->openParms.wDeviceID, MCI_NOTIFY_SUCCESSFUL);
     }
     
-    return ret;
+    wma->dwStatus = MCI_MODE_STOP;
+    
+    return dwRet;
 }
 
 /***************************************************************************
- * 				AVI_mciGetDevCaps			[internal]
+ * 				MCIAVI_mciRecord			[internal]
  */
-static	DWORD	AVI_mciGetDevCaps(UINT16 wDevID, DWORD dwFlags,  LPMCI_GETDEVCAPS_PARMS lpParms)
+static	DWORD	MCIAVI_mciRecord(UINT wDevID, DWORD dwFlags, LPMCI_DGV_RECORD_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    DWORD		ret;
-
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    if (lpParms == NULL) 	return MCIERR_NULL_PARAMETER_BLOCK;
+    FIXME("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
+    
+    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
     
-    if (dwFlags & MCI_GETDEVCAPS_ITEM) {
-	switch (lpParms->dwItem) {
-	case MCI_GETDEVCAPS_DEVICE_TYPE:
-	    TRACE("MCI_GETDEVCAPS_DEVICE_TYPE !\n");
-	    lpParms->dwReturn = MAKEMCIRESOURCE(MCI_DEVTYPE_DIGITAL_VIDEO, MCI_DEVTYPE_DIGITAL_VIDEO);
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	case MCI_GETDEVCAPS_HAS_AUDIO:
-	    TRACE("MCI_GETDEVCAPS_HAS_AUDIO !\n");
-	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	case MCI_GETDEVCAPS_HAS_VIDEO:
-	    TRACE("MCI_GETDEVCAPS_HAS_VIDEO !\n");
-	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	case MCI_GETDEVCAPS_USES_FILES:
-	    TRACE("MCI_GETDEVCAPS_USES_FILES !\n");
-	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	case MCI_GETDEVCAPS_COMPOUND_DEVICE:
-	    TRACE("MCI_GETDEVCAPS_COMPOUND_DEVICE !\n");
-	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	case MCI_GETDEVCAPS_CAN_EJECT:
-	    TRACE("MCI_GETDEVCAPS_CAN_EJECT !\n");
-	    lpParms->dwReturn = MAKEMCIRESOURCE(FALSE, MCI_FALSE);
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	case MCI_GETDEVCAPS_CAN_PLAY:
-	    TRACE("MCI_GETDEVCAPS_CAN_PLAY !\n");
-	    lpParms->dwReturn = MAKEMCIRESOURCE(TRUE, MCI_TRUE);
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	case MCI_GETDEVCAPS_CAN_RECORD:
-	    TRACE("MCI_GETDEVCAPS_CAN_RECORD !\n");
-	    lpParms->dwReturn = MAKEMCIRESOURCE(FALSE, MCI_FALSE);
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	case MCI_GETDEVCAPS_CAN_SAVE:
-	    TRACE("MCI_GETDEVCAPS_CAN_SAVE !\n");
-	    lpParms->dwReturn = MAKEMCIRESOURCE(FALSE, MCI_FALSE);
-	    ret = MCI_RESOURCE_RETURNED;
-	    break;
-	default:
-	    FIXME("Unknown capability (%08lx) !\n", lpParms->dwItem);
-	    return MCIERR_UNRECOGNIZED_COMMAND;
-	}
-    } else {
-	WARN("No GetDevCaps-Item !\n");
-	return MCIERR_UNRECOGNIZED_COMMAND;
-    }
-    return ret;
+    wma->dwStatus = MCI_MODE_RECORD;
+    return 0;
 }
 
 /***************************************************************************
- * 				AVI_mciInfo			[internal]
+ * 				MCIAVI_mciStop			[internal]
  */
-static	DWORD	AVI_mciInfo(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_INFO_PARMSA lpParms)
+static	DWORD	MCIAVI_mciStop(UINT wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
 {
-    LPSTR		str = 0;
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    DWORD		ret = 0;
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+    DWORD		dwRet = 0;
 
-    TRACE("(%04X, %08lX, %p) : stub;\n", wDevID, dwFlags, lpParms);
+    TRACE("(%04x, %08lX, %p)\n", wDevID, dwFlags, lpParms);
     
-    if (lpParms == NULL || lpParms->lpstrReturn == NULL)
-	return MCIERR_NULL_PARAMETER_BLOCK;
-    if (wma == NULL) return MCIERR_INVALID_DEVICE_ID;
-
-    TRACE("buf=%p, len=%lu\n", lpParms->lpstrReturn, lpParms->dwRetSize);
+    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
+    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
     
-    switch (dwFlags) {
-    case MCI_INFO_PRODUCT:
-	str = "Wine's AVI player";
-	break;
-    case MCI_INFO_FILE:
-	str = "";
-	break;
-#if 0
-	/* FIXME: the following manifest constants are not defined in <WINE>/include/mmsystem.h */
-    case MCI_INFO_COPYRIGHT:
-	break;
-    case MCI_INFO_NAME:
+    switch (wma->dwStatus) {
+    case MCI_MODE_PAUSE:
+    case MCI_MODE_PLAY:
+    case MCI_MODE_RECORD:
+	{
+	    int oldStat = wma->dwStatus;
+	    wma->dwStatus = MCI_MODE_NOT_READY;
+	    if (oldStat == MCI_MODE_PAUSE)
+		dwRet = waveOutReset(wma->hWave);
+	}
+	while (wma->dwStatus != MCI_MODE_STOP)
+	    Sleep(10);
 	break;
-#endif
     default:
-	WARN("Don't know this info command (%lu)\n", dwFlags);
-	return MCIERR_UNRECOGNIZED_COMMAND;
+	wma->dwStatus = MCI_MODE_STOP;
+	break;
     }
-    if (str) {
-	if (lpParms->dwRetSize <= strlen(str)) {
-	    lstrcpynA(lpParms->lpstrReturn, str, lpParms->dwRetSize - 1);
-	    ret = MCIERR_PARAM_OVERFLOW;
-	} else {
-	    strcpy(lpParms->lpstrReturn, str);
-	}	
-    } else {
-	*lpParms->lpstrReturn = 0;
+    
+    if ((dwFlags & MCI_NOTIFY) && lpParms) {
+	mciDriverNotify((HWND)LOWORD(lpParms->dwCallback), 
+			wma->openParms.wDeviceID, MCI_NOTIFY_SUCCESSFUL);
     }
-    return ret;
+    
+    return dwRet;
 }
 
 /***************************************************************************
- * 				AVI_mciPut			[internal]
+ * 				MCIAVI_mciPause			[internal]
  */
-static	DWORD	AVI_mciPut(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_PUT_PARMS lpParms)
+static	DWORD	MCIAVI_mciPause(UINT wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    RECT		rc;
-    char		buffer[256];
-    
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
     
-    if (dwFlags & MCI_DGV_RECT) {
-	rc = lpParms->rc;
-    } else {
-	SetRectEmpty(&rc);
-    }
-    
-    *buffer = 0;
-    if (dwFlags & MCI_DGV_PUT_CLIENT) {
-	strncat(buffer, "PUT_CLIENT", sizeof(buffer));
-    }
-    if (dwFlags & MCI_DGV_PUT_DESTINATION) {
-	strncat(buffer, "PUT_DESTINATION", sizeof(buffer));
-    }
-    if (dwFlags & MCI_DGV_PUT_FRAME) {
-	strncat(buffer, "PUT_FRAME", sizeof(buffer));
-    }
-    if (dwFlags & MCI_DGV_PUT_SOURCE) {
-	strncat(buffer, "PUT_SOURCE", sizeof(buffer));
-    }
-    if (dwFlags & MCI_DGV_PUT_VIDEO) {
-	strncat(buffer, "PUT_VIDEO", sizeof(buffer));
-    }
-    if (dwFlags & MCI_DGV_PUT_WINDOW) {
-	strncat(buffer, "PUT_WINDOW", sizeof(buffer));
-    }
-    TRACE("%s (%d,%d,%d,%d)\n", buffer, rc.left, rc.top, rc.right, rc.bottom);
-    
-    return 0;
+    if (wma->dwStatus == MCI_MODE_PLAY)
+	wma->dwStatus = MCI_MODE_PAUSE;
+
+    return (wma->lpWaveFormat) ? waveOutPause(wma->hWave) : 0;
 }
 
 /***************************************************************************
- * 				AVI_mciWindow			[internal]
+ * 				MCIAVI_mciResume			[internal]
  */
-static	DWORD	AVI_mciWindow(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_WINDOW_PARMSA lpParms)
+static	DWORD	MCIAVI_mciResume(UINT wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
     
-    if (dwFlags & MCI_DGV_WINDOW_HWND) {
-	TRACE("Setting hWnd to %08lx\n", (DWORD)lpParms->hWnd);
-    }
-    if (dwFlags & MCI_DGV_WINDOW_STATE) {
-	TRACE("Setting nCmdShow to %d\n", lpParms->nCmdShow);
-    }
-    if (dwFlags & MCI_DGV_WINDOW_TEXT) {
-	TRACE("Setting caption to '%s'\n", lpParms->lpstrText);
-    }
-    
-    return 0;
+    if (wma->dwStatus == MCI_MODE_PAUSE)
+	wma->dwStatus = MCI_MODE_PLAY;
+
+    return (wma->lpWaveFormat) ? waveOutRestart(wma->hWave) : 0;
 }
 
-/*****************************************************************************
- * 				AVI_mciLoad			[internal]
+/***************************************************************************
+ * 				MCIAVI_mciSeek			[internal]
  */
-static DWORD	AVI_mciLoad(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_LOAD_PARMSA lpParms)
+static	DWORD	MCIAVI_mciSeek(UINT wDevID, DWORD dwFlags, LPMCI_SEEK_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    TRACE("(%04x, %08lX, %p)\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
     
+    EnterCriticalSection(&wma->cs);
+    
+    MCIAVI_mciStop(wDevID, MCI_WAIT, 0);
+	
+    if (dwFlags & MCI_SEEK_TO_START) {
+	wma->dwCurrVideoFrame = 0;
+    } else if (dwFlags & MCI_SEEK_TO_END) {
+	wma->dwCurrVideoFrame = wma->dwPlayableVideoFrames - 1;
+    } else if (dwFlags & MCI_TO) {
+	wma->dwCurrVideoFrame = MCIAVI_ConvertTimeFormatToFrame(wma, lpParms->dwTo);
+    } else {
+	WARN("dwFlag doesn't tell where to seek to...\n");
+	return MCIERR_MISSING_PARAMETER;
+    }
+	
+    TRACE("Seeking to frame=%lu bytes\n", wma->dwCurrVideoFrame);
+	
+    if (dwFlags & MCI_NOTIFY) {
+	mciDriverNotify((HWND)LOWORD(lpParms->dwCallback), 
+			wma->openParms.wDeviceID, MCI_NOTIFY_SUCCESSFUL);
+    }
+
+    LeaveCriticalSection(&wma->cs);
+
     return 0;
 }
 
-/******************************************************************************
- * 				AVI_mciSave			[internal]
+/*****************************************************************************
+ * 				MCIAVI_mciLoad			[internal]
  */
-static	DWORD	AVI_mciSave(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_SAVE_PARMSA lpParms)
+static DWORD	MCIAVI_mciLoad(UINT wDevID, DWORD dwFlags, LPMCI_DGV_LOAD_PARMSA lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -645,13 +580,13 @@ static	DWORD	AVI_mciSave(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_SAVE_PARMSA lpP
 }
 
 /******************************************************************************
- * 				AVI_mciFreeze			[internal]
+ * 				MCIAVI_mciSave			[internal]
  */
-static	DWORD	AVI_mciFreeze(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RECT_PARMS lpParms)
+static	DWORD	MCIAVI_mciSave(UINT wDevID, DWORD dwFlags, LPMCI_DGV_SAVE_PARMSA lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -660,13 +595,13 @@ static	DWORD	AVI_mciFreeze(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RECT_PARMS lp
 }
 
 /******************************************************************************
- * 				AVI_mciRealize			[internal]
+ * 				MCIAVI_mciFreeze			[internal]
  */
-static	DWORD	AVI_mciRealize(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
+static	DWORD	MCIAVI_mciFreeze(UINT wDevID, DWORD dwFlags, LPMCI_DGV_RECT_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -675,13 +610,13 @@ static	DWORD	AVI_mciRealize(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lp
 }
 
 /******************************************************************************
- * 				AVI_mciUnFreeze			[internal]
+ * 				MCIAVI_mciRealize			[internal]
  */
-static	DWORD	AVI_mciUnFreeze(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RECT_PARMS lpParms)
+static	DWORD	MCIAVI_mciRealize(UINT wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -690,13 +625,13 @@ static	DWORD	AVI_mciUnFreeze(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RECT_PARMS
 }
 
 /******************************************************************************
- * 				AVI_mciUpdate			[internal]
+ * 				MCIAVI_mciUnFreeze			[internal]
  */
-static	DWORD	AVI_mciUpdate(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_UPDATE_PARMS lpParms)
+static	DWORD	MCIAVI_mciUnFreeze(UINT wDevID, DWORD dwFlags, LPMCI_DGV_RECT_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -705,13 +640,13 @@ static	DWORD	AVI_mciUpdate(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_UPDATE_PARMS
 }
 
 /******************************************************************************
- * 				AVI_mciWhere			[internal]
+ * 				MCIAVI_mciUpdate			[internal]
  */
-static	DWORD	AVI_mciWhere(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RECT_PARMS lpParms)
+static	DWORD	MCIAVI_mciUpdate(UINT wDevID, DWORD dwFlags, LPMCI_DGV_UPDATE_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
-    
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -720,13 +655,13 @@ static	DWORD	AVI_mciWhere(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RECT_PARMS lpP
 }
 
 /******************************************************************************
- * 				AVI_mciStep			[internal]
+ * 				MCIAVI_mciStep			[internal]
  */
-static	DWORD	AVI_mciStep(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_STEP_PARMS lpParms)
+static	DWORD	MCIAVI_mciStep(UINT wDevID, DWORD dwFlags, LPMCI_DGV_STEP_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -735,13 +670,13 @@ static	DWORD	AVI_mciStep(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_STEP_PARMS lpPa
 }
 
 /******************************************************************************
- * 				AVI_mciCopy			[internal]
+ * 				MCIAVI_mciCopy			[internal]
  */
-static	DWORD	AVI_mciCopy(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_COPY_PARMS lpParms)
+static	DWORD	MCIAVI_mciCopy(UINT wDevID, DWORD dwFlags, LPMCI_DGV_COPY_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -750,13 +685,13 @@ static	DWORD	AVI_mciCopy(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_COPY_PARMS lpPa
 }
 
 /******************************************************************************
- * 				AVI_mciCut			[internal]
+ * 				MCIAVI_mciCut			[internal]
  */
-static	DWORD	AVI_mciCut(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_CUT_PARMS lpParms)
+static	DWORD	MCIAVI_mciCut(UINT wDevID, DWORD dwFlags, LPMCI_DGV_CUT_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -765,13 +700,13 @@ static	DWORD	AVI_mciCut(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_CUT_PARMS lpParm
 }
 
 /******************************************************************************
- * 				AVI_mciDelete			[internal]
+ * 				MCIAVI_mciDelete			[internal]
  */
-static	DWORD	AVI_mciDelete(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_DELETE_PARMS lpParms)
+static	DWORD	MCIAVI_mciDelete(UINT wDevID, DWORD dwFlags, LPMCI_DGV_DELETE_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -780,13 +715,13 @@ static	DWORD	AVI_mciDelete(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_DELETE_PARMS
 }
 
 /******************************************************************************
- * 				AVI_mciPaste			[internal]
+ * 				MCIAVI_mciPaste			[internal]
  */
-static	DWORD	AVI_mciPaste(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_PASTE_PARMS lpParms)
+static	DWORD	MCIAVI_mciPaste(UINT wDevID, DWORD dwFlags, LPMCI_DGV_PASTE_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -795,13 +730,13 @@ static	DWORD	AVI_mciPaste(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_PASTE_PARMS lp
 }
 
 /******************************************************************************
- * 				AVI_mciCue			[internal]
+ * 				MCIAVI_mciCue			[internal]
  */
-static	DWORD	AVI_mciCue(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_CUE_PARMS lpParms)
+static	DWORD	MCIAVI_mciCue(UINT wDevID, DWORD dwFlags, LPMCI_DGV_CUE_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -810,13 +745,13 @@ static	DWORD	AVI_mciCue(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_CUE_PARMS lpParm
 }
 
 /******************************************************************************
- * 				AVI_mciCapture			[internal]
+ * 				MCIAVI_mciCapture			[internal]
  */
-static	DWORD	AVI_mciCapture(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_CAPTURE_PARMSA lpParms)
+static	DWORD	MCIAVI_mciCapture(UINT wDevID, DWORD dwFlags, LPMCI_DGV_CAPTURE_PARMSA lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -825,13 +760,13 @@ static	DWORD	AVI_mciCapture(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_CAPTURE_PARM
 }
 
 /******************************************************************************
- * 				AVI_mciMonitor			[internal]
+ * 				MCIAVI_mciMonitor			[internal]
  */
-static	DWORD	AVI_mciMonitor(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_MONITOR_PARMS lpParms)
+static	DWORD	MCIAVI_mciMonitor(UINT wDevID, DWORD dwFlags, LPMCI_DGV_MONITOR_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -840,13 +775,13 @@ static	DWORD	AVI_mciMonitor(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_MONITOR_PARM
 }
 
 /******************************************************************************
- * 				AVI_mciReserve			[internal]
+ * 				MCIAVI_mciReserve			[internal]
  */
-static	DWORD	AVI_mciReserve(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RESERVE_PARMSA lpParms)
+static	DWORD	MCIAVI_mciReserve(UINT wDevID, DWORD dwFlags, LPMCI_DGV_RESERVE_PARMSA lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -855,13 +790,13 @@ static	DWORD	AVI_mciReserve(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RESERVE_PARM
 }
 
 /******************************************************************************
- * 				AVI_mciSetAudio			[internal]
+ * 				MCIAVI_mciSetAudio			[internal]
  */
-static	DWORD	AVI_mciSetAudio(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_SETAUDIO_PARMSA lpParms)
+static	DWORD	MCIAVI_mciSetAudio(UINT wDevID, DWORD dwFlags, LPMCI_DGV_SETAUDIO_PARMSA lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -870,13 +805,13 @@ static	DWORD	AVI_mciSetAudio(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_SETAUDIO_PA
 }
 
 /******************************************************************************
- * 				AVI_mciSignal			[internal]
+ * 				MCIAVI_mciSignal			[internal]
  */
-static	DWORD	AVI_mciSignal(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_SIGNAL_PARMS lpParms)
+static	DWORD	MCIAVI_mciSignal(UINT wDevID, DWORD dwFlags, LPMCI_DGV_SIGNAL_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -885,13 +820,13 @@ static	DWORD	AVI_mciSignal(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_SIGNAL_PARMS
 }
 
 /******************************************************************************
- * 				AVI_mciSetVideo			[internal]
+ * 				MCIAVI_mciSetVideo			[internal]
  */
-static	DWORD	AVI_mciSetVideo(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_SETVIDEO_PARMSA lpParms)
+static	DWORD	MCIAVI_mciSetVideo(UINT wDevID, DWORD dwFlags, LPMCI_DGV_SETVIDEO_PARMSA lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -900,13 +835,13 @@ static	DWORD	AVI_mciSetVideo(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_SETVIDEO_PA
 }
 
 /******************************************************************************
- * 				AVI_mciQuality			[internal]
+ * 				MCIAVI_mciQuality			[internal]
  */
-static	DWORD	AVI_mciQuality(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_QUALITY_PARMSA lpParms)
+static	DWORD	MCIAVI_mciQuality(UINT wDevID, DWORD dwFlags, LPMCI_DGV_QUALITY_PARMSA lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -915,13 +850,13 @@ static	DWORD	AVI_mciQuality(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_QUALITY_PARM
 }
 
 /******************************************************************************
- * 				AVI_mciList			[internal]
+ * 				MCIAVI_mciList			[internal]
  */
-static	DWORD	AVI_mciList(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_LIST_PARMSA lpParms)
+static	DWORD	MCIAVI_mciList(UINT wDevID, DWORD dwFlags, LPMCI_DGV_LIST_PARMSA lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -930,13 +865,13 @@ static	DWORD	AVI_mciList(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_LIST_PARMSA lpP
 }
 
 /******************************************************************************
- * 				AVI_mciUndo			[internal]
+ * 				MCIAVI_mciUndo			[internal]
  */
-static	DWORD	AVI_mciUndo(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
+static	DWORD	MCIAVI_mciUndo(UINT wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -945,13 +880,13 @@ static	DWORD	AVI_mciUndo(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpPar
 }
 
 /******************************************************************************
- * 				AVI_mciConfigure			[internal]
+ * 				MCIAVI_mciConfigure			[internal]
  */
-static	DWORD	AVI_mciConfigure(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
+static	DWORD	MCIAVI_mciConfigure(UINT wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -960,13 +895,13 @@ static	DWORD	AVI_mciConfigure(UINT16 wDevID, DWORD dwFlags, LPMCI_GENERIC_PARMS
 }
 
 /******************************************************************************
- * 				AVI_mciRestore			[internal]
+ * 				MCIAVI_mciRestore			[internal]
  */
-static	DWORD	AVI_mciRestore(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RESTORE_PARMSA lpParms)
+static	DWORD	MCIAVI_mciRestore(UINT wDevID, DWORD dwFlags, LPMCI_DGV_RESTORE_PARMSA lpParms)
 {
-    WINE_MCIAVI*	wma = AVI_mciGetOpenDev(wDevID);
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
     
-    TRACE("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
+    FIXME("(%04x, %08lx, %p) : stub\n", wDevID, dwFlags, lpParms);
     
     if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
     if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
@@ -984,57 +919,60 @@ static	DWORD	AVI_mciRestore(UINT16 wDevID, DWORD dwFlags, LPMCI_DGV_RESTORE_PARM
 LONG CALLBACK	MCIAVI_DriverProc(DWORD dwDevID, HDRVR hDriv, DWORD wMsg, 
 				  DWORD dwParam1, DWORD dwParam2)
 {
+    TRACE("(%08lX, %04X, %08lX, %08lX, %08lX)\n", 
+	  dwDevID, hDriv, wMsg, dwParam1, dwParam2);
+    
     switch (wMsg) {
     case DRV_LOAD:		return 1;
     case DRV_FREE:		return 1;
-    case DRV_OPEN:		return AVI_drvOpen((LPSTR)dwParam1, (LPMCI_OPEN_DRIVER_PARMSA)dwParam2);
-    case DRV_CLOSE:		return AVI_drvClose(dwDevID);
+    case DRV_OPEN:		return MCIAVI_drvOpen((LPSTR)dwParam1, (LPMCI_OPEN_DRIVER_PARMSA)dwParam2);
+    case DRV_CLOSE:		return MCIAVI_drvClose(dwDevID);
     case DRV_ENABLE:		return 1;
     case DRV_DISABLE:		return 1;
     case DRV_QUERYCONFIGURE:	return 1;
-    case DRV_CONFIGURE:		MessageBoxA(0, "Sample AVI Wine Driver !", "MM-Wine Driver", MB_OK); return 1;
+    case DRV_CONFIGURE:		return MCIAVI_drvConfigure(dwDevID);
     case DRV_INSTALL:		return DRVCNF_RESTART;
     case DRV_REMOVE:		return DRVCNF_RESTART;
 	
-    case MCI_OPEN_DRIVER:	return AVI_mciOpen      (dwDevID, dwParam1, (LPMCI_DGV_OPEN_PARMSA)     dwParam2);
-    case MCI_CLOSE_DRIVER:	return AVI_mciClose     (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
-    case MCI_PLAY:		return AVI_mciPlay      (dwDevID, dwParam1, (LPMCI_PLAY_PARMS)          dwParam2);
-    case MCI_RECORD:		return AVI_mciRecord    (dwDevID, dwParam1, (LPMCI_DGV_RECORD_PARMS)    dwParam2);
-    case MCI_STOP:		return AVI_mciStop      (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
-    case MCI_SET:		return AVI_mciSet       (dwDevID, dwParam1, (LPMCI_DGV_SET_PARMS)       dwParam2);
-    case MCI_PAUSE:		return AVI_mciPause     (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
-    case MCI_RESUME:		return AVI_mciResume    (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
-    case MCI_STATUS:		return AVI_mciStatus    (dwDevID, dwParam1, (LPMCI_DGV_STATUS_PARMSA)   dwParam2);
-    case MCI_GETDEVCAPS:	return AVI_mciGetDevCaps(dwDevID, dwParam1, (LPMCI_GETDEVCAPS_PARMS)    dwParam2);
-    case MCI_INFO:		return AVI_mciInfo      (dwDevID, dwParam1, (LPMCI_DGV_INFO_PARMSA)     dwParam2);
-    case MCI_SEEK:		return AVI_mciSeek      (dwDevID, dwParam1, (LPMCI_SEEK_PARMS)          dwParam2);
-    case MCI_PUT:		return AVI_mciPut	(dwDevID, dwParam1, (LPMCI_DGV_PUT_PARMS)       dwParam2);		
-    case MCI_WINDOW:		return AVI_mciWindow	(dwDevID, dwParam1, (LPMCI_DGV_WINDOW_PARMSA)   dwParam2);		
-    case MCI_LOAD:		return AVI_mciLoad      (dwDevID, dwParam1, (LPMCI_DGV_LOAD_PARMSA)     dwParam2);		
-    case MCI_SAVE:		return AVI_mciSave      (dwDevID, dwParam1, (LPMCI_DGV_SAVE_PARMSA)     dwParam2);		
-    case MCI_FREEZE:		return AVI_mciFreeze	(dwDevID, dwParam1, (LPMCI_DGV_RECT_PARMS)      dwParam2);
-    case MCI_REALIZE:		return AVI_mciRealize   (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
-    case MCI_UNFREEZE:		return AVI_mciUnFreeze  (dwDevID, dwParam1, (LPMCI_DGV_RECT_PARMS)      dwParam2);
-    case MCI_UPDATE:		return AVI_mciUpdate    (dwDevID, dwParam1, (LPMCI_DGV_UPDATE_PARMS)    dwParam2);
-    case MCI_WHERE:		return AVI_mciWhere	(dwDevID, dwParam1, (LPMCI_DGV_RECT_PARMS)      dwParam2);
-    case MCI_STEP:		return AVI_mciStep      (dwDevID, dwParam1, (LPMCI_DGV_STEP_PARMS)      dwParam2);
-    case MCI_COPY:		return AVI_mciCopy      (dwDevID, dwParam1, (LPMCI_DGV_COPY_PARMS)      dwParam2);		
-    case MCI_CUT:		return AVI_mciCut       (dwDevID, dwParam1, (LPMCI_DGV_CUT_PARMS)       dwParam2);		
-    case MCI_DELETE:		return AVI_mciDelete    (dwDevID, dwParam1, (LPMCI_DGV_DELETE_PARMS)    dwParam2);				
-    case MCI_PASTE:		return AVI_mciPaste     (dwDevID, dwParam1, (LPMCI_DGV_PASTE_PARMS)     dwParam2);				
-    case MCI_CUE:		return AVI_mciCue       (dwDevID, dwParam1, (LPMCI_DGV_CUE_PARMS)       dwParam2);
+    case MCI_OPEN_DRIVER:	return MCIAVI_mciOpen      (dwDevID, dwParam1, (LPMCI_DGV_OPEN_PARMSA)     dwParam2);
+    case MCI_CLOSE_DRIVER:	return MCIAVI_mciClose     (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
+    case MCI_PLAY:		return MCIAVI_mciPlay      (dwDevID, dwParam1, (LPMCI_PLAY_PARMS)          dwParam2);
+    case MCI_RECORD:		return MCIAVI_mciRecord    (dwDevID, dwParam1, (LPMCI_DGV_RECORD_PARMS)    dwParam2);
+    case MCI_STOP:		return MCIAVI_mciStop      (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
+    case MCI_SET:		return MCIAVI_mciSet       (dwDevID, dwParam1, (LPMCI_DGV_SET_PARMS)       dwParam2);
+    case MCI_PAUSE:		return MCIAVI_mciPause     (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
+    case MCI_RESUME:		return MCIAVI_mciResume    (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
+    case MCI_STATUS:		return MCIAVI_mciStatus    (dwDevID, dwParam1, (LPMCI_DGV_STATUS_PARMSA)   dwParam2);
+    case MCI_GETDEVCAPS:	return MCIAVI_mciGetDevCaps(dwDevID, dwParam1, (LPMCI_GETDEVCAPS_PARMS)    dwParam2);
+    case MCI_INFO:		return MCIAVI_mciInfo      (dwDevID, dwParam1, (LPMCI_DGV_INFO_PARMSA)     dwParam2);
+    case MCI_SEEK:		return MCIAVI_mciSeek      (dwDevID, dwParam1, (LPMCI_SEEK_PARMS)          dwParam2);
+    case MCI_PUT:		return MCIAVI_mciPut	   (dwDevID, dwParam1, (LPMCI_DGV_PUT_PARMS)       dwParam2);		
+    case MCI_WINDOW:		return MCIAVI_mciWindow	   (dwDevID, dwParam1, (LPMCI_DGV_WINDOW_PARMSA)   dwParam2);		
+    case MCI_LOAD:		return MCIAVI_mciLoad      (dwDevID, dwParam1, (LPMCI_DGV_LOAD_PARMSA)     dwParam2);		
+    case MCI_SAVE:		return MCIAVI_mciSave      (dwDevID, dwParam1, (LPMCI_DGV_SAVE_PARMSA)     dwParam2);		
+    case MCI_FREEZE:		return MCIAVI_mciFreeze	   (dwDevID, dwParam1, (LPMCI_DGV_RECT_PARMS)      dwParam2);
+    case MCI_REALIZE:		return MCIAVI_mciRealize   (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
+    case MCI_UNFREEZE:		return MCIAVI_mciUnFreeze  (dwDevID, dwParam1, (LPMCI_DGV_RECT_PARMS)      dwParam2);
+    case MCI_UPDATE:		return MCIAVI_mciUpdate    (dwDevID, dwParam1, (LPMCI_DGV_UPDATE_PARMS)    dwParam2);
+    case MCI_WHERE:		return MCIAVI_mciWhere	   (dwDevID, dwParam1, (LPMCI_DGV_RECT_PARMS)      dwParam2);
+    case MCI_STEP:		return MCIAVI_mciStep      (dwDevID, dwParam1, (LPMCI_DGV_STEP_PARMS)      dwParam2);
+    case MCI_COPY:		return MCIAVI_mciCopy      (dwDevID, dwParam1, (LPMCI_DGV_COPY_PARMS)      dwParam2);		
+    case MCI_CUT:		return MCIAVI_mciCut       (dwDevID, dwParam1, (LPMCI_DGV_CUT_PARMS)       dwParam2);		
+    case MCI_DELETE:		return MCIAVI_mciDelete    (dwDevID, dwParam1, (LPMCI_DGV_DELETE_PARMS)    dwParam2);				
+    case MCI_PASTE:		return MCIAVI_mciPaste     (dwDevID, dwParam1, (LPMCI_DGV_PASTE_PARMS)     dwParam2);				
+    case MCI_CUE:		return MCIAVI_mciCue       (dwDevID, dwParam1, (LPMCI_DGV_CUE_PARMS)       dwParam2);
 	/* Digital Video specific */	
-    case MCI_CAPTURE:		return AVI_mciCapture   (dwDevID, dwParam1, (LPMCI_DGV_CAPTURE_PARMSA)  dwParam2);
-    case MCI_MONITOR:		return AVI_mciMonitor   (dwDevID, dwParam1, (LPMCI_DGV_MONITOR_PARMS)   dwParam2);
-    case MCI_RESERVE:		return AVI_mciReserve   (dwDevID, dwParam1, (LPMCI_DGV_RESERVE_PARMSA)  dwParam2);
-    case MCI_SETAUDIO:		return AVI_mciSetAudio  (dwDevID, dwParam1, (LPMCI_DGV_SETAUDIO_PARMSA) dwParam2);
-    case MCI_SIGNAL:		return AVI_mciSignal    (dwDevID, dwParam1, (LPMCI_DGV_SIGNAL_PARMS)    dwParam2);
-    case MCI_SETVIDEO:		return AVI_mciSetVideo  (dwDevID, dwParam1, (LPMCI_DGV_SETVIDEO_PARMSA) dwParam2);
-    case MCI_QUALITY:		return AVI_mciQuality   (dwDevID, dwParam1, (LPMCI_DGV_QUALITY_PARMSA)  dwParam2);
-    case MCI_LIST:		return AVI_mciList      (dwDevID, dwParam1, (LPMCI_DGV_LIST_PARMSA)     dwParam2);
-    case MCI_UNDO:		return AVI_mciUndo      (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
-    case MCI_CONFIGURE:		return AVI_mciConfigure (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
-    case MCI_RESTORE:		return AVI_mciRestore   (dwDevID, dwParam1, (LPMCI_DGV_RESTORE_PARMSA)	dwParam2);
+    case MCI_CAPTURE:		return MCIAVI_mciCapture   (dwDevID, dwParam1, (LPMCI_DGV_CAPTURE_PARMSA)  dwParam2);
+    case MCI_MONITOR:		return MCIAVI_mciMonitor   (dwDevID, dwParam1, (LPMCI_DGV_MONITOR_PARMS)   dwParam2);
+    case MCI_RESERVE:		return MCIAVI_mciReserve   (dwDevID, dwParam1, (LPMCI_DGV_RESERVE_PARMSA)  dwParam2);
+    case MCI_SETAUDIO:		return MCIAVI_mciSetAudio  (dwDevID, dwParam1, (LPMCI_DGV_SETAUDIO_PARMSA) dwParam2);
+    case MCI_SIGNAL:		return MCIAVI_mciSignal    (dwDevID, dwParam1, (LPMCI_DGV_SIGNAL_PARMS)    dwParam2);
+    case MCI_SETVIDEO:		return MCIAVI_mciSetVideo  (dwDevID, dwParam1, (LPMCI_DGV_SETVIDEO_PARMSA) dwParam2);
+    case MCI_QUALITY:		return MCIAVI_mciQuality   (dwDevID, dwParam1, (LPMCI_DGV_QUALITY_PARMSA)  dwParam2);
+    case MCI_LIST:		return MCIAVI_mciList      (dwDevID, dwParam1, (LPMCI_DGV_LIST_PARMSA)     dwParam2);
+    case MCI_UNDO:		return MCIAVI_mciUndo      (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
+    case MCI_CONFIGURE:		return MCIAVI_mciConfigure (dwDevID, dwParam1, (LPMCI_GENERIC_PARMS)       dwParam2);
+    case MCI_RESTORE:		return MCIAVI_mciRestore   (dwDevID, dwParam1, (LPMCI_DGV_RESTORE_PARMSA)  dwParam2);
 	
     case MCI_SPIN:
     case MCI_ESCAPE:		
diff --git a/dlls/winmm/mciavi/mciavi.drv.spec b/dlls/winmm/mciavi/mciavi.drv.spec
index 623f9f9a68cbdddbb44d2914df9eef4083b09b24..b9178066b37d594a9f672ecb2f4bbf5cf69fb32a 100644
--- a/dlls/winmm/mciavi/mciavi.drv.spec
+++ b/dlls/winmm/mciavi/mciavi.drv.spec
@@ -1,11 +1,15 @@
 name mciavi
 file mciavi.drv
 type win32
+init MCIAVI_LibMain
+rsrc mciavi_res.res
 
+import msvfw32.dll
 import winmm.dll
 import user32.dll
+import gdi32.dll
 import kernel32.dll
-import	ntdll.dll
+import ntdll.dll
 
 debug_channels (mciavi)
 
diff --git a/dlls/winmm/mciavi/mciavi_res.rc b/dlls/winmm/mciavi/mciavi_res.rc
new file mode 100644
index 0000000000000000000000000000000000000000..befc39dac41e2338883b53c8d9b31ef3db4d2f0e
--- /dev/null
+++ b/dlls/winmm/mciavi/mciavi_res.rc
@@ -0,0 +1,550 @@
+/* MciAvi resources
+ *
+ * (c) 2000, Eric Pouech
+ *
+ */
+
+#include "mmddk.h"
+
+MCIAVI RCDATA
+BEGIN
+"play\0", 0x00000806L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"from\0", 0x00000004L, MCI_INTEGER,
+"to\0", 0x00000008L, MCI_INTEGER,
+"repeat\0", 0x00010000L, MCI_FLAG,
+"reverse\0", 0x00020000L, MCI_FLAG,
+"window\0", 0x01000000L, MCI_FLAG,
+"fullscreen by 2\0", 0x04000000L, MCI_FLAG,
+"fullscreen\0", 0x02000000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"capability\0", 0x0000080bL, MCI_COMMAND_HEAD,
+"\0", 0x00000002L, MCI_RETURN,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00000100L, MCI_CONSTANT,
+"can record\0", 0x00000001L, MCI_INTEGER,
+"has audio\0", 0x00000002L, MCI_INTEGER,
+"has video\0", 0x00000003L, MCI_INTEGER,
+"uses files\0", 0x00000005L, MCI_INTEGER,
+"compound device\0", 0x00000006L, MCI_INTEGER,
+"device type\0", 0x00000004L, MCI_INTEGER,
+"can eject\0", 0x00000007L, MCI_INTEGER,
+"can play\0", 0x00000008L, MCI_INTEGER,
+"can save\0", 0x00000009L, MCI_INTEGER,
+"can lock\0", 0x00004000L, MCI_INTEGER,
+"can reverse\0", 0x00004004L, MCI_INTEGER,
+"can stretch input\0", 0x00004008L, MCI_INTEGER,
+"can stretch\0", 0x00004001L, MCI_INTEGER,
+"can test\0", 0x00004009L, MCI_INTEGER,
+"has still\0", 0x00004005L, MCI_INTEGER,
+"can freeze\0", 0x00004002L, MCI_INTEGER,
+"uses palettes\0", 0x00004006L, MCI_INTEGER,
+"windows\0", 0x00004003L, MCI_INTEGER,
+"maximum play rate\0", 0x0000400aL, MCI_INTEGER,
+"minimum play rate\0", 0x0000400bL, MCI_INTEGER,
+"can colorkey\0", 0x00004100L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"capture\0", 0x00000870L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"as\0", 0x00010000L, MCI_STRING,
+"at\0", 0x00020000L, MCI_RECT,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"close\0", 0x00000804L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"configure\0", 0x0000087aL, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"copy\0", 0x00000852L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"from\0", 0x00000004L, MCI_INTEGER,
+"to\0", 0x00000008L, MCI_INTEGER,
+"at\0", 0x00010000L, MCI_RECT,
+"audio stream\0", 0x00020000L, MCI_INTEGER,
+"video stream\0", 0x00040000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"cue\0", 0x00000830L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"input\0", 0x00010000L, MCI_FLAG,
+"output\0", 0x00020000L, MCI_FLAG,
+"to\0", 0x00000008L, MCI_INTEGER,
+"noshow\0", 0x00040000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"cut\0", 0x00000851L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"from\0", 0x00000004L, MCI_INTEGER,
+"to\0", 0x00000008L, MCI_INTEGER,
+"at\0", 0x00010000L, MCI_RECT,
+"audio stream\0", 0x00020000L, MCI_INTEGER,
+"video stream\0", 0x00040000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"delete\0", 0x00000856L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"from\0", 0x00000004L, MCI_INTEGER,
+"to\0", 0x00000008L, MCI_INTEGER,
+"at\0", 0x00010000L, MCI_RECT,
+"audio stream\0", 0x00020000L, MCI_INTEGER,
+"video stream\0", 0x00040000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"freeze\0", 0x00000844L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"at\0", 0x00010000L, MCI_RECT,
+"outside\0", 0x00020000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"info\0", 0x0000080aL, MCI_COMMAND_HEAD,
+"\0", 0x00000001L, MCI_RETURN,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"file\0", 0x00000200L, MCI_FLAG,
+"product\0", 0x00000100L, MCI_FLAG,
+"window text\0", 0x00010000L, MCI_FLAG,
+"usage\0", 0x00004000L, MCI_FLAG,
+"version\0", 0x00000400L, MCI_FLAG,
+"\0", 0x00020000L, MCI_CONSTANT,
+"audio algorithm\0", 0x00004004L, MCI_INTEGER,
+"audio quality\0", 0x00004001L, MCI_INTEGER,
+"still algorithm\0", 0x00004005L, MCI_INTEGER,
+"still quality\0", 0x00004002L, MCI_INTEGER,
+"video algorithm\0", 0x00004006L, MCI_INTEGER,
+"video quality\0", 0x00004003L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"list\0", 0x00000878L, MCI_COMMAND_HEAD,
+"\0", 0x00000001L, MCI_RETURN,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"count\0", 0x00020000L, MCI_FLAG,
+"number\0", 0x00040000L, MCI_INTEGER,
+"\0", 0x00010000L, MCI_CONSTANT,
+"audio algorithm\0", 0x00004000L, MCI_INTEGER,
+"audio quality\0", 0x00004001L, MCI_INTEGER,
+"audio stream\0", 0x00004002L, MCI_INTEGER,
+"still algorithm\0", 0x00004003L, MCI_INTEGER,
+"still quality\0", 0x00004004L, MCI_INTEGER,
+"video algorithm\0", 0x00004005L, MCI_INTEGER,
+"video quality\0", 0x00004006L, MCI_INTEGER,
+"video source\0", 0x00004008L, MCI_INTEGER,
+"video stream\0", 0x00004007L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"algorithm\0", 0x00080000L, MCI_STRING,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"load\0", 0x00000850L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00000100L, MCI_STRING,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"monitor\0", 0x00000871L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00020000L, MCI_CONSTANT,
+"input\0", 0x00004000L, MCI_INTEGER,
+"file\0", 0x00004001L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"method\0", 0x00010000L, MCI_CONSTANT,
+"pre\0", 0x0000a000L, MCI_INTEGER,
+"post\0", 0x0000a001L, MCI_INTEGER,
+"direct\0", 0x0000a002L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"open\0", 0x00000803L, MCI_COMMAND_HEAD,
+"\0", 0x00000002L, MCI_RETURN,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"type\0", 0x00002000L, MCI_STRING,
+"element\0", 0x00000200L, MCI_STRING,
+"alias\0", 0x00000400L, MCI_STRING,
+"shareable\0", 0x00000100L, MCI_FLAG,
+"style\0", 0x00010000L, MCI_CONSTANT,
+"overlapped\0", 0x00cf0000L, MCI_INTEGER,
+"popup\0", 0x80880000L, MCI_INTEGER,
+"child\0", 0x40000000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"parent\0", 0x00020000L, MCI_INTEGER,
+"nostatic\0", 0x00040000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"paste\0", 0x00000853L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"to\0", 0x00000008L, MCI_INTEGER,
+"at\0", 0x00010000L, MCI_RECT,
+"insert\0", 0x00080000L, MCI_FLAG,
+"overwrite\0", 0x00100000L, MCI_FLAG,
+"audio stream\0", 0x00020000L, MCI_INTEGER,
+"video stream\0", 0x00040000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"pause\0", 0x00000809L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"put\0", 0x00000842L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"at\0", 0x00010000L, MCI_RECT,
+"source\0", 0x00020000L, MCI_FLAG,
+"destination\0", 0x00040000L, MCI_FLAG,
+"frame\0", 0x00080000L, MCI_FLAG,
+"video\0", 0x00100000L, MCI_FLAG,
+"window\0", 0x00200000L, MCI_FLAG,
+"client\0", 0x00400000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"quality\0", 0x00000877L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00010000L, MCI_CONSTANT,
+"audio\0", 0x00004000L, MCI_INTEGER,
+"still\0", 0x00004001L, MCI_INTEGER,
+"video\0", 0x00004002L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"name\0", 0x00020000L, MCI_STRING,
+"algorithm\0", 0x00040000L, MCI_STRING,
+"dialog\0", 0x00080000L, MCI_FLAG,
+"handle\0", 0x00100000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"realize\0", 0x00000840L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"normal\0", 0x00010000L, MCI_FLAG,
+"background\0", 0x00020000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"record\0", 0x0000080fL, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"from\0", 0x00000004L, MCI_INTEGER,
+"to\0", 0x00000008L, MCI_INTEGER,
+"insert\0", 0x00000100L, MCI_FLAG,
+"overwrite\0", 0x00000200L, MCI_FLAG,
+"at\0", 0x00010000L, MCI_RECT,
+"hold\0", 0x00020000L, MCI_FLAG,
+"audio stream\0", 0x00040000L, MCI_INTEGER,
+"video stream\0", 0x00080000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"reserve\0", 0x00000872L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"in\0", 0x00010000L, MCI_STRING,
+"size\0", 0x00020000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"restore\0", 0x0000087bL, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"from\0", 0x00010000L, MCI_STRING,
+"at\0", 0x00020000L, MCI_RECT,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"resume\0", 0x00000855L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"save\0", 0x00000813L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00000100L, MCI_STRING,
+"at\0", 0x00010000L, MCI_RECT,
+"abort\0", 0x00020000L, MCI_FLAG,
+"keepreserve\0", 0x00040000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"seek\0", 0x00000807L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"to start\0", 0x00000100L, MCI_FLAG,
+"to end\0", 0x00000200L, MCI_FLAG,
+"to\0", 0x00000008L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"set\0", 0x0000080dL, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"time format\0", 0x00000400L, MCI_CONSTANT,
+"frames\0", 0x00000003L, MCI_INTEGER,
+"milliseconds\0", 0x00000000L, MCI_INTEGER,
+"ms\0", 0x00000000L, MCI_INTEGER,
+"bytes\0", 0x00000008L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"door open\0", 0x00000100L, MCI_FLAG,
+"door closed\0", 0x00000200L, MCI_FLAG,
+"audio\0", 0x00000800L, MCI_CONSTANT,
+"all\0", 0x00000000L, MCI_INTEGER,
+"left\0", 0x00000001L, MCI_INTEGER,
+"right\0", 0x00000002L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"video\0", 0x00001000L, MCI_FLAG,
+"seek exactly\0", 0x00010000L, MCI_FLAG,
+"file format\0", 0x00080000L, MCI_CONSTANT,
+"avss\0", 0x00004000L, MCI_INTEGER,
+"avi\0", 0x00004001L, MCI_INTEGER,
+"dib\0", 0x00004002L, MCI_INTEGER,
+"rdib\0", 0x00004003L, MCI_INTEGER,
+"jpeg\0", 0x00004004L, MCI_INTEGER,
+"rjpeg\0", 0x00004005L, MCI_INTEGER,
+"jfif\0", 0x00004006L, MCI_INTEGER,
+"mpeg\0", 0x00004007L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"still\0", 0x00040000L, MCI_FLAG,
+"on\0", 0x00002000L, MCI_FLAG,
+"off\0", 0x00004000L, MCI_FLAG,
+"speed\0", 0x00020000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"setaudio\0", 0x00000873L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00800000L, MCI_CONSTANT,
+"bass\0", 0x00004001L, MCI_INTEGER,
+"treble\0", 0x00004000L, MCI_INTEGER,
+"volume\0", 0x00004002L, MCI_INTEGER,
+"stream\0", 0x00004003L, MCI_INTEGER,
+"source\0", 0x00004004L, MCI_INTEGER,
+"samplespersec\0", 0x00004005L, MCI_INTEGER,
+"bytespersec\0", 0x00004006L, MCI_INTEGER,
+"alignment\0", 0x00004007L, MCI_INTEGER,
+"bitspersample\0", 0x00004008L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"to\0", 0x01000000L, MCI_CONSTANT,
+"left\0", 0x00000001L, MCI_INTEGER,
+"right\0", 0x00000002L, MCI_INTEGER,
+"average\0", 0x00004000L, MCI_INTEGER,
+"stereo\0", 0x00000000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"over\0", 0x00010000L, MCI_INTEGER,
+"algorithm\0", 0x00040000L, MCI_STRING,
+"quality\0", 0x00080000L, MCI_STRING,
+"record\0", 0x00100000L, MCI_FLAG,
+"left\0", 0x00200000L, MCI_FLAG,
+"clocktime\0", 0x00020000L, MCI_FLAG,
+"right\0", 0x00400000L, MCI_FLAG,
+"on\0", 0x00002000L, MCI_FLAG,
+"off\0", 0x00004000L, MCI_FLAG,
+"input\0", 0x02000000L, MCI_FLAG,
+"output\0", 0x04000000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"setvideo\0", 0x00000876L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00100000L, MCI_CONSTANT,
+"frame rate\0", 0x00004008L, MCI_INTEGER,
+"brightness\0", 0x00004000L, MCI_INTEGER,
+"color\0", 0x00004001L, MCI_INTEGER,
+"contrast\0", 0x00004002L, MCI_INTEGER,
+"tint\0", 0x00004003L, MCI_INTEGER,
+"sharpness\0", 0x00004004L, MCI_INTEGER,
+"gamma\0", 0x00004005L, MCI_INTEGER,
+"palette handle\0", 0x00004007L, MCI_INTEGER,
+"stream\0", 0x00004006L, MCI_INTEGER,
+"source\0", 0x00004009L, MCI_INTEGER,
+"key index\0", 0x0000400aL, MCI_INTEGER,
+"key color\0", 0x0000400bL, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"to\0", 0x01000000L, MCI_CONSTANT,
+"ntsc\0", 0x00004000L, MCI_INTEGER,
+"rgb\0", 0x00004001L, MCI_INTEGER,
+"svideo\0", 0x00004002L, MCI_INTEGER,
+"pal\0", 0x00004003L, MCI_INTEGER,
+"secam\0", 0x00004004L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"quality\0", 0x00010000L, MCI_STRING,
+"algorithm\0", 0x00020000L, MCI_STRING,
+"number\0", 0x00080000L, MCI_INTEGER,
+"over\0", 0x00200000L, MCI_INTEGER,
+"record\0", 0x00400000L, MCI_FLAG,
+"still\0", 0x00800000L, MCI_FLAG,
+"clocktime\0", 0x00040000L, MCI_FLAG,
+"on\0", 0x00002000L, MCI_FLAG,
+"off\0", 0x00004000L, MCI_FLAG,
+"input\0", 0x02000000L, MCI_FLAG,
+"output\0", 0x04000000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"signal\0", 0x00000875L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"at\0", 0x00010000L, MCI_INTEGER,
+"every\0", 0x00020000L, MCI_INTEGER,
+"uservalue\0", 0x00040000L, MCI_INTEGER,
+"cancel\0", 0x00080000L, MCI_FLAG,
+"return position\0", 0x00100000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"status\0", 0x00000814L, MCI_COMMAND_HEAD,
+"\0", 0x00000002L, MCI_RETURN,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00000100L, MCI_CONSTANT,
+"frames skipped\0", 0x00008001L, MCI_INTEGER,
+"play speed\0", 0x00008002L, MCI_INTEGER,
+"audio breaks\0", 0x00008003L, MCI_INTEGER,
+"alignment\0", 0x00004029L, MCI_INTEGER,
+"audio input\0", 0x00004000L, MCI_INTEGER,
+"audio record\0", 0x0000401aL, MCI_INTEGER,
+"audio source\0", 0x00004009L, MCI_INTEGER,
+"audio stream\0", 0x0000402dL, MCI_INTEGER,
+"bass\0", 0x0000400fL, MCI_INTEGER,
+"bitsperpel\0", 0x0000402bL, MCI_INTEGER,
+"bitspersample\0", 0x0000402aL, MCI_INTEGER,
+"brightness\0", 0x00004005L, MCI_INTEGER,
+"bytespersec\0", 0x00004028L, MCI_INTEGER,
+"color\0", 0x00004006L, MCI_INTEGER,
+"contrast\0", 0x00004007L, MCI_INTEGER,
+"current track\0", 0x00000008L, MCI_INTEGER,
+"file format\0", 0x00004008L, MCI_INTEGER,
+"still file format\0", 0x0000401dL, MCI_INTEGER,
+"file mode\0", 0x0000401fL, MCI_INTEGER,
+"file completion\0", 0x00004020L, MCI_INTEGER,
+"forward\0", 0x0000402cL, MCI_INTEGER,
+"gamma\0", 0x0000400aL, MCI_INTEGER,
+"length\0", 0x00000001L, MCI_INTEGER,
+"media present\0", 0x00000005L, MCI_INTEGER,
+"mode\0", 0x00000004L, MCI_INTEGER,
+"monitor method\0", 0x0000400cL, MCI_INTEGER,
+"monitor\0", 0x0000400bL, MCI_INTEGER,
+"number of tracks\0", 0x00000003L, MCI_INTEGER,
+"palette handle\0", 0x00004004L, MCI_INTEGER,
+"pause mode\0", 0x00004026L, MCI_INTEGER,
+"position\0", 0x00000002L, MCI_INTEGER,
+"ready\0", 0x00000007L, MCI_INTEGER,
+"frame rate\0", 0x0000400eL, MCI_INTEGER,
+"reserved size\0", 0x00004010L, MCI_INTEGER,
+"samplespersec\0", 0x00004027L, MCI_INTEGER,
+"seek exactly\0", 0x00004011L, MCI_INTEGER,
+"sharpness\0", 0x00004012L, MCI_INTEGER,
+"smpte\0", 0x00004013L, MCI_INTEGER,
+"speed\0", 0x00004003L, MCI_INTEGER,
+"time format\0", 0x00000006L, MCI_INTEGER,
+"tint\0", 0x00004015L, MCI_INTEGER,
+"treble\0", 0x00004016L, MCI_INTEGER,
+"unsaved\0", 0x00004017L, MCI_INTEGER,
+"video key color\0", 0x00004025L, MCI_INTEGER,
+"video key index\0", 0x00004024L, MCI_INTEGER,
+"video source\0", 0x0000401bL, MCI_INTEGER,
+"video source number\0", 0x0000401eL, MCI_INTEGER,
+"video record\0", 0x0000401cL, MCI_INTEGER,
+"video stream\0", 0x0000402eL, MCI_INTEGER,
+"volume\0", 0x00004019L, MCI_INTEGER,
+"window handle\0", 0x00004001L, MCI_INTEGER,
+"window visible\0", 0x00004021L, MCI_INTEGER,
+"window minimized\0", 0x00004022L, MCI_INTEGER,
+"window maximized\0", 0x00004023L, MCI_INTEGER,
+"video streams\0", 0x00004100L, MCI_INTEGER,
+"video bitrate\0", 0x00004101L, MCI_INTEGER,
+"video maxbitrate\0", 0x00004102L, MCI_INTEGER,
+"audio streams\0", 0x00004103L, MCI_INTEGER,
+"audio bitrate\0", 0x00004104L, MCI_INTEGER,
+"video brush\0", 0x00004105L, MCI_INTEGER,
+"audio\0", 0x00004014L, MCI_INTEGER,
+"video\0", 0x00004018L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"track\0", 0x00000010L, MCI_INTEGER,
+"start\0", 0x00000200L, MCI_FLAG,
+"left\0", 0x00080000L, MCI_FLAG,
+"right\0", 0x00100000L, MCI_FLAG,
+"nominal\0", 0x00020000L, MCI_FLAG,
+"record\0", 0x01000000L, MCI_FLAG,
+"input\0", 0x00400000L, MCI_FLAG,
+"output\0", 0x00800000L, MCI_FLAG,
+"disk space\0", 0x00200000L, MCI_STRING,
+"reference\0", 0x00040000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"step\0", 0x0000080eL, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"reverse\0", 0x00010000L, MCI_FLAG,
+"by\0", 0x00020000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"stop\0", 0x00000808L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"hold\0", 0x00010000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"undo\0", 0x00000879L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"unfreeze\0", 0x00000845L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"at\0", 0x00010000L, MCI_RECT,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"update\0", 0x00000854L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"at\0", 0x00010000L, MCI_RECT,
+"hdc\0", 0x00020000L, MCI_INTEGER,
+"paint\0", 0x00040000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"where\0", 0x00000843L, MCI_COMMAND_HEAD,
+"\0", 0x00000007L, MCI_RETURN,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"source\0", 0x00020000L, MCI_FLAG,
+"destination\0", 0x00040000L, MCI_FLAG,
+"frame\0", 0x00080000L, MCI_FLAG,
+"video\0", 0x00100000L, MCI_FLAG,
+"window\0", 0x00200000L, MCI_FLAG,
+"max\0", 0x00400000L, MCI_FLAG,
+"min\0", 0x00800000L, MCI_FLAG,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"window\0", 0x00000841L, MCI_COMMAND_HEAD,
+"notify\0", 0x00000001L, MCI_FLAG,
+"wait\0", 0x00000002L, MCI_FLAG,
+"test\0", 0x00000020L, MCI_FLAG,
+"handle\0", 0x00010000L, MCI_CONSTANT,
+"default\0", 0x00000000L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"state\0", 0x00040000L, MCI_CONSTANT,
+"hide\0", 0x00000000L, MCI_INTEGER,
+"minimize\0", 0x00000006L, MCI_INTEGER,
+"restore\0", 0x00000009L, MCI_INTEGER,
+"show maximized\0", 0x00000003L, MCI_INTEGER,
+"show min noactive\0", 0x00000007L, MCI_INTEGER,
+"show minimized\0", 0x00000002L, MCI_INTEGER,
+"show na\0", 0x00000008L, MCI_INTEGER,
+"show noactivate\0", 0x00000004L, MCI_INTEGER,
+"show normal\0", 0x00000001L, MCI_INTEGER,
+"show\0", 0x00000005L, MCI_INTEGER,
+"no action\0", 0x00000008L, MCI_INTEGER,
+"minimized\0", 0x00000002L, MCI_INTEGER,
+"\0", 0x00000000L, MCI_END_CONSTANT,
+"text\0", 0x00080000L, MCI_STRING,
+"\0", 0x00000000L, MCI_END_COMMAND,
+"\0", 0x00000000L, MCI_END_COMMAND_LIST
+END
diff --git a/dlls/winmm/mciavi/mmoutput.c b/dlls/winmm/mciavi/mmoutput.c
new file mode 100644
index 0000000000000000000000000000000000000000..9932ad45bcad574574c739366902ede20f738e8d
--- /dev/null
+++ b/dlls/winmm/mciavi/mmoutput.c
@@ -0,0 +1,573 @@
+/* -*- tab-width: 8; c-basic-offset: 4 -*- */
+
+/*
+ * Digital video MCI Wine Driver
+ *
+ * Copyright 1999, 2000 Eric POUECH
+ */
+
+#include "private_mciavi.h"
+#include "debugtools.h"
+
+DEFAULT_DEBUG_CHANNEL(mciavi);
+
+static BOOL MCIAVI_GetInfoAudio(WINE_MCIAVI* wma, const MMCKINFO* mmckList)
+{
+    MMCKINFO	mmckInfo;
+    
+    mmckInfo.ckid = ckidSTREAMHEADER;
+    if (mmioDescend(wma->hFile, &mmckInfo, mmckList, MMIO_FINDCHUNK) != 0) {
+	WARN("Can't find 'strh' chunk\n");
+	return FALSE;
+    }
+    
+    mmioRead(wma->hFile, (LPSTR)&wma->ash_audio, sizeof(wma->ash_audio));
+    
+    TRACE("ash.fccType='%c%c%c%c'\n", 		LOBYTE(LOWORD(wma->ash_audio.fccType)), 
+	                                        HIBYTE(LOWORD(wma->ash_audio.fccType)), 
+	                                        LOBYTE(HIWORD(wma->ash_audio.fccType)), 
+	                                        HIBYTE(HIWORD(wma->ash_audio.fccType)));
+    TRACE("ash.fccHandler='%c%c%c%c'\n",	LOBYTE(LOWORD(wma->ash_audio.fccHandler)), 
+	                                        HIBYTE(LOWORD(wma->ash_audio.fccHandler)), 
+	                                        LOBYTE(HIWORD(wma->ash_audio.fccHandler)), 
+	                                        HIBYTE(HIWORD(wma->ash_audio.fccHandler)));
+    TRACE("ash.dwFlags=%ld\n", 			wma->ash_audio.dwFlags);
+    TRACE("ash.wPriority=%d\n", 		wma->ash_audio.wPriority);
+    TRACE("ash.wLanguage=%d\n", 		wma->ash_audio.wLanguage);
+    TRACE("ash.dwInitialFrames=%ld\n", 		wma->ash_audio.dwInitialFrames);
+    TRACE("ash.dwScale=%ld\n", 			wma->ash_audio.dwScale);
+    TRACE("ash.dwRate=%ld\n", 			wma->ash_audio.dwRate);
+    TRACE("ash.dwStart=%ld\n", 			wma->ash_audio.dwStart);
+    TRACE("ash.dwLength=%ld\n", 		wma->ash_audio.dwLength);
+    TRACE("ash.dwSuggestedBufferSize=%ld\n", 	wma->ash_audio.dwSuggestedBufferSize);
+    TRACE("ash.dwQuality=%ld\n", 		wma->ash_audio.dwQuality);
+    TRACE("ash.dwSampleSize=%ld\n", 		wma->ash_audio.dwSampleSize);
+    TRACE("ash.rcFrame=(%d,%d,%d,%d)\n", 	wma->ash_audio.rcFrame.top, wma->ash_audio.rcFrame.left, 
+	  wma->ash_audio.rcFrame.bottom, wma->ash_audio.rcFrame.right);
+    
+    mmioAscend(wma->hFile, &mmckInfo, 0);
+    
+    mmckInfo.ckid = ckidSTREAMFORMAT;
+    if (mmioDescend(wma->hFile, &mmckInfo, mmckList, MMIO_FINDCHUNK) != 0) {
+	WARN("Can't find 'strh' chunk\n");
+	return FALSE;
+    }
+    if (mmckInfo.cksize < sizeof(WAVEFORMAT)) {
+	WARN("Size of strf chunk (%ld) < audio format struct\n", mmckInfo.cksize);
+	return FALSE;
+    }
+    wma->lpWaveFormat = HeapAlloc(GetProcessHeap(), 0, mmckInfo.cksize);
+    if (!wma->lpWaveFormat) {
+	WARN("Can't alloc WaveFormat\n");
+	return FALSE;
+    }
+    
+    mmioRead(wma->hFile, (LPSTR)wma->lpWaveFormat, mmckInfo.cksize);
+    
+    TRACE("waveFormat.wFormatTag=%d\n",		wma->lpWaveFormat->wFormatTag);
+    TRACE("waveFormat.nChannels=%d\n", 		wma->lpWaveFormat->nChannels);
+    TRACE("waveFormat.nSamplesPerSec=%ld\n",	wma->lpWaveFormat->nSamplesPerSec);
+    TRACE("waveFormat.nAvgBytesPerSec=%ld\n",	wma->lpWaveFormat->nAvgBytesPerSec);
+    TRACE("waveFormat.nBlockAlign=%d\n",	wma->lpWaveFormat->nBlockAlign);
+    TRACE("waveFormat.wBitsPerSample=%d\n",	wma->lpWaveFormat->wBitsPerSample);
+    if (mmckInfo.cksize >= sizeof(WAVEFORMATEX))
+	TRACE("waveFormat.cbSize=%d\n", 		wma->lpWaveFormat->cbSize);
+    
+    mmioAscend(wma->hFile, &mmckInfo, 0);
+    
+    return TRUE;
+}
+
+static BOOL MCIAVI_GetInfoVideo(WINE_MCIAVI* wma, const MMCKINFO* mmckList)
+{
+    MMCKINFO	mmckInfo;
+    
+    mmckInfo.ckid = ckidSTREAMHEADER;
+    if (mmioDescend(wma->hFile, &mmckInfo, mmckList, MMIO_FINDCHUNK) != 0) {
+	WARN("Can't find 'strh' chunk\n");
+	return FALSE;
+    }
+    
+    mmioRead(wma->hFile, (LPSTR)&wma->ash_video, sizeof(wma->ash_video));
+    
+    TRACE("ash.fccType='%c%c%c%c'\n", 		LOBYTE(LOWORD(wma->ash_video.fccType)), 
+	                                        HIBYTE(LOWORD(wma->ash_video.fccType)), 
+	                                        LOBYTE(HIWORD(wma->ash_video.fccType)), 
+	                                        HIBYTE(HIWORD(wma->ash_video.fccType)));
+    TRACE("ash.fccHandler='%c%c%c%c'\n",	LOBYTE(LOWORD(wma->ash_video.fccHandler)), 
+	                                        HIBYTE(LOWORD(wma->ash_video.fccHandler)), 
+	                                        LOBYTE(HIWORD(wma->ash_video.fccHandler)), 
+	                                        HIBYTE(HIWORD(wma->ash_video.fccHandler)));
+    TRACE("ash.dwFlags=%ld\n", 			wma->ash_video.dwFlags);
+    TRACE("ash.wPriority=%d\n", 		wma->ash_video.wPriority);
+    TRACE("ash.wLanguage=%d\n", 		wma->ash_video.wLanguage);
+    TRACE("ash.dwInitialFrames=%ld\n", 		wma->ash_video.dwInitialFrames);
+    TRACE("ash.dwScale=%ld\n", 			wma->ash_video.dwScale);
+    TRACE("ash.dwRate=%ld\n", 			wma->ash_video.dwRate);
+    TRACE("ash.dwStart=%ld\n", 			wma->ash_video.dwStart);
+    TRACE("ash.dwLength=%ld\n", 		wma->ash_video.dwLength);
+    TRACE("ash.dwSuggestedBufferSize=%ld\n", 	wma->ash_video.dwSuggestedBufferSize);
+    TRACE("ash.dwQuality=%ld\n", 		wma->ash_video.dwQuality);
+    TRACE("ash.dwSampleSize=%ld\n", 		wma->ash_video.dwSampleSize);
+    TRACE("ash.rcFrame=(%d,%d,%d,%d)\n", 	wma->ash_video.rcFrame.top, wma->ash_video.rcFrame.left, 
+	  wma->ash_video.rcFrame.bottom, wma->ash_video.rcFrame.right);
+    
+    mmioAscend(wma->hFile, &mmckInfo, 0);
+    
+    mmckInfo.ckid = ckidSTREAMFORMAT;
+    if (mmioDescend(wma->hFile, &mmckInfo, mmckList, MMIO_FINDCHUNK) != 0) {
+	WARN("Can't find 'strh' chunk\n");
+	return FALSE;
+    }
+    
+    wma->inbih = HeapAlloc(GetProcessHeap(), 0, mmckInfo.cksize);
+    if (!wma->inbih) {
+	WARN("Can't alloc input BIH\n");
+	return FALSE;
+    }
+    
+    mmioRead(wma->hFile, (LPSTR)wma->inbih, mmckInfo.cksize);
+    
+    TRACE("bih.biSize=%ld\n", 		wma->inbih->biSize);
+    TRACE("bih.biWidth=%ld\n", 		wma->inbih->biWidth);
+    TRACE("bih.biHeight=%ld\n", 	wma->inbih->biHeight);
+    TRACE("bih.biPlanes=%d\n", 		wma->inbih->biPlanes);
+    TRACE("bih.biBitCount=%d\n", 	wma->inbih->biBitCount);
+    TRACE("bih.biCompression=%lx\n", 	wma->inbih->biCompression);
+    TRACE("bih.biSizeImage=%ld\n", 	wma->inbih->biSizeImage);
+    TRACE("bih.biXPelsPerMeter=%ld\n", 	wma->inbih->biXPelsPerMeter);
+    TRACE("bih.biYPelsPerMeter=%ld\n", 	wma->inbih->biYPelsPerMeter);
+    TRACE("bih.biClrUsed=%ld\n", 	wma->inbih->biClrUsed);
+    TRACE("bih.biClrImportant=%ld\n", 	wma->inbih->biClrImportant);
+    
+    mmioAscend(wma->hFile, &mmckInfo, 0);
+    
+    return TRUE;
+}
+
+struct AviListBuild {
+    DWORD	numVideoFrames;
+    DWORD	numAudioAllocated;
+    DWORD	numAudioBlocks;
+    DWORD	inVideoSize;
+    DWORD	inAudioSize;
+};
+
+static BOOL	MCIAVI_AddFrame(WINE_MCIAVI* wma, LPMMCKINFO mmck, 
+				struct AviListBuild* alb)
+{
+    if (mmck->ckid == ckidAVIPADDING) return TRUE;
+    
+    switch (TWOCCFromFOURCC(mmck->ckid)) {
+    case cktypeDIBbits:
+    case cktypeDIBcompressed:
+    case cktypePALchange:
+	TRACE("Adding video frame[%ld]: %ld bytes\n", 
+	      alb->numVideoFrames, mmck->cksize);
+	if (alb->numVideoFrames < wma->dwPlayableVideoFrames) {
+	    wma->lpVideoIndex[alb->numVideoFrames].dwOffset = mmck->dwDataOffset;
+	    wma->lpVideoIndex[alb->numVideoFrames].dwSize = mmck->cksize;
+	    if (alb->inVideoSize < mmck->cksize)
+		alb->inVideoSize = mmck->cksize;
+	    alb->numVideoFrames++;
+	} else {
+	    WARN("Too many video frames\n");
+	}
+	break;
+    case cktypeWAVEbytes:
+	TRACE("Adding audio frame[%ld]: %ld bytes\n", 
+	      alb->numAudioBlocks, mmck->cksize);
+	if (wma->lpWaveFormat) {
+	    if (alb->numAudioBlocks >= alb->numAudioAllocated) {
+		alb->numAudioAllocated += 32;
+		wma->lpAudioIndex = HeapReAlloc(GetProcessHeap(), 0, 
+						wma->lpAudioIndex, 
+						alb->numAudioAllocated * sizeof(struct MMIOPos));
+		if (!wma->lpAudioIndex) return FALSE;
+	    }
+	    wma->lpAudioIndex[alb->numAudioBlocks].dwOffset = mmck->dwDataOffset;
+	    wma->lpAudioIndex[alb->numAudioBlocks].dwSize = mmck->cksize;
+	    if (alb->inAudioSize < mmck->cksize)
+		alb->inAudioSize = mmck->cksize;
+	    alb->numAudioBlocks++;
+	} else {
+	    WARN("Wave chunk without wave format... discarding\n");
+	}
+	break;
+    default:
+	WARN("Unknown frame type %04x\n", TWOCCFromFOURCC(mmck->ckid));
+	break;
+    }
+    return TRUE;
+}
+
+BOOL MCIAVI_GetInfo(WINE_MCIAVI* wma)
+{
+    MMCKINFO		ckMainRIFF;
+    MMCKINFO		mmckHead;
+    MMCKINFO		mmckList;
+    MMCKINFO		mmckInfo;
+    struct AviListBuild alb;
+    
+    if (mmioDescend(wma->hFile, &ckMainRIFF, NULL, 0) != 0) {
+	WARN("Can't find 'RIFF' chunk\n");
+	return FALSE;
+    }
+    
+    if ((ckMainRIFF.ckid != FOURCC_RIFF) || (ckMainRIFF.fccType != formtypeAVI)) {
+	WARN("Can't find 'AVI ' chunk\n");
+	return FALSE;
+    }
+    
+    mmckHead.fccType = listtypeAVIHEADER;
+    if (mmioDescend(wma->hFile, &mmckHead, &ckMainRIFF, MMIO_FINDLIST) != 0) {
+	WARN("Can't find 'hdrl' list\n");
+	return FALSE;
+    }
+    
+    mmckInfo.ckid = ckidAVIMAINHDR;
+    if (mmioDescend(wma->hFile, &mmckInfo, &mmckHead, MMIO_FINDCHUNK) != 0) {
+	WARN("Can't find 'avih' chunk\n");
+	return FALSE;
+    }
+    
+    mmioRead(wma->hFile, (LPSTR)&wma->mah, sizeof(wma->mah));
+    
+    TRACE("mah.dwMicroSecPerFrame=%ld\n", 	wma->mah.dwMicroSecPerFrame);
+    TRACE("mah.dwMaxBytesPerSec=%ld\n", 	wma->mah.dwMaxBytesPerSec);
+    TRACE("mah.dwPaddingGranularity=%ld\n", 	wma->mah.dwPaddingGranularity);
+    TRACE("mah.dwFlags=%ld\n", 			wma->mah.dwFlags);
+    TRACE("mah.dwTotalFrames=%ld\n", 		wma->mah.dwTotalFrames);
+    TRACE("mah.dwInitialFrames=%ld\n", 		wma->mah.dwInitialFrames);
+    TRACE("mah.dwStreams=%ld\n", 		wma->mah.dwStreams);
+    TRACE("mah.dwSuggestedBufferSize=%ld\n",	wma->mah.dwSuggestedBufferSize);
+    TRACE("mah.dwWidth=%ld\n", 			wma->mah.dwWidth);
+    TRACE("mah.dwHeight=%ld\n", 		wma->mah.dwHeight);
+    
+    mmioAscend(wma->hFile, &mmckInfo, 0);
+    
+    mmckList.fccType = listtypeSTREAMHEADER;
+    if (mmioDescend(wma->hFile, &mmckList, &mmckHead, MMIO_FINDLIST) != 0) {
+	WARN("Can't find 'strl' list\n");
+	return FALSE;
+    }
+    
+    if (!MCIAVI_GetInfoVideo(wma, &mmckList)) {
+	return FALSE;
+    }
+    
+    mmioAscend(wma->hFile, &mmckList, 0);
+    
+    mmckList.fccType = listtypeSTREAMHEADER;
+    if (mmioDescend(wma->hFile, &mmckList, &mmckHead, MMIO_FINDLIST) == 0) {
+	if (!MCIAVI_GetInfoAudio(wma, &mmckList)) {
+	    return FALSE;
+	}
+	mmioAscend(wma->hFile, &mmckList, 0);
+    }
+    
+    mmioAscend(wma->hFile, &mmckHead, 0);
+    
+    /* no need to read optional JUNK chunk */
+    
+    mmckList.fccType = listtypeAVIMOVIE;
+    if (mmioDescend(wma->hFile, &mmckList, &ckMainRIFF, MMIO_FINDLIST) != 0) {
+	WARN("Can't find 'movi' list\n");
+	return FALSE;
+    }
+    
+    wma->dwPlayableVideoFrames = wma->mah.dwTotalFrames;
+    wma->lpVideoIndex = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, 
+				  wma->dwPlayableVideoFrames * sizeof(struct MMIOPos));
+    if (!wma->lpVideoIndex) {
+	WARN("Can't alloc video index array\n");
+	return FALSE;
+    }
+    wma->dwPlayableAudioBlocks = 0;
+    wma->lpAudioIndex = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, 
+				  wma->dwPlayableVideoFrames * sizeof(struct MMIOPos));
+    if (!wma->lpAudioIndex) {
+	WARN("Can't alloc audio index array\n");
+	return FALSE;
+    }
+    
+    alb.numAudioBlocks = alb.numVideoFrames = 0;
+    alb.inVideoSize = alb.inAudioSize = 0;
+    alb.numAudioAllocated = 0;
+    
+    while (mmioDescend(wma->hFile, &mmckInfo, &mmckList, 0) == 0) {
+	if (mmckInfo.fccType == listtypeAVIRECORD) {	
+	    MMCKINFO	tmp;
+	    
+	    while (mmioDescend(wma->hFile, &tmp, &mmckInfo, 0) == 0) {
+		MCIAVI_AddFrame(wma, &tmp, &alb);
+		mmioAscend(wma->hFile, &tmp, 0);
+	    }
+	} else {
+	    MCIAVI_AddFrame(wma, &mmckInfo, &alb);
+	}
+	
+	mmioAscend(wma->hFile, &mmckInfo, 0);
+    }
+    if (alb.numVideoFrames != wma->dwPlayableVideoFrames) {
+	WARN("Found %ld video frames (/%ld), reducing playable frames\n", 
+	     alb.numVideoFrames, wma->dwPlayableVideoFrames);
+	wma->dwPlayableVideoFrames = alb.numVideoFrames;
+    }
+    wma->dwPlayableAudioBlocks = alb.numAudioBlocks;
+    
+    if (alb.inVideoSize > wma->ash_video.dwSuggestedBufferSize) {
+	WARN("inVideoSize=%ld suggestedSize=%ld\n", alb.inVideoSize, wma->ash_video.dwSuggestedBufferSize);
+	wma->ash_video.dwSuggestedBufferSize = alb.inVideoSize;
+    }
+    if (alb.inAudioSize > wma->ash_audio.dwSuggestedBufferSize) {
+	WARN("inAudioSize=%ld suggestedSize=%ld\n", alb.inAudioSize, wma->ash_audio.dwSuggestedBufferSize);
+	wma->ash_audio.dwSuggestedBufferSize = alb.inAudioSize;
+    }
+    
+    wma->indata = HeapAlloc(GetProcessHeap(), 0, wma->ash_video.dwSuggestedBufferSize);
+    if (!wma->indata) {
+	WARN("Can't alloc input buffer\n");
+	return FALSE;
+    }
+    
+    return TRUE;
+}
+
+BOOL    MCIAVI_OpenVideo(WINE_MCIAVI* wma)
+{
+    DWORD	outSize;
+    FOURCC	fcc = wma->ash_video.fccHandler;
+    
+    /* check uncompressed AVI */
+    if ((fcc == mmioFOURCC('D','I','B',' ')) || 
+	(fcc == mmioFOURCC('R','L','E',' '))) {
+	wma->hic = 0;             
+	MCIAVI_DrawFrame(wma);
+	return TRUE;
+    }
+    
+    /* get the right handle */
+    if (fcc == 0) fcc = wma->inbih->biCompression;
+    if (fcc == mmioFOURCC('C','R','A','M')) fcc = mmioFOURCC('M','S','V','C');
+    
+    /* try to get a decompressor for that type */
+    wma->hic = ICLocate(ICTYPE_VIDEO, fcc, wma->inbih, NULL, ICMODE_DECOMPRESS);
+    if (!wma->hic) {
+	WARN("Can't locate codec for the file\n");
+	return FALSE;
+    }
+    
+    outSize = sizeof(BITMAPINFOHEADER) + 256 * sizeof(RGBQUAD);
+    
+    wma->outbih = HeapAlloc(GetProcessHeap(), 0, outSize);
+    if (!wma->outbih) {
+	WARN("Can't alloc output BIH\n");
+	return FALSE;
+    }
+    if (!ICGetDisplayFormat(wma->hic, wma->inbih, wma->outbih, 0, 0, 0)) {
+	WARN("Can't open decompressor\n");
+	return FALSE;
+    }
+    
+    TRACE("bih.biSize=%ld\n", 		wma->outbih->biSize);
+    TRACE("bih.biWidth=%ld\n", 		wma->outbih->biWidth);
+    TRACE("bih.biHeight=%ld\n", 	wma->outbih->biHeight);
+    TRACE("bih.biPlanes=%d\n", 		wma->outbih->biPlanes);
+    TRACE("bih.biBitCount=%d\n", 	wma->outbih->biBitCount);
+    TRACE("bih.biCompression=%lx\n", 	wma->outbih->biCompression);
+    TRACE("bih.biSizeImage=%ld\n", 	wma->outbih->biSizeImage);
+    TRACE("bih.biXPelsPerMeter=%ld\n", 	wma->outbih->biXPelsPerMeter);
+    TRACE("bih.biYPelsPerMeter=%ld\n", 	wma->outbih->biYPelsPerMeter);
+    TRACE("bih.biClrUsed=%ld\n", 	wma->outbih->biClrUsed);
+    TRACE("bih.biClrImportant=%ld\n", 	wma->outbih->biClrImportant);
+    
+    wma->outdata = HeapAlloc(GetProcessHeap(), 0, wma->outbih->biSizeImage);
+    if (!wma->outdata) {
+	WARN("Can't alloc output buffer\n");
+	return FALSE;
+    }
+    
+    if (ICSendMessage(wma->hic, ICM_DECOMPRESS_BEGIN, 
+		      (DWORD)wma->inbih, (DWORD)wma->outbih) != ICERR_OK) {
+	WARN("Can't begin decompression\n");
+	return FALSE;
+    }
+    
+    MCIAVI_DrawFrame(wma);
+    
+    return TRUE;
+}
+
+static void CALLBACK MCIAVI_waveCallback(HWAVEOUT hwo, UINT uMsg, DWORD dwInstance,  
+					 DWORD dwParam1, DWORD dwParam2)
+{
+    WINE_MCIAVI*	wma = (WINE_MCIAVI*)dwInstance;
+    
+    switch (uMsg) {
+    case WOM_OPEN:
+    case WOM_CLOSE:
+	break;
+    case WOM_DONE:
+	InterlockedIncrement(&wma->dwEventCount);
+	TRACE("Returning waveHdr=%lx\n", dwParam1);
+	SetEvent(wma->hEvent);
+	break;
+    default:
+	ERR("Unknown uMsg=%d\n", uMsg);
+    }
+}
+
+DWORD MCIAVI_OpenAudio(WINE_MCIAVI* wma, unsigned* nHdr, LPWAVEHDR* pWaveHdr)
+{
+    DWORD	dwRet;
+    LPWAVEHDR	waveHdr;
+    unsigned	i;
+    
+    dwRet = waveOutOpen(&wma->hWave, WAVE_MAPPER, wma->lpWaveFormat, 
+			(DWORD)MCIAVI_waveCallback, (DWORD)wma, CALLBACK_FUNCTION);
+    if (dwRet != 0) {
+	TRACE("Can't open low level audio device %ld\n", dwRet);
+	dwRet = MCIERR_DEVICE_OPEN;
+	wma->hWave = 0;
+	goto cleanUp;
+    }
+    
+    /* FIXME: should set up a heuristic to compute the number of wave headers
+     * to be used...
+     */
+    *nHdr = 7;
+    waveHdr = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, 
+			*nHdr * (sizeof(WAVEHDR) + wma->ash_audio.dwSuggestedBufferSize));
+    if (!waveHdr) {
+	TRACE("Can't alloc wave headers\n");
+	dwRet = MCIERR_DEVICE_OPEN;
+	goto cleanUp;
+    }
+    
+    for (i = 0; i < *nHdr; i++) {
+	/* other fields are zero:ed on allocation */
+	waveHdr[i].lpData = (char*)waveHdr + 
+	    *nHdr * sizeof(WAVEHDR) + i * wma->ash_audio.dwSuggestedBufferSize;
+	waveHdr[i].dwBufferLength = wma->ash_audio.dwSuggestedBufferSize;
+	if (waveOutPrepareHeader(wma->hWave, &waveHdr[i], sizeof(WAVEHDR))) {
+	    dwRet = MCIERR_INTERNAL;
+	    goto cleanUp;
+	}
+    }
+    
+    if (wma->dwCurrVideoFrame != 0 && wma->lpWaveFormat) {
+	FIXME("Should recompute dwCurrAudioBlock, except unsynchronized sound & video");
+    }
+    wma->dwCurrAudioBlock = 0;
+    
+    wma->hEvent = CreateEventA(NULL, FALSE, FALSE, NULL);
+    wma->dwEventCount = *nHdr - 1;
+    *pWaveHdr = waveHdr;
+ cleanUp:
+    return dwRet;
+}	
+
+void MCIAVI_PlayAudioBlocks(WINE_MCIAVI* wma, unsigned nHdr, LPWAVEHDR waveHdr)
+{
+    TRACE("%ld (ec=%lu)\n", wma->lpAudioIndex[wma->dwCurrAudioBlock].dwOffset, wma->dwEventCount);
+    
+    /* push as many blocks as possible => audio gets priority */
+    while (wma->dwStatus != MCI_MODE_STOP && wma->dwStatus != MCI_MODE_NOT_READY && 
+	   wma->dwCurrAudioBlock < wma->dwPlayableAudioBlocks) {
+	unsigned	whidx = wma->dwCurrAudioBlock % nHdr;
+	
+	ResetEvent(wma->hEvent);
+	if (InterlockedDecrement(&wma->dwEventCount) < 0 ||
+	    !wma->lpAudioIndex[wma->dwCurrAudioBlock].dwOffset)
+	    break;
+	
+	mmioSeek(wma->hFile, wma->lpAudioIndex[wma->dwCurrAudioBlock].dwOffset, SEEK_SET);
+	mmioRead(wma->hFile, waveHdr[whidx].lpData, wma->lpAudioIndex[wma->dwCurrAudioBlock].dwSize);
+	
+	waveHdr[whidx].dwFlags &= ~WHDR_DONE;
+	waveHdr[whidx].dwBufferLength = wma->lpAudioIndex[wma->dwCurrAudioBlock].dwSize;
+	waveOutWrite(wma->hWave, &waveHdr[whidx], sizeof(WAVEHDR));
+	wma->dwCurrAudioBlock++;
+    }
+    InterlockedIncrement(&wma->dwEventCount);
+}
+
+LRESULT MCIAVI_PaintFrame(WINE_MCIAVI* wma, HDC hDC)
+{
+    void* 		pBitmapData = NULL;
+    LPBITMAPINFO	pBitmapInfo = NULL;
+    HDC 		hdcMem;
+    HBITMAP		hbmOld;
+    int 		nWidth;
+    int 		nHeight;
+    
+    if (!hDC || !wma->inbih)
+	return TRUE;
+    
+    TRACE("Painting frame %lu\n", wma->dwCurrVideoFrame);
+    
+    if (wma->hic) {
+        pBitmapData = wma->outdata;
+        pBitmapInfo = (LPBITMAPINFO)wma->outbih;
+	
+        nWidth = wma->outbih->biWidth;
+        nHeight = wma->outbih->biHeight;  
+    } else {  
+        pBitmapData = wma->indata;
+        pBitmapInfo = (LPBITMAPINFO)wma->inbih;
+	
+        nWidth = wma->inbih->biWidth;
+        nHeight = wma->inbih->biHeight;  
+    }  
+    
+    if (!wma->hbmFrame) 
+        wma->hbmFrame = CreateCompatibleBitmap(hDC, nWidth, nHeight);
+    
+    SetDIBits(hDC, wma->hbmFrame, 0, nHeight, pBitmapData, pBitmapInfo, DIB_RGB_COLORS); 
+    
+    hdcMem = CreateCompatibleDC(hDC);
+    hbmOld = SelectObject(hdcMem, wma->hbmFrame);
+    
+    BitBlt(hDC, 0, 0, nWidth, nHeight, hdcMem, 0, 0, SRCCOPY);    
+    
+    SelectObject(hdcMem, hbmOld);
+    DeleteDC(hdcMem);
+    return TRUE;
+}
+
+LRESULT MCIAVI_DrawFrame(WINE_MCIAVI* wma)
+{
+    HDC		hDC;
+    
+    TRACE("Drawing frame %lu\n", wma->dwCurrVideoFrame);
+    
+    if (!wma->lpVideoIndex[wma->dwCurrVideoFrame].dwOffset)
+	return FALSE;
+    
+    EnterCriticalSection(&wma->cs);
+    
+    mmioSeek(wma->hFile, wma->lpVideoIndex[wma->dwCurrVideoFrame].dwOffset, SEEK_SET);
+    mmioRead(wma->hFile, wma->indata, wma->lpVideoIndex[wma->dwCurrVideoFrame].dwSize);
+    
+    /* FIXME ? */
+    wma->inbih->biSizeImage = wma->lpVideoIndex[wma->dwCurrVideoFrame].dwSize;
+    
+    if (wma->hic &&
+	ICDecompress(wma->hic, 0, wma->inbih, wma->indata, 
+		     wma->outbih, wma->outdata) != ICERR_OK) {
+	LeaveCriticalSection(&wma->cs);
+	WARN("Decompression error\n");
+	return FALSE;
+    }
+    
+    if (IsWindowVisible(wma->hWnd) && (hDC = GetDC(wma->hWnd)) != 0) {
+	MCIAVI_PaintFrame(wma, hDC);
+	ReleaseDC(wma->hWnd, hDC);
+    }
+    
+    LeaveCriticalSection(&wma->cs);
+    
+    return TRUE;
+}
+
diff --git a/dlls/winmm/mciavi/private_mciavi.h b/dlls/winmm/mciavi/private_mciavi.h
new file mode 100644
index 0000000000000000000000000000000000000000..5c39f96b15d993bdc216f4072e985cc7d26eaf0e
--- /dev/null
+++ b/dlls/winmm/mciavi/private_mciavi.h
@@ -0,0 +1,88 @@
+/* -*- tab-width: 8; c-basic-offset: 4 -*- */
+
+/*
+ * Digital video MCI Wine Driver
+ *
+ * Copyright 1999, 2000 Eric POUECH
+ */
+
+#include "windef.h"
+#include "winbase.h"
+#include "wingdi.h"
+#include "winuser.h"
+#include "mmddk.h"
+#include "digitalv.h"
+#include "vfw.h"
+#include "mciavi.h"
+
+struct MMIOPos {
+    DWORD	dwOffset;
+    DWORD	dwSize;
+};
+
+typedef struct {
+    UINT		wDevID;
+    int			nUseCount;          	/* Incremented for each shared open          */
+    BOOL16  		fShareable;         	/* TRUE if first open was shareable 	     */
+    HANDLE16 		hCallback;         	/* Callback handle for pending notification  */
+    WORD		wCommandTable;		/* custom MCI command table */
+    volatile DWORD	dwStatus;		/* One of MCI_MODE_XXX			     */
+    MCI_OPEN_PARMSA 	openParms;
+    DWORD		dwMciTimeFormat;	/* current time format */
+    DWORD		dwSet;			/* what's turned on: video & audio l&r */
+    /* information on the loaded AVI file */
+    HMMIO		hFile;	            	/* mmio file handle open as Element          */
+    MainAVIHeader	mah;
+    AVIStreamHeader	ash_video;
+    AVIStreamHeader	ash_audio;
+    LPBITMAPINFOHEADER	inbih;
+    struct MMIOPos*	lpVideoIndex;
+    LPWAVEFORMATEX	lpWaveFormat;
+    struct MMIOPos*	lpAudioIndex;
+    /* computed data from the file */
+    DWORD		dwPlayableVideoFrames;	/* max number of frames to be played. Takes care of truncated files and audio skew */
+    DWORD		dwPlayableAudioBlocks;
+    /* data for the AVI decompressor */
+    HIC			hic;
+    LPBITMAPINFOHEADER	outbih;
+    LPVOID		indata;
+    LPVOID		outdata;   
+    HBITMAP  	    	hbmFrame;
+    /* data for playing the audio part */
+    HANDLE		hWave;
+    HANDLE		hEvent;			/* for synchronization */
+    DWORD		dwEventCount;		/* for synchronization */
+    /* data for play back */
+    HWND		hWnd;
+    DWORD		dwCurrVideoFrame;	/* video frame to display and current position */
+    DWORD		dwCurrAudioBlock;	/* current audio block being played */
+    /* data for the background mechanism */
+    CRITICAL_SECTION	cs;
+} WINE_MCIAVI;
+
+extern HINSTANCE MCIAVI_hInstance;
+
+/* info.c */
+DWORD 	MCIAVI_ConvertFrameToTimeFormat(WINE_MCIAVI* wma, DWORD val, LPDWORD lpRet);
+DWORD 	MCIAVI_ConvertTimeFormatToFrame(WINE_MCIAVI* wma, DWORD val);
+DWORD	MCIAVI_mciGetDevCaps(UINT wDevID, DWORD dwFlags,  LPMCI_GETDEVCAPS_PARMS lpParms);
+DWORD	MCIAVI_mciInfo(UINT wDevID, DWORD dwFlags, LPMCI_DGV_INFO_PARMSA lpParms);
+DWORD	MCIAVI_mciSet(UINT wDevID, DWORD dwFlags, LPMCI_DGV_SET_PARMS lpParms);
+DWORD	MCIAVI_mciStatus(UINT wDevID, DWORD dwFlags, LPMCI_DGV_STATUS_PARMSA lpParms);
+
+/* mmoutput.c */
+BOOL	MCIAVI_GetInfo(WINE_MCIAVI* wma);
+DWORD	MCIAVI_OpenAudio(WINE_MCIAVI* wma, unsigned* nHdr, LPWAVEHDR* pWaveHdr);
+BOOL	MCIAVI_OpenVideo(WINE_MCIAVI* wma);
+void	MCIAVI_PlayAudioBlocks(WINE_MCIAVI* wma, unsigned nHdr, LPWAVEHDR waveHdr);
+LRESULT MCIAVI_DrawFrame(WINE_MCIAVI* wma);
+LRESULT MCIAVI_PaintFrame(WINE_MCIAVI* wma, HDC hDC);
+
+/* mciavi.c */
+WINE_MCIAVI*	MCIAVI_mciGetOpenDev(UINT wDevID);
+
+/* window.c */
+BOOL    MCIAVI_CreateWindow(WINE_MCIAVI* wma, DWORD dwFlags, LPMCI_DGV_OPEN_PARMSA lpOpenParms);
+DWORD	MCIAVI_mciPut(UINT wDevID, DWORD dwFlags, LPMCI_DGV_PUT_PARMS lpParms);
+DWORD	MCIAVI_mciWhere(UINT wDevID, DWORD dwFlags, LPMCI_DGV_RECT_PARMS lpParms);
+DWORD	MCIAVI_mciWindow(UINT wDevID, DWORD dwFlags, LPMCI_DGV_WINDOW_PARMSA lpParms);
diff --git a/dlls/winmm/mciavi/wnd.c b/dlls/winmm/mciavi/wnd.c
new file mode 100644
index 0000000000000000000000000000000000000000..b39e28dd0ec739946f5ce9e9432a546744fb6722
--- /dev/null
+++ b/dlls/winmm/mciavi/wnd.c
@@ -0,0 +1,221 @@
+/* -*- tab-width: 8; c-basic-offset: 4 -*- */
+
+/*
+ * Digital video MCI Wine Driver
+ *
+ * Copyright 1999, 2000 Eric POUECH
+ */
+
+#include <string.h>
+#include "private_mciavi.h"
+#include "debugtools.h"
+
+DEFAULT_DEBUG_CHANNEL(mciavi);
+
+static LRESULT WINAPI MCIAVI_WindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
+{
+    TRACE("hwnd=%x msg=%x wparam=%x lparam=%lx\n", hWnd, uMsg, wParam, lParam);
+    
+    if (!(WINE_MCIAVI*)GetWindowLongA(hWnd, 0) && uMsg != WM_CREATE)
+	return DefWindowProcA(hWnd, uMsg, wParam, lParam);
+    
+    switch (uMsg) {
+    case WM_CREATE:
+	SetWindowLongA(hWnd, 0, (LPARAM)((CREATESTRUCTA*)lParam)->lpCreateParams);
+	return DefWindowProcA(hWnd, uMsg, wParam, lParam);
+	
+    case WM_DESTROY:
+	SetWindowLongA(hWnd, 0, 0);
+	return DefWindowProcA(hWnd, uMsg, wParam, lParam);
+	
+    case WM_ERASEBKGND:
+	{
+	    RECT	rect;
+	    GetClientRect(hWnd, &rect);
+	    FillRect((HDC)wParam, &rect, GetStockObject(BLACK_BRUSH));
+	}
+	break;
+    case WM_PAINT:
+        {
+            WINE_MCIAVI* wma = (WINE_MCIAVI*)GetWindowLongA(hWnd, 0);
+	    
+            /* the animation isn't playing, don't paint */
+	    if (wma->dwStatus == MCI_MODE_NOT_READY)
+		/* default paint handling */
+	    	return DefWindowProcA(hWnd, uMsg, wParam, lParam);
+	    
+            if (wParam) {
+                EnterCriticalSection(&wma->cs);
+                MCIAVI_PaintFrame(wma, (HDC)wParam);
+                LeaveCriticalSection(&wma->cs);
+            } else {
+	        PAINTSTRUCT ps;
+ 	        HDC hDC = BeginPaint(hWnd, &ps);
+		
+                EnterCriticalSection(&wma->cs);
+                MCIAVI_PaintFrame(wma, hDC);
+                LeaveCriticalSection(&wma->cs);
+		
+	        EndPaint(hWnd, &ps);
+	    }
+        }
+	break;
+	
+    default:
+	return DefWindowProcA(hWnd, uMsg, wParam, lParam);
+    }
+    return 0;
+}
+
+BOOL    MCIAVI_CreateWindow(WINE_MCIAVI* wma, DWORD dwFlags, LPMCI_DGV_OPEN_PARMSA lpOpenParms)
+{
+    WNDCLASSA 	wndClass;
+    HWND	hParent = 0;
+    DWORD	dwStyle = WS_OVERLAPPEDWINDOW;
+    int		p = CW_USEDEFAULT;
+
+    /* what should be done ? */
+    if (wma->hWnd) return TRUE;
+    
+    ZeroMemory(&wndClass, sizeof(WNDCLASSA));
+    wndClass.style         = CS_GLOBALCLASS | CS_DBLCLKS;
+    wndClass.lpfnWndProc   = (WNDPROC)MCIAVI_WindowProc;
+    wndClass.cbClsExtra    = 0;
+    wndClass.cbWndExtra    = sizeof(WINE_MCIAVI*);
+    wndClass.hCursor       = LoadCursorA(0, IDC_ARROWA);
+    wndClass.hbrBackground = (HBRUSH)(COLOR_BTNFACE + 1);
+    wndClass.lpszClassName = "MCIAVI";
+    
+    RegisterClassA(&wndClass);
+
+    if (dwFlags & MCI_DGV_OPEN_PARENT)	hParent = lpOpenParms->hWndParent;
+    if (dwFlags & MCI_DGV_OPEN_WS)	dwStyle = lpOpenParms->dwStyle;
+    if (dwStyle & WS_CHILD)		p = 0;
+
+    wma->hWnd = CreateWindowA("MCIAVI", "Wine MCI-AVI player", 
+			      dwStyle, p, p, 
+			      (wma->hic ? wma->outbih : wma->inbih)->biWidth, 
+			      (wma->hic ? wma->outbih : wma->inbih)->biHeight, 
+			      hParent, 0, MCIAVI_hInstance, wma);
+    return (BOOL)wma->hWnd;
+}
+
+/***************************************************************************
+ * 				MCIAVI_mciPut			[internal]
+ */
+DWORD	MCIAVI_mciPut(UINT wDevID, DWORD dwFlags, LPMCI_DGV_PUT_PARMS lpParms)
+{
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+    RECT		rc;
+    char		buffer[256];
+    
+    FIXME("(%04x, %08lX, %p) : stub\n", wDevID, dwFlags, lpParms);
+    
+    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
+    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
+    
+    if (dwFlags & MCI_DGV_RECT) {
+	rc = lpParms->rc;
+    } else {
+	SetRectEmpty(&rc);
+    }
+    
+    *buffer = 0;
+    if (dwFlags & MCI_DGV_PUT_CLIENT) {
+	strncat(buffer, "PUT_CLIENT", sizeof(buffer));
+    }
+    if (dwFlags & MCI_DGV_PUT_DESTINATION) {
+	strncat(buffer, "PUT_DESTINATION", sizeof(buffer));
+    }
+    if (dwFlags & MCI_DGV_PUT_FRAME) {
+	strncat(buffer, "PUT_FRAME", sizeof(buffer));
+    }
+    if (dwFlags & MCI_DGV_PUT_SOURCE) {
+	strncat(buffer, "PUT_SOURCE", sizeof(buffer));
+    }
+    if (dwFlags & MCI_DGV_PUT_VIDEO) {
+	strncat(buffer, "PUT_VIDEO", sizeof(buffer));
+    }
+    if (dwFlags & MCI_DGV_PUT_WINDOW) {
+	strncat(buffer, "PUT_WINDOW", sizeof(buffer));
+    }
+    TRACE("%s (%d,%d,%d,%d)\n", buffer, rc.left, rc.top, rc.right, rc.bottom);
+    
+    return 0;
+}
+
+/******************************************************************************
+ * 				MCIAVI_mciWhere			[internal]
+ */
+DWORD	MCIAVI_mciWhere(UINT wDevID, DWORD dwFlags, LPMCI_DGV_RECT_PARMS lpParms)
+{
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+    LPSTR		x = "";
+
+    TRACE("(%04x, %08lx, %p)\n", wDevID, dwFlags, lpParms);
+    
+    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
+    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
+    
+    if (dwFlags & MCI_DGV_WHERE_MAX) FIXME("Max NIY\n");
+
+    if (dwFlags & MCI_DGV_WHERE_DESTINATION) {
+	x = "Dest";
+	GetClientRect(wma->hWnd, &lpParms->rc);
+    }
+    if (dwFlags & MCI_DGV_WHERE_FRAME) {
+	FIXME(x = "Frame");
+	return MCIERR_UNRECOGNIZED_COMMAND;
+    }
+    if (dwFlags & MCI_DGV_WHERE_SOURCE) {
+	x = "Source";
+	lpParms->rc.left = lpParms->rc.top = 0;
+	lpParms->rc.right = wma->mah.dwWidth;
+	lpParms->rc.bottom = wma->mah.dwHeight;
+    }
+    if (dwFlags & MCI_DGV_WHERE_VIDEO) {
+	FIXME(x = "Video");
+	return MCIERR_UNRECOGNIZED_COMMAND;
+    }
+    if (dwFlags & MCI_DGV_WHERE_WINDOW) {
+	x = "Window";
+	GetClientRect(wma->hWnd, &lpParms->rc);
+    }
+    TRACE("%s -> (%d,%d,%d,%d)\n", 
+	  x, lpParms->rc.left, lpParms->rc.top, lpParms->rc.right, lpParms->rc.bottom);
+
+    return 0;
+}
+
+/***************************************************************************
+ * 				MCIAVI_mciWindow			[internal]
+ */
+DWORD	MCIAVI_mciWindow(UINT wDevID, DWORD dwFlags, LPMCI_DGV_WINDOW_PARMSA lpParms)
+{
+    WINE_MCIAVI*	wma = MCIAVI_mciGetOpenDev(wDevID);
+    
+    TRACE("(%04x, %08lX, %p)\n", wDevID, dwFlags, lpParms);
+    
+    if (lpParms == NULL)	return MCIERR_NULL_PARAMETER_BLOCK;
+    if (wma == NULL)		return MCIERR_INVALID_DEVICE_ID;
+    
+    if (dwFlags & MCI_DGV_WINDOW_HWND) {
+	FIXME("Setting hWnd to %08lx\n", (DWORD)lpParms->hWnd);
+#if 0
+	if (wma->hWnd) DestroyWindow(wma->hWnd);
+	/* is the window to be subclassed ? */
+	wma->hWnd = lpParms->hWnd;
+#endif
+    }
+    if (dwFlags & MCI_DGV_WINDOW_STATE) {
+	TRACE("Setting nCmdShow to %d\n", lpParms->nCmdShow);
+	ShowWindow(wma->hWnd, lpParms->nCmdShow);
+    }
+    if (dwFlags & MCI_DGV_WINDOW_TEXT) {
+	TRACE("Setting caption to '%s'\n", lpParms->lpstrText);
+	SetWindowTextA(wma->hWnd, lpParms->lpstrText);
+    }
+    
+    return 0;
+}
+
diff --git a/include/Makefile.in b/include/Makefile.in
index 372980fa3ec566b2344ddb9bc908122e9ba45288..4fe7b4c396f66dd46ebf444c5df7a9d6c6a58f63 100644
--- a/include/Makefile.in
+++ b/include/Makefile.in
@@ -36,6 +36,7 @@ INSTALLED_INCLUDES = \
 	lzexpand.h \
 	mapi.h \
 	mapidefs.h \
+	mciavi.h \
 	mcx.h \
 	mmreg.h \
 	mmsystem.h \
diff --git a/include/mciavi.h b/include/mciavi.h
new file mode 100644
index 0000000000000000000000000000000000000000..44116a3210786e88ea7b9a0b295635ae04edfb91
--- /dev/null
+++ b/include/mciavi.h
@@ -0,0 +1,25 @@
+#define MCI_MCIAVI_PLAY_WINDOW		0x01000000L
+#define MCI_MCIAVI_PLAY_FULLSCREEN	0x02000000L
+#define MCI_MCIAVI_PLAY_FULLBY2		0x04000000L
+
+#define MCI_AVI_STATUS_FRAMES_SKIPPED	0x8001L
+
+#define MCI_AVI_STATUS_LAST_PLAY_SPEED		0x8002L
+
+#define MCI_AVI_STATUS_AUDIO_BREAKS		0x8003L
+
+#define MCI_AVI_SETVIDEO_DRAW_PROCEDURE		0x8000L
+
+#define MCI_AVI_SETVIDEO_PALETTE_COLOR		0x8100L
+
+#define MCI_AVI_SETVIDEO_PALETTE_HALFTONE       0x0000FFFFL
+
+#define MCIERR_AVI_OLDAVIFORMAT		(MCIERR_CUSTOM_DRIVER_BASE + 100)
+#define MCIERR_AVI_NOTINTERLEAVED	(MCIERR_CUSTOM_DRIVER_BASE + 101)
+#define MCIERR_AVI_NODISPDIB		(MCIERR_CUSTOM_DRIVER_BASE + 102)
+#define MCIERR_AVI_CANTPLAYFULLSCREEN	(MCIERR_CUSTOM_DRIVER_BASE + 103)
+#define MCIERR_AVI_TOOBIGFORVGA		(MCIERR_CUSTOM_DRIVER_BASE + 104)
+#define MCIERR_AVI_NOCOMPRESSOR         (MCIERR_CUSTOM_DRIVER_BASE + 105)
+#define MCIERR_AVI_DISPLAYERROR         (MCIERR_CUSTOM_DRIVER_BASE + 106)
+#define MCIERR_AVI_AUDIOERROR		(MCIERR_CUSTOM_DRIVER_BASE + 107)
+#define MCIERR_AVI_BADPALETTE		(MCIERR_CUSTOM_DRIVER_BASE + 108)
diff --git a/include/vfw.h b/include/vfw.h
index 1a5c197ef5354b6c6732e84f4a11e4380007ab18..e0492f4a96ab1db6ae89f87f605a8a30b21d4620 100644
--- a/include/vfw.h
+++ b/include/vfw.h
@@ -4,7 +4,6 @@
 #include "windef.h"
 #include "mmsystem.h"
 #include "wingdi.h"
-#include "unknwn.h"
 
 #define VFWAPI	WINAPI
 #define VFWAPIV	WINAPIV
@@ -15,26 +14,10 @@ extern "C" {
 
 typedef HANDLE HDRAWDIB;
 
-HWND        VFWAPIV MCIWndCreateA(HWND hwndParent, HINSTANCE hInstance, DWORD dwStyle, LPCSTR szFile);
-HWND        VFWAPIV MCIWndCreateW(HWND hwndParent, HINSTANCE hInstance, DWORD dwStyle, LPCWSTR szFile);
-#define     MCIWndCreate WINELIB_NAME_AW(MCIWndCreate)
 DWORD       VFWAPI  VideoForWindowsVersion(void);
 LONG 	    VFWAPI  InitVFW(void);
 LONG	    VFWAPI  TermVFW(void);
 
-#ifndef mmioFOURCC
-#define mmioFOURCC( ch0, ch1, ch2, ch3 )				\
-	( (DWORD)(BYTE)(ch0) | ( (DWORD)(BYTE)(ch1) << 8 ) |		\
-	( (DWORD)(BYTE)(ch2) << 16 ) | ( (DWORD)(BYTE)(ch3) << 24 ) )
-#endif
-
-#ifndef aviTWOCC
-#define aviTWOCC(ch0, ch1) ((WORD)(BYTE)(ch0) | ((WORD)(BYTE)(ch1) << 8))
-#endif
-
-#define ICTYPE_VIDEO	mmioFOURCC('v', 'i', 'd', 'c')
-#define ICTYPE_AUDIO	mmioFOURCC('a', 'u', 'd', 'c')
-
 /*****************************************************************************
  * Predeclare the interfaces
  */
@@ -44,7 +27,7 @@ typedef struct IGetFrame IGetFrame,*PGETFRAME;
 
 /* Installable Compressor Manager */
 
-DECLARE_OLD_HANDLE(HIC);
+DECLARE_HANDLE(HIC);
 
 #ifdef __WINE__
 /* HIC struct (same layout as Win95 one) */
@@ -729,6 +712,22 @@ LPVOID VFWAPI ICSeqCompressFrame(PCOMPVARS pc, UINT uiFlags, LPVOID lpBits,
 void VFWAPI ICCompressorFree(PCOMPVARS pc);
 
 /********************* AVIFILE function declarations *************************/
+
+#ifndef mmioFOURCC
+#define mmioFOURCC( ch0, ch1, ch2, ch3 )				\
+	( (DWORD)(BYTE)(ch0) | ( (DWORD)(BYTE)(ch1) << 8 ) |		\
+	( (DWORD)(BYTE)(ch2) << 16 ) | ( (DWORD)(BYTE)(ch3) << 24 ) )
+#endif
+
+#ifndef aviTWOCC
+#define aviTWOCC(ch0, ch1) ((WORD)(BYTE)(ch0) | ((WORD)(BYTE)(ch1) << 8))
+#endif
+
+typedef WORD TWOCC;
+
+#define ICTYPE_VIDEO		mmioFOURCC('v', 'i', 'd', 'c')
+#define ICTYPE_AUDIO		mmioFOURCC('a', 'u', 'd', 'c')
+
 #define formtypeAVI             mmioFOURCC('A', 'V', 'I', ' ')
 #define listtypeAVIHEADER       mmioFOURCC('h', 'd', 'r', 'l')
 #define ckidAVIMAINHDR          mmioFOURCC('a', 'v', 'i', 'h')
@@ -757,6 +756,15 @@ void VFWAPI ICCompressorFree(PCOMPVARS pc);
 /* Chunk id to use for extra chunks for padding. */
 #define ckidAVIPADDING          mmioFOURCC('J', 'U', 'N', 'K')
 
+#define FromHex(n)		(((n) >= 'A') ? ((n) + 10 - 'A') : ((n) - '0'))
+#define StreamFromFOURCC(fcc)	((WORD)((FromHex(LOBYTE(LOWORD(fcc))) << 4) + \
+					(FromHex(HIBYTE(LOWORD(fcc))))))
+#define TWOCCFromFOURCC(fcc)    HIWORD(fcc)
+#define ToHex(n)		((BYTE)(((n) > 9) ? ((n) - 10 + 'A') : ((n) + '0')))
+#define MAKEAVICKID(tcc, stream) \
+                                MAKELONG((ToHex((stream) & 0x0f) << 8) | \
+			                 (ToHex(((stream) & 0xf0) >> 4)), tcc)
+
 /* AVIFileHdr.dwFlags */
 #define AVIF_HASINDEX		0x00000010	/* Index at end of file? */
 #define AVIF_MUSTUSEINDEX	0x00000020
@@ -942,7 +950,7 @@ typedef struct {
     DWORD	dwInterleaveEvery;	/* for non-video streams only */
 } AVICOMPRESSOPTIONS, *LPAVICOMPRESSOPTIONS,*PAVICOMPRESSOPTIONS;
 
-
+#include "ole2.h"
 
 #define DEFINE_AVIGUID(name, l, w1, w2) \
     DEFINE_GUID(name, l, w1, w2, 0xC0,0,0,0,0,0,0,0x46)
@@ -1117,6 +1125,229 @@ ICOM_DEFINE(IGetFrame,IUnknown)
 #define AVIERR_USERABORT	MAKE_AVIERR(198)
 #define AVIERR_ERROR		MAKE_AVIERR(199)
 
+HWND        VFWAPIV MCIWndCreateA(HWND hwndParent, HINSTANCE hInstance, DWORD dwStyle, LPCSTR szFile);
+HWND        VFWAPIV MCIWndCreateW(HWND hwndParent, HINSTANCE hInstance, DWORD dwStyle, LPCWSTR szFile);
+#define     MCIWndCreate WINELIB_NAME_AW(MCIWndCreate)
+
+#define MCIWNDOPENF_NEW			0x0001
+
+#define MCIWNDF_NOAUTOSIZEWINDOW	0x0001
+#define MCIWNDF_NOPLAYBAR		0x0002
+#define MCIWNDF_NOAUTOSIZEMOVIE		0x0004
+#define MCIWNDF_NOMENU			0x0008
+#define MCIWNDF_SHOWNAME		0x0010
+#define MCIWNDF_SHOWPOS			0x0020
+#define MCIWNDF_SHOWMODE		0x0040
+#define MCIWNDF_SHOWALL			0x0070
+
+#define MCIWNDF_NOTIFYMODE		0x0100
+#define MCIWNDF_NOTIFYPOS		0x0200
+#define MCIWNDF_NOTIFYSIZE		0x0400
+#define MCIWNDF_NOTIFYERROR		0x1000
+#define MCIWNDF_NOTIFYALL		0x1F00
+
+#define MCIWNDF_NOTIFYANSI		0x0080
+
+#define MCIWNDF_NOTIFYMEDIAA		0x0880
+#define MCIWNDF_NOTIFYMEDIAW		0x0800
+#define MCIWNDF_NOTIFYMEDIA WINELIB_NAME_AW(MCIWNDF_NOTIFYMEDIA)
+
+#define MCIWNDF_RECORD			0x2000
+#define MCIWNDF_NOERRORDLG		0x4000
+#define MCIWNDF_NOOPEN			0x8000
+
+#ifdef __cplusplus
+#define MCIWndSM ::SendMessage
+#else
+#define MCIWndSM SendMessage
+#endif
+
+#define MCIWndCanPlay(hWnd)         (BOOL)MCIWndSM(hWnd,MCIWNDM_CAN_PLAY,0,0)
+#define MCIWndCanRecord(hWnd)       (BOOL)MCIWndSM(hWnd,MCIWNDM_CAN_RECORD,0,0)
+#define MCIWndCanSave(hWnd)         (BOOL)MCIWndSM(hWnd,MCIWNDM_CAN_SAVE,0,0)
+#define MCIWndCanWindow(hWnd)       (BOOL)MCIWndSM(hWnd,MCIWNDM_CAN_WINDOW,0,0)
+#define MCIWndCanEject(hWnd)        (BOOL)MCIWndSM(hWnd,MCIWNDM_CAN_EJECT,0,0)
+#define MCIWndCanConfig(hWnd)       (BOOL)MCIWndSM(hWnd,MCIWNDM_CAN_CONFIG,0,0)
+#define MCIWndPaletteKick(hWnd)     (BOOL)MCIWndSM(hWnd,MCIWNDM_PALETTEKICK,0,0)
+
+#define MCIWndSave(hWnd,szFile)	    (LONG)MCIWndSM(hWnd,MCI_SAVE,0,(LPARAM)(LPVOID)(szFile))
+#define MCIWndSaveDialog(hWnd)      MCIWndSave(hWnd,-1)
+
+#define MCIWndNew(hWnd,lp)          (LONG)MCIWndSM(hWnd,MCIWNDM_NEW,0,(LPARAM)(LPVOID)(lp))
+
+#define MCIWndRecord(hWnd)          (LONG)MCIWndSM(hWnd,MCI_RECORD,0,0)
+#define MCIWndOpen(hWnd,sz,f)       (LONG)MCIWndSM(hWnd,MCIWNDM_OPEN,(WPARAM)(UINT)(f),(LPARAM)(LPVOID)(sz))
+#define MCIWndOpenDialog(hWnd)      MCIWndOpen(hWnd,-1,0)
+#define MCIWndClose(hWnd)           (LONG)MCIWndSM(hWnd,MCI_CLOSE,0,0)
+#define MCIWndPlay(hWnd)            (LONG)MCIWndSM(hWnd,MCI_PLAY,0,0)
+#define MCIWndStop(hWnd)            (LONG)MCIWndSM(hWnd,MCI_STOP,0,0)
+#define MCIWndPause(hWnd)           (LONG)MCIWndSM(hWnd,MCI_PAUSE,0,0)
+#define MCIWndResume(hWnd)          (LONG)MCIWndSM(hWnd,MCI_RESUME,0,0)
+#define MCIWndSeek(hWnd,lPos)       (LONG)MCIWndSM(hWnd,MCI_SEEK,0,(LPARAM)(LONG)(lPos))
+#define MCIWndEject(hWnd)           (LONG)MCIWndSM(hWnd,MCIWNDM_EJECT,0,0)
+
+#define MCIWndHome(hWnd)            MCIWndSeek(hWnd,MCIWND_START)
+#define MCIWndEnd(hWnd)             MCIWndSeek(hWnd,MCIWND_END)
+
+#define MCIWndGetSource(hWnd,prc)   (LONG)MCIWndSM(hWnd,MCIWNDM_GET_SOURCE,0,(LPARAM)(LPRECT)(prc))
+#define MCIWndPutSource(hWnd,prc)   (LONG)MCIWndSM(hWnd,MCIWNDM_PUT_SOURCE,0,(LPARAM)(LPRECT)(prc))
+
+#define MCIWndGetDest(hWnd,prc)     (LONG)MCIWndSM(hWnd,MCIWNDM_GET_DEST,0,(LPARAM)(LPRECT)(prc))
+#define MCIWndPutDest(hWnd,prc)     (LONG)MCIWndSM(hWnd,MCIWNDM_PUT_DEST,0,(LPARAM)(LPRECT)(prc))
+
+#define MCIWndPlayReverse(hWnd)     (LONG)MCIWndSM(hWnd,MCIWNDM_PLAYREVERSE,0,0)
+#define MCIWndPlayFrom(hWnd,lPos)   (LONG)MCIWndSM(hWnd,MCIWNDM_PLAYFROM,0,(LPARAM)(LONG)(lPos))
+#define MCIWndPlayTo(hWnd,lPos)     (LONG)MCIWndSM(hWnd,MCIWNDM_PLAYTO,  0,(LPARAM)(LONG)(lPos))
+#define MCIWndPlayFromTo(hWnd,lStart,lEnd) (MCIWndSeek(hWnd,lStart),MCIWndPlayTo(hWnd,lEnd))
+
+#define MCIWndGetDeviceID(hWnd)     (UINT)MCIWndSM(hWnd,MCIWNDM_GETDEVICEID,0,0)
+#define MCIWndGetAlias(hWnd)        (UINT)MCIWndSM(hWnd,MCIWNDM_GETALIAS,0,0)
+#define MCIWndGetMode(hWnd,lp,len)  (LONG)MCIWndSM(hWnd,MCIWNDM_GETMODE,(WPARAM)(UINT)(len),(LPARAM)(LPTSTR)(lp))
+#define MCIWndGetPosition(hWnd)     (LONG)MCIWndSM(hWnd,MCIWNDM_GETPOSITION,0,0)
+#define MCIWndGetPositionString(hWnd,lp,len) (LONG)MCIWndSM(hWnd,MCIWNDM_GETPOSITION,(WPARAM)(UINT)(len),(LPARAM)(LPTSTR)(lp))
+#define MCIWndGetStart(hWnd)        (LONG)MCIWndSM(hWnd,MCIWNDM_GETSTART,0,0)
+#define MCIWndGetLength(hWnd)       (LONG)MCIWndSM(hWnd,MCIWNDM_GETLENGTH,0,0)
+#define MCIWndGetEnd(hWnd)          (LONG)MCIWndSM(hWnd,MCIWNDM_GETEND,0,0)
+
+#define MCIWndStep(hWnd,n)          (LONG)MCIWndSM(hWnd,MCI_STEP,0,(LPARAM)(long)(n))
+
+#define MCIWndDestroy(hWnd)         (VOID)MCIWndSM(hWnd,WM_CLOSE,0,0)
+#define MCIWndSetZoom(hWnd,iZoom)   (VOID)MCIWndSM(hWnd,MCIWNDM_SETZOOM,0,(LPARAM)(UINT)(iZoom))
+#define MCIWndGetZoom(hWnd)         (UINT)MCIWndSM(hWnd,MCIWNDM_GETZOOM,0,0)
+#define MCIWndSetVolume(hWnd,iVol)  (LONG)MCIWndSM(hWnd,MCIWNDM_SETVOLUME,0,(LPARAM)(UINT)(iVol))
+#define MCIWndGetVolume(hWnd)       (LONG)MCIWndSM(hWnd,MCIWNDM_GETVOLUME,0,0)
+#define MCIWndSetSpeed(hWnd,iSpeed) (LONG)MCIWndSM(hWnd,MCIWNDM_SETSPEED,0,(LPARAM)(UINT)(iSpeed))
+#define MCIWndGetSpeed(hWnd)        (LONG)MCIWndSM(hWnd,MCIWNDM_GETSPEED,0,0)
+#define MCIWndSetTimeFormat(hWnd,lp) (LONG)MCIWndSM(hWnd,MCIWNDM_SETTIMEFORMAT,0,(LPARAM)(LPTSTR)(lp))
+#define MCIWndGetTimeFormat(hWnd,lp,len) (LONG)MCIWndSM(hWnd,MCIWNDM_GETTIMEFORMAT,(WPARAM)(UINT)(len),(LPARAM)(LPTSTR)(lp))
+#define MCIWndValidateMedia(hWnd)   (VOID)MCIWndSM(hWnd,MCIWNDM_VALIDATEMEDIA,0,0)
+
+#define MCIWndSetRepeat(hWnd,f)     (void)MCIWndSM(hWnd,MCIWNDM_SETREPEAT,0,(LPARAM)(BOOL)(f))
+#define MCIWndGetRepeat(hWnd)       (BOOL)MCIWndSM(hWnd,MCIWNDM_GETREPEAT,0,0)
+
+#define MCIWndUseFrames(hWnd)       MCIWndSetTimeFormat(hWnd,TEXT("frames"))
+#define MCIWndUseTime(hWnd)         MCIWndSetTimeFormat(hWnd,TEXT("ms"))
+
+#define MCIWndSetActiveTimer(hWnd,active)				\
+	(VOID)MCIWndSM(hWnd,MCIWNDM_SETACTIVETIMER,			\
+	(WPARAM)(UINT)(active),0L)
+#define MCIWndSetInactiveTimer(hWnd,inactive)				\
+	(VOID)MCIWndSM(hWnd,MCIWNDM_SETINACTIVETIMER,			\
+	(WPARAM)(UINT)(inactive),0L)
+#define MCIWndSetTimers(hWnd,active,inactive)				\
+	    (VOID)MCIWndSM(hWnd,MCIWNDM_SETTIMERS,(WPARAM)(UINT)(active),\
+	    (LPARAM)(UINT)(inactive))
+#define MCIWndGetActiveTimer(hWnd)					\
+	(UINT)MCIWndSM(hWnd,MCIWNDM_GETACTIVETIMER,0,0L);
+#define MCIWndGetInactiveTimer(hWnd)					\
+	(UINT)MCIWndSM(hWnd,MCIWNDM_GETINACTIVETIMER,0,0L);
+
+#define MCIWndRealize(hWnd,fBkgnd) (LONG)MCIWndSM(hWnd,MCIWNDM_REALIZE,(WPARAM)(BOOL)(fBkgnd),0)
+
+#define MCIWndSendString(hWnd,sz)  (LONG)MCIWndSM(hWnd,MCIWNDM_SENDSTRING,0,(LPARAM)(LPTSTR)(sz))
+#define MCIWndReturnString(hWnd,lp,len)  (LONG)MCIWndSM(hWnd,MCIWNDM_RETURNSTRING,(WPARAM)(UINT)(len),(LPARAM)(LPVOID)(lp))
+#define MCIWndGetError(hWnd,lp,len) (LONG)MCIWndSM(hWnd,MCIWNDM_GETERROR,(WPARAM)(UINT)(len),(LPARAM)(LPVOID)(lp))
+
+#define MCIWndGetPalette(hWnd)      (HPALETTE)MCIWndSM(hWnd,MCIWNDM_GETPALETTE,0,0)
+#define MCIWndSetPalette(hWnd,hpal) (LONG)MCIWndSM(hWnd,MCIWNDM_SETPALETTE,(WPARAM)(HPALETTE)(hpal),0)
+
+#define MCIWndGetFileName(hWnd,lp,len) (LONG)MCIWndSM(hWnd,MCIWNDM_GETFILENAME,(WPARAM)(UINT)(len),(LPARAM)(LPVOID)(lp))
+#define MCIWndGetDevice(hWnd,lp,len)   (LONG)MCIWndSM(hWnd,MCIWNDM_GETDEVICE,(WPARAM)(UINT)(len),(LPARAM)(LPVOID)(lp))
+
+#define MCIWndGetStyles(hWnd) (UINT)MCIWndSM(hWnd,MCIWNDM_GETSTYLES,0,0L)
+#define MCIWndChangeStyles(hWnd,mask,value) (LONG)MCIWndSM(hWnd,MCIWNDM_CHANGESTYLES,(WPARAM)(UINT)(mask),(LPARAM)(LONG)(value))
+
+#define MCIWndOpenInterface(hWnd,pUnk)  (LONG)MCIWndSM(hWnd,MCIWNDM_OPENINTERFACE,0,(LPARAM)(LPUNKNOWN)(pUnk))
+
+#define MCIWndSetOwner(hWnd,hWndP)  (LONG)MCIWndSM(hWnd,MCIWNDM_SETOWNER,(WPARAM)(hWndP),0)
+
+#define MCIWNDM_GETDEVICEID	(WM_USER + 100)
+#define MCIWNDM_GETSTART	(WM_USER + 103)
+#define MCIWNDM_GETLENGTH	(WM_USER + 104)
+#define MCIWNDM_GETEND		(WM_USER + 105)
+#define MCIWNDM_EJECT		(WM_USER + 107)
+#define MCIWNDM_SETZOOM		(WM_USER + 108)
+#define MCIWNDM_GETZOOM         (WM_USER + 109)
+#define MCIWNDM_SETVOLUME	(WM_USER + 110)
+#define MCIWNDM_GETVOLUME	(WM_USER + 111)
+#define MCIWNDM_SETSPEED	(WM_USER + 112)
+#define MCIWNDM_GETSPEED	(WM_USER + 113)
+#define MCIWNDM_SETREPEAT	(WM_USER + 114)
+#define MCIWNDM_GETREPEAT	(WM_USER + 115)
+#define MCIWNDM_REALIZE         (WM_USER + 118)
+#define MCIWNDM_VALIDATEMEDIA   (WM_USER + 121)
+#define MCIWNDM_PLAYFROM	(WM_USER + 122)
+#define MCIWNDM_PLAYTO          (WM_USER + 123)
+#define MCIWNDM_GETPALETTE      (WM_USER + 126)
+#define MCIWNDM_SETPALETTE      (WM_USER + 127)
+#define MCIWNDM_SETTIMERS	(WM_USER + 129)
+#define MCIWNDM_SETACTIVETIMER	(WM_USER + 130)
+#define MCIWNDM_SETINACTIVETIMER (WM_USER + 131)
+#define MCIWNDM_GETACTIVETIMER	(WM_USER + 132)
+#define MCIWNDM_GETINACTIVETIMER (WM_USER + 133)
+#define MCIWNDM_CHANGESTYLES	(WM_USER + 135)
+#define MCIWNDM_GETSTYLES	(WM_USER + 136)
+#define MCIWNDM_GETALIAS	(WM_USER + 137)
+#define MCIWNDM_PLAYREVERSE	(WM_USER + 139)
+#define MCIWNDM_GET_SOURCE      (WM_USER + 140)
+#define MCIWNDM_PUT_SOURCE      (WM_USER + 141)
+#define MCIWNDM_GET_DEST        (WM_USER + 142)
+#define MCIWNDM_PUT_DEST        (WM_USER + 143)
+#define MCIWNDM_CAN_PLAY        (WM_USER + 144)
+#define MCIWNDM_CAN_WINDOW      (WM_USER + 145)
+#define MCIWNDM_CAN_RECORD      (WM_USER + 146)
+#define MCIWNDM_CAN_SAVE        (WM_USER + 147)
+#define MCIWNDM_CAN_EJECT       (WM_USER + 148)
+#define MCIWNDM_CAN_CONFIG      (WM_USER + 149)
+#define MCIWNDM_PALETTEKICK     (WM_USER + 150)
+#define MCIWNDM_OPENINTERFACE	(WM_USER + 151)
+#define MCIWNDM_SETOWNER	(WM_USER + 152)
+
+#define MCIWNDM_SENDSTRINGA	(WM_USER + 101)
+#define MCIWNDM_GETPOSITIONA	(WM_USER + 102)
+#define MCIWNDM_GETMODEA	(WM_USER + 106)
+#define MCIWNDM_SETTIMEFORMATA  (WM_USER + 119)
+#define MCIWNDM_GETTIMEFORMATA  (WM_USER + 120)
+#define MCIWNDM_GETFILENAMEA    (WM_USER + 124)
+#define MCIWNDM_GETDEVICEA      (WM_USER + 125)
+#define MCIWNDM_GETERRORA       (WM_USER + 128)
+#define MCIWNDM_NEWA		(WM_USER + 134)
+#define MCIWNDM_RETURNSTRINGA	(WM_USER + 138)
+#define MCIWNDM_OPENA		(WM_USER + 153)
+
+#define MCIWNDM_SENDSTRINGW	(WM_USER + 201)
+#define MCIWNDM_GETPOSITIONW	(WM_USER + 202)
+#define MCIWNDM_GETMODEW	(WM_USER + 206)
+#define MCIWNDM_SETTIMEFORMATW  (WM_USER + 219)
+#define MCIWNDM_GETTIMEFORMATW  (WM_USER + 220)
+#define MCIWNDM_GETFILENAMEW    (WM_USER + 224)
+#define MCIWNDM_GETDEVICEW      (WM_USER + 225)
+#define MCIWNDM_GETERRORW       (WM_USER + 228)
+#define MCIWNDM_NEWW		(WM_USER + 234)
+#define MCIWNDM_RETURNSTRINGW	(WM_USER + 238)
+#define MCIWNDM_OPENW		(WM_USER + 252)
+
+#define MCIWNDM_SENDSTRING	WINELIB_NAME_AW(MCIWNDM_SENDSTRING)
+#define MCIWNDM_GETPOSITION	WINELIB_NAME_AW(MCIWNDM_GETPOSITION)
+#define MCIWNDM_GETMODE		WINELIB_NAME_AW(MCIWNDM_GETMODE)
+#define MCIWNDM_SETTIMEFORMAT	WINELIB_NAME_AW(MCIWNDM_SETTIMEFORMAT)
+#define MCIWNDM_GETTIMEFORMAT	WINELIB_NAME_AW(MCIWNDM_GETTIMEFORMAT)
+#define MCIWNDM_GETFILENAME	WINELIB_NAME_AW(MCIWNDM_GETFILENAME)
+#define MCIWNDM_GETDEVICE	WINELIB_NAME_AW(MCIWNDM_GETDEVICE)
+#define MCIWNDM_GETERROR	WINELIB_NAME_AW(MCIWNDM_GETERROR)
+#define MCIWNDM_NEW		WINELIB_NAME_AW(MCIWNDM_NEW)
+#define MCIWNDM_RETURNSTRING	WINELIB_NAME_AW(MCIWNDM_RETURNSTRING)
+#define MCIWNDM_OPEN		WINELIB_NAME_AW(MCIWNDM_OPEN)
+
+#define MCIWNDM_NOTIFYMODE      (WM_USER + 200)
+#define MCIWNDM_NOTIFYPOS	(WM_USER + 201)
+#define MCIWNDM_NOTIFYSIZE	(WM_USER + 202)
+#define MCIWNDM_NOTIFYMEDIA     (WM_USER + 203)
+#define MCIWNDM_NOTIFYERROR     (WM_USER + 205)
+
+#define MCIWND_START                -1
+#define MCIWND_END                  -2
+
 /********************************************
  * DrawDib declarations
  */