Wine-20041201 vendor drop
Added: vendor/wine/dlls/winmm/
Added: vendor/wine/dlls/winmm/current/
Added: vendor/wine/dlls/winmm/current/Makefile.in
Added: vendor/wine/dlls/winmm/current/driver.c
Added: vendor/wine/dlls/winmm/current/joystick.c
Added: vendor/wine/dlls/winmm/current/lolvldrv.c
Added: vendor/wine/dlls/winmm/current/mci.c
Added: vendor/wine/dlls/winmm/current/message16.c
Added: vendor/wine/dlls/winmm/current/midimap/
Added: vendor/wine/dlls/winmm/current/midimap/.cvsignore
Added: vendor/wine/dlls/winmm/current/midimap/Makefile.in
Added: vendor/wine/dlls/winmm/current/midimap/midimap.c
Added: vendor/wine/dlls/winmm/current/midimap/midimap.drv.spec
Added: vendor/wine/dlls/winmm/current/mmio.c
Added: vendor/wine/dlls/winmm/current/mmsystem.c
Added: vendor/wine/dlls/winmm/current/mmsystem.spec
Added: vendor/wine/dlls/winmm/current/playsound.c
Added: vendor/wine/dlls/winmm/current/sound.spec
Added: vendor/wine/dlls/winmm/current/sound16.c
Added: vendor/wine/dlls/winmm/current/time.c
Added: vendor/wine/dlls/winmm/current/wavemap/
Added: vendor/wine/dlls/winmm/current/wavemap/.cvsignore
Added: vendor/wine/dlls/winmm/current/wavemap/Makefile.in
Added: vendor/wine/dlls/winmm/current/wavemap/msacm.drv.spec
Added: vendor/wine/dlls/winmm/current/wavemap/wavemap.c
Added: vendor/wine/dlls/winmm/current/winemm.h
Added: vendor/wine/dlls/winmm/current/winemm16.h
Added: vendor/wine/dlls/winmm/current/winmm.c
Added: vendor/wine/dlls/winmm/current/winmm.spec
Added: vendor/wine/dlls/winmm/current/winmm_Cs.rc
Added: vendor/wine/dlls/winmm/current/winmm_De.rc
Added: vendor/wine/dlls/winmm/current/winmm_En.rc
Added: vendor/wine/dlls/winmm/current/winmm_Es.rc
Added: vendor/wine/dlls/winmm/current/winmm_Fr.rc
Added: vendor/wine/dlls/winmm/current/winmm_It.rc
Added: vendor/wine/dlls/winmm/current/winmm_Ja.rc
Added: vendor/wine/dlls/winmm/current/winmm_Nl.rc
Added: vendor/wine/dlls/winmm/current/winmm_Pt.rc
Added: vendor/wine/dlls/winmm/current/winmm_Ru.rc
Added: vendor/wine/dlls/winmm/current/winmm_Si.rc
Added: vendor/wine/dlls/winmm/current/winmm_Sk.rc
Added: vendor/wine/dlls/winmm/current/winmm_res.rc

Added: vendor/wine/dlls/winmm/current/Makefile.in
--- vendor/wine/dlls/winmm/current/Makefile.in	2004-12-31 16:30:04 UTC (rev 12637)
+++ vendor/wine/dlls/winmm/current/Makefile.in	2004-12-31 16:34:31 UTC (rev 12638)
@@ -0,0 +1,34 @@
+EXTRADEFS = -D_WINMM_
+TOPSRCDIR = @top_srcdir@
+TOPOBJDIR = ../..
+SRCDIR    = @srcdir@
+VPATH     = @srcdir@
+MODULE    = winmm.dll
+IMPORTS   = user32 advapi32 kernel32 ntdll
+
+C_SRCS = \
+	driver.c \
+	joystick.c \
+	lolvldrv.c \
+	mci.c \
+	mmio.c \
+	playsound.c \
+	time.c \
+	winmm.c
+
+C_SRCS16 = \
+	message16.c \
+	mmsystem.c \
+	sound16.c
+
+SPEC_SRCS16 = \
+	mmsystem.spec \
+	sound.spec
+
+RC_SRCS = winmm_res.rc
+
+SUBDIRS = tests
+
+@MAKE_DLL_RULES@
+
+### Dependencies:

Added: vendor/wine/dlls/winmm/current/driver.c
--- vendor/wine/dlls/winmm/current/driver.c	2004-12-31 16:30:04 UTC (rev 12637)
+++ vendor/wine/dlls/winmm/current/driver.c	2004-12-31 16:34:31 UTC (rev 12638)
@@ -0,0 +1,567 @@
+/* -*- tab-width: 8; c-basic-offset: 4 -*- */
+
+/*
+ * WINE Drivers functions
+ *
+ * Copyright 1994 Martin Ayotte
+ * Copyright 1998 Marcus Meissner
+ * Copyright 1999 Eric Pouech
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+
+#include <string.h>
+#include <stdarg.h>
+#include "windef.h"
+#include "winbase.h"
+#include "wingdi.h"
+#include "winuser.h"
+#include "winnls.h"
+#include "winreg.h"
+#include "mmddk.h"
+#include "winemm.h"
+#include "wine/debug.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(driver);
+
+#define HKLM_BASE "Software\\Microsoft\\Windows NT\\CurrentVersion"
+
+static LPWINE_DRIVER   lpDrvItemList  /* = NULL */;
+
+WINE_MMTHREAD*  (*pFnGetMMThread16)(UINT16 h) /* = NULL */;
+LPWINE_DRIVER   (*pFnOpenDriver16)(LPCSTR,LPCSTR,LPARAM) /* = NULL */;
+LRESULT         (*pFnCloseDriver16)(UINT16,LPARAM,LPARAM) /* = NULL */;
+LRESULT         (*pFnSendMessage16)(UINT16,UINT,LPARAM,LPARAM) /* = NULL */;
+
+/**************************************************************************
+ *			DRIVER_GetNumberOfModuleRefs		[internal]
+ *
+ * Returns the number of open drivers which share the same module.
+ */
+static	unsigned DRIVER_GetNumberOfModuleRefs(HMODULE hModule, WINE_DRIVER** found)
+{
+    LPWINE_DRIVER	lpDrv;
+    unsigned		count = 0;
+
+    if (found) *found = NULL;
+    for (lpDrv = lpDrvItemList; lpDrv; lpDrv = lpDrv->lpNextItem)
+    {
+	if (!(lpDrv->dwFlags & WINE_GDF_16BIT) && lpDrv->d.d32.hModule == hModule)
+        {
+            if (found && !*found) *found = lpDrv;
+	    count++;
+	}
+    }
+    return count;
+}
+
+/**************************************************************************
+ *				DRIVER_FindFromHDrvr		[internal]
+ *
+ * From a hDrvr being 32 bits, returns the WINE internal structure.
+ */
+LPWINE_DRIVER	DRIVER_FindFromHDrvr(HDRVR hDrvr)
+{
+    LPWINE_DRIVER	d = (LPWINE_DRIVER)hDrvr;
+
+    if (hDrvr && HeapValidate(GetProcessHeap(), 0, d) && d->dwMagic == WINE_DI_MAGIC) {
+	return d;
+    }
+    return NULL;
+}
+
+/**************************************************************************
+ *				DRIVER_SendMessage		[internal]
+ */
+static LRESULT inline DRIVER_SendMessage(LPWINE_DRIVER lpDrv, UINT msg,
+                                         LPARAM lParam1, LPARAM lParam2)
+{
+    LRESULT		ret = 0;
+
+    if (lpDrv->dwFlags & WINE_GDF_16BIT) {
+        /* no need to check mmsystem presence: the driver must have been opened as a 16 bit one,
+         */
+        if (pFnSendMessage16)
+            ret = pFnSendMessage16(lpDrv->d.d16.hDriver16, msg, lParam1, lParam2);
+    } else {
+        TRACE("Before call32 proc=%p drvrID=%08lx hDrv=%p wMsg=%04x p1=%08lx p2=%08lx\n", 
+              lpDrv->d.d32.lpDrvProc, lpDrv->d.d32.dwDriverID, (HDRVR)lpDrv, msg, lParam1, lParam2);
+        ret = lpDrv->d.d32.lpDrvProc(lpDrv->d.d32.dwDriverID, (HDRVR)lpDrv, msg, lParam1, lParam2);
+        TRACE("After  call32 proc=%p drvrID=%08lx hDrv=%p wMsg=%04x p1=%08lx p2=%08lx => %08lx\n", 
+              lpDrv->d.d32.lpDrvProc, lpDrv->d.d32.dwDriverID, (HDRVR)lpDrv, msg, lParam1, lParam2, ret);
+    }
+    return ret;
+}
+
+/**************************************************************************
+ *				SendDriverMessage		[WINMM.@]
+ *				DrvSendMessage			[WINMM.@]
+ */
+LRESULT WINAPI SendDriverMessage(HDRVR hDriver, UINT msg, LPARAM lParam1,
+				 LPARAM lParam2)
+{
+    LPWINE_DRIVER	lpDrv;
+    LRESULT 		retval = 0;
+
+    TRACE("(%p, %04X, %08lX, %08lX)\n", hDriver, msg, lParam1, lParam2);
+
+    if ((lpDrv = DRIVER_FindFromHDrvr(hDriver)) != NULL) {
+	retval = DRIVER_SendMessage(lpDrv, msg, lParam1, lParam2);
+    } else {
+	WARN("Bad driver handle %p\n", hDriver);
+    }
+    TRACE("retval = %ld\n", retval);
+
+    return retval;
+}
+
+/**************************************************************************
+ *				DRIVER_RemoveFromList		[internal]
+ *
+ * Generates all the logic to handle driver closure / deletion
+ * Removes a driver struct to the list of open drivers.
+ */
+static	BOOL	DRIVER_RemoveFromList(LPWINE_DRIVER lpDrv)
+{
+    if (!(lpDrv->dwFlags & WINE_GDF_16BIT)) {
+        /* last of this driver in list ? */
+	if (DRIVER_GetNumberOfModuleRefs(lpDrv->d.d32.hModule, NULL) == 1) {
+	    DRIVER_SendMessage(lpDrv, DRV_DISABLE, 0L, 0L);
+	    DRIVER_SendMessage(lpDrv, DRV_FREE,    0L, 0L);
+	}
+    }
+
+    if (lpDrv->lpPrevItem)
+	lpDrv->lpPrevItem->lpNextItem = lpDrv->lpNextItem;
+    else
+	lpDrvItemList = lpDrv->lpNextItem;
+    if (lpDrv->lpNextItem)
+	lpDrv->lpNextItem->lpPrevItem = lpDrv->lpPrevItem;
+    /* trash magic number */
+    lpDrv->dwMagic ^= 0xa5a5a5a5;
+
+    return TRUE;
+}
+
+/**************************************************************************
+ *				DRIVER_AddToList		[internal]
+ *
+ * Adds a driver struct to the list of open drivers.
+ * Generates all the logic to handle driver creation / open.
+ */
+static	BOOL	DRIVER_AddToList(LPWINE_DRIVER lpNewDrv, LPARAM lParam1, LPARAM lParam2)
+{
+    lpNewDrv->dwMagic = WINE_DI_MAGIC;
+    /* First driver to be loaded for this module, need to load correctly the module */
+    if (!(lpNewDrv->dwFlags & WINE_GDF_16BIT)) {
+        /* first of this driver in list ? */
+	if (DRIVER_GetNumberOfModuleRefs(lpNewDrv->d.d32.hModule, NULL) == 0) {
+	    if (DRIVER_SendMessage(lpNewDrv, DRV_LOAD, 0L, 0L) != DRV_SUCCESS) {
+		TRACE("DRV_LOAD failed on driver 0x%08lx\n", (DWORD)lpNewDrv);
+		return FALSE;
+	    }
+	    /* returned value is not checked */
+	    DRIVER_SendMessage(lpNewDrv, DRV_ENABLE, 0L, 0L);
+	}
+    }
+
+    lpNewDrv->lpNextItem = NULL;
+    if (lpDrvItemList == NULL) {
+	lpDrvItemList = lpNewDrv;
+	lpNewDrv->lpPrevItem = NULL;
+    } else {
+	LPWINE_DRIVER	lpDrv = lpDrvItemList;	/* find end of list */
+	while (lpDrv->lpNextItem != NULL)
+	    lpDrv = lpDrv->lpNextItem;
+
+	lpDrv->lpNextItem = lpNewDrv;
+	lpNewDrv->lpPrevItem = lpDrv;
+    }
+
+    if (!(lpNewDrv->dwFlags & WINE_GDF_16BIT)) {
+	/* Now just open a new instance of a driver on this module */
+	lpNewDrv->d.d32.dwDriverID = DRIVER_SendMessage(lpNewDrv, DRV_OPEN, lParam1, lParam2);
+
+	if (lpNewDrv->d.d32.dwDriverID == 0) {
+	    TRACE("DRV_OPEN failed on driver 0x%08lx\n", (DWORD)lpNewDrv);
+	    DRIVER_RemoveFromList(lpNewDrv);
+	    return FALSE;
+	}
+    }
+    return TRUE;
+}
+
+/**************************************************************************
+ *				DRIVER_GetLibName		[internal]
+ *
+ */
+BOOL	DRIVER_GetLibName(LPCSTR keyName, LPCSTR sectName, LPSTR buf, int sz)
+{
+    HKEY	hKey, hSecKey;
+    DWORD	bufLen, lRet;
+
+    lRet = RegOpenKeyExA(HKEY_LOCAL_MACHINE, HKLM_BASE, 0, KEY_QUERY_VALUE, &hKey);
+    if (lRet == ERROR_SUCCESS) {
+	lRet = RegOpenKeyExA(hKey, sectName, 0, KEY_QUERY_VALUE, &hSecKey);
+	if (lRet == ERROR_SUCCESS) {
+	    lRet = RegQueryValueExA(hSecKey, keyName, 0, 0, buf, &bufLen);
+	    RegCloseKey( hSecKey );
+	}
+        RegCloseKey( hKey );
+    }
+    if (lRet == ERROR_SUCCESS) return TRUE;
+    /* default to system.ini if we can't find it in the registry,
+     * to support native installations where system.ini is still used */
+    return GetPrivateProfileStringA(sectName, keyName, "", buf, sz, "SYSTEM.INI");
+}
+
+/**************************************************************************
+ *				DRIVER_TryOpenDriver32		[internal]
+ *
+ * Tries to load a 32 bit driver whose DLL's (module) name is fn
+ */
+LPWINE_DRIVER	DRIVER_TryOpenDriver32(LPCSTR fn, LPARAM lParam2)
+{
+    LPWINE_DRIVER 	lpDrv = NULL;
+    HMODULE		hModule = 0;
+    LPSTR		ptr;
+    LPCSTR		cause = 0;
+
+    TRACE("(%s, %08lX);\n", debugstr_a(fn), lParam2);
+
+    if ((ptr = strchr(fn, ' ')) != NULL) {
+	*ptr++ = '\0';
+	while (*ptr == ' ') ptr++;
+	if (*ptr == '\0') ptr = NULL;
+    }
+
+    lpDrv = HeapAlloc(GetProcessHeap(), 0, sizeof(WINE_DRIVER));
+    if (lpDrv == NULL) {cause = "OOM"; goto exit;}
+
+    if ((hModule = LoadLibraryA(fn)) == 0) {cause = "Not a 32 bit lib"; goto exit;}
+
+    lpDrv->d.d32.lpDrvProc = (DRIVERPROC)GetProcAddress(hModule, "DriverProc");
+    if (lpDrv->d.d32.lpDrvProc == NULL) {cause = "no DriverProc"; goto exit;}
+
+    lpDrv->dwFlags          = 0;
+    lpDrv->d.d32.hModule    = hModule;
+    lpDrv->d.d32.dwDriverID = 0;
+
+    /* Win32 installable drivers must support a two phase opening scheme:
+     * + first open with NULL as lParam2 (session instance),
+     * + then do a second open with the real non null lParam2)
+     */
+    if (DRIVER_GetNumberOfModuleRefs(lpDrv->d.d32.hModule, NULL) == 0 && lParam2)
+    {
+        LPWINE_DRIVER   ret;
+
+        if (!DRIVER_AddToList(lpDrv, (LPARAM)ptr, 0L))
+        {
+            cause = "load0 failed";
+            goto exit;
+        }
+        ret = DRIVER_TryOpenDriver32(fn, lParam2);
+        if (!ret)
+        {
+            CloseDriver((HDRVR)lpDrv, 0L, 0L);
+            cause = "load1 failed";
+            goto exit;
+        }
+        return ret;
+    }
+
+    if (!DRIVER_AddToList(lpDrv, (LPARAM)ptr, lParam2))
+    {cause = "load failed"; goto exit;}
+
+    TRACE("=> %p\n", lpDrv);
+    return lpDrv;
+ exit:
+    FreeLibrary(hModule);
+    HeapFree(GetProcessHeap(), 0, lpDrv);
+    TRACE("Unable to load 32 bit module %s: %s\n", debugstr_a(fn), cause);
+    return NULL;
+}
+
+/**************************************************************************
+ *				OpenDriverA		        [WINMM.@]
+ *				DrvOpenA			[WINMM.@]
+ * (0,1,DRV_LOAD  ,0       ,0)
+ * (0,1,DRV_ENABLE,0       ,0)
+ * (0,1,DRV_OPEN  ,buf[256],0)
+ */
+HDRVR WINAPI OpenDriverA(LPCSTR lpDriverName, LPCSTR lpSectionName, LPARAM lParam2)
+{
+    LPWINE_DRIVER	lpDrv = NULL;
+    char 		libName[128];
+    LPCSTR		lsn = lpSectionName;
+
+    TRACE("(%s, %s, 0x%08lx);\n", debugstr_a(lpDriverName), debugstr_a(lpSectionName), lParam2);
+
+    if (lsn == NULL) {
+	lstrcpynA(libName, lpDriverName, sizeof(libName));
+
+	if ((lpDrv = DRIVER_TryOpenDriver32(libName, lParam2)))
+	    goto the_end;
+	lsn = "Drivers32";
+    }
+    if (DRIVER_GetLibName(lpDriverName, lsn, libName, sizeof(libName)) &&
+	(lpDrv = DRIVER_TryOpenDriver32(libName, lParam2)))
+	goto the_end;
+
+    /* now we will try a 16 bit driver (and add all the glue to make it work... which
+     * is located in our mmsystem implementation)
+     * so ensure, we can load our mmsystem, otherwise just fail
+     */
+    WINMM_CheckForMMSystem();
+    if (pFnOpenDriver16 &&
+        (lpDrv = pFnOpenDriver16(lpDriverName, lpSectionName, lParam2)))
+    {
+        if (DRIVER_AddToList(lpDrv, 0, lParam2)) goto the_end;
+        HeapFree(GetProcessHeap(), 0, lpDrv);
+    }
+    TRACE("Failed to open driver %s from system.ini file, section %s\n", debugstr_a(lpDriverName), debugstr_a(lpSectionName));
+    return 0;
+
+ the_end:
+    if (lpDrv)	TRACE("=> %08lx\n", (DWORD)lpDrv);
+    return (HDRVR)lpDrv;
+}
+
+/**************************************************************************
+ *				OpenDriver 		        [WINMM.@]
+ *				DrvOpen				[WINMM.@]
+ */
+HDRVR WINAPI OpenDriverW(LPCWSTR lpDriverName, LPCWSTR lpSectionName, LPARAM lParam)
+{
+    INT                 len;
+    LPSTR 		dn = NULL;
+    LPSTR 		sn = NULL;
+    HDRVR		ret;
+
+    if (lpDriverName)
+    {
+        len = WideCharToMultiByte( CP_ACP, 0, lpDriverName, -1, NULL, 0, NULL, NULL );
+        dn = HeapAlloc( GetProcessHeap(), 0, len );
+        if (!dn) return 0;
+        WideCharToMultiByte( CP_ACP, 0, lpDriverName, -1, dn, len, NULL, NULL );
+    }
+
+    if (lpSectionName)
+    {
+        len = WideCharToMultiByte( CP_ACP, 0, lpSectionName, -1, NULL, 0, NULL, NULL );
+        sn = HeapAlloc( GetProcessHeap(), 0, len );
+        if (!sn) return 0;
+        WideCharToMultiByte( CP_ACP, 0, lpSectionName, -1, sn, len, NULL, NULL );
+    }
+
+    ret = OpenDriverA(dn, sn, lParam);
+
+    if (dn) HeapFree(GetProcessHeap(), 0, dn);
+    if (sn) HeapFree(GetProcessHeap(), 0, sn);
+    return ret;
+}
+
+/**************************************************************************
+ *			CloseDriver				[WINMM.@]
+ *			DrvClose				[WINMM.@]
+ */
+LRESULT WINAPI CloseDriver(HDRVR hDrvr, LPARAM lParam1, LPARAM lParam2)
+{
+    LPWINE_DRIVER	lpDrv;
+
+    TRACE("(%p, %08lX, %08lX);\n", hDrvr, lParam1, lParam2);
+
+    if ((lpDrv = DRIVER_FindFromHDrvr(hDrvr)) != NULL)
+    {
+	if (lpDrv->dwFlags & WINE_GDF_16BIT)
+        {
+            if (pFnCloseDriver16)
+                pFnCloseDriver16(lpDrv->d.d16.hDriver16, lParam1, lParam2);
+        }
+	else
+        {
+	    DRIVER_SendMessage(lpDrv, DRV_CLOSE, lParam1, lParam2);
+            lpDrv->d.d32.dwDriverID = 0;
+        }
+	if (DRIVER_RemoveFromList(lpDrv)) {
+            if (!(lpDrv->dwFlags & WINE_GDF_16BIT))
+            {
+                LPWINE_DRIVER       lpDrv0;
+
+                /* if driver has an opened session instance, we have to close it too */
+                if (DRIVER_GetNumberOfModuleRefs(lpDrv->d.d32.hModule, &lpDrv0) == 1)
+                {
+                    DRIVER_SendMessage(lpDrv0, DRV_CLOSE, 0L, 0L);
+                    lpDrv0->d.d32.dwDriverID = 0;
+                    DRIVER_RemoveFromList(lpDrv0);
+                    FreeLibrary(lpDrv0->d.d32.hModule);
+                    HeapFree(GetProcessHeap(), 0, lpDrv0);
+                }
+                FreeLibrary(lpDrv->d.d32.hModule);
+            }
+            HeapFree(GetProcessHeap(), 0, lpDrv);
+            return TRUE;
+        }
+    }
+    WARN("Failed to close driver\n");
+    return FALSE;
+}
+
+/**************************************************************************
+ *				GetDriverFlags		[WINMM.@]
+ * [in] hDrvr handle to the driver
+ *
+ * Returns:
+ *	0x00000000 if hDrvr is an invalid handle
+ *	0x80000000 if hDrvr is a valid 32 bit driver
+ *	0x90000000 if hDrvr is a valid 16 bit driver
+ *
+ * native WINMM doesn't return those flags
+ *	0x80000000 for a valid 32 bit driver and that's it
+ *	(I may have mixed up the two flags :-(
+ */
+DWORD	WINAPI GetDriverFlags(HDRVR hDrvr)
+{
+    LPWINE_DRIVER 	lpDrv;
+    DWORD		ret = 0;
+
+    TRACE("(%p)\n", hDrvr);
+
+    if ((lpDrv = DRIVER_FindFromHDrvr(hDrvr)) != NULL) {
+	ret = WINE_GDF_EXIST | lpDrv->dwFlags;
+    }
+    return ret;
+}
+
+/**************************************************************************
+ *				GetDriverModuleHandle	[WINMM.@]
+ *				DrvGetModuleHandle	[WINMM.@]
+ */
+HMODULE WINAPI GetDriverModuleHandle(HDRVR hDrvr)
+{
+    LPWINE_DRIVER 	lpDrv;
+    HMODULE		hModule = 0;
+
+    TRACE("(%p);\n", hDrvr);
+
+    if ((lpDrv = DRIVER_FindFromHDrvr(hDrvr)) != NULL) {
+	if (!(lpDrv->dwFlags & WINE_GDF_16BIT))
+	    hModule = lpDrv->d.d32.hModule;
+    }
+    TRACE("=> %p\n", hModule);
+    return hModule;
+}
+
+/**************************************************************************
+ * 				DefDriverProc			  [WINMM.@]
+ * 				DrvDefDriverProc		  [WINMM.@]
+ */
+LRESULT WINAPI DefDriverProc(DWORD_PTR dwDriverIdentifier, HDRVR hDrv,
+			     UINT Msg, LPARAM lParam1, LPARAM lParam2)
+{
+    switch (Msg) {
+    case DRV_LOAD:
+    case DRV_FREE:
+    case DRV_ENABLE:
+    case DRV_DISABLE:
+        return 1;
+    case DRV_INSTALL:
+    case DRV_REMOVE:
+        return DRV_SUCCESS;
+    default:
+        return 0;
+    }
+}
+
+/**************************************************************************
+ * 				DriverCallback			[WINMM.@]
+ */
+BOOL WINAPI DriverCallback(DWORD dwCallBack, UINT uFlags, HDRVR hDev,
+			   UINT wMsg, DWORD dwUser, DWORD dwParam1,
+			   DWORD dwParam2)
+{
+    TRACE("(%08lX, %04X, %p, %04X, %08lX, %08lX, %08lX); !\n",
+	  dwCallBack, uFlags, hDev, wMsg, dwUser, dwParam1, dwParam2);
+
+    switch (uFlags & DCB_TYPEMASK) {
+    case DCB_NULL:
+	TRACE("Null !\n");
+	if (dwCallBack)
+	    WARN("uFlags=%04X has null DCB value, but dwCallBack=%08lX is not null !\n", uFlags, dwCallBack);
+	break;
+    case DCB_WINDOW:
+	TRACE("Window(%04lX) handle=%p!\n", dwCallBack, hDev);
+	PostMessageA((HWND)dwCallBack, wMsg, (WPARAM)hDev, dwParam1);
+	break;
+    case DCB_TASK: /* aka DCB_THREAD */
+	TRACE("Task(%04lx) !\n", dwCallBack);
+	PostThreadMessageA(dwCallBack, wMsg, (WPARAM)hDev, dwParam1);
+	break;
+    case DCB_FUNCTION:
+	TRACE("Function (32 bit) !\n");
+	((LPDRVCALLBACK)dwCallBack)(hDev, wMsg, dwUser, dwParam1, dwParam2);
+	break;
+    case DCB_EVENT:
+	TRACE("Event(%08lx) !\n", dwCallBack);
+	SetEvent((HANDLE)dwCallBack);
+	break;
+    case 6: /* I would dub it DCB_MMTHREADSIGNAL */
+	/* this is an undocumented DCB_ value used for mmThreads
+	 * loword of dwCallBack contains the handle of the lpMMThd block
+	 * which dwSignalCount has to be incremented
+	 */     
+        if (pFnGetMMThread16)
+	{
+	    WINE_MMTHREAD*	lpMMThd = pFnGetMMThread16(LOWORD(dwCallBack));
+
+	    TRACE("mmThread (%04x, %p) !\n", LOWORD(dwCallBack), lpMMThd);
+	    /* same as mmThreadSignal16 */
+	    InterlockedIncrement(&lpMMThd->dwSignalCount);
+	    SetEvent(lpMMThd->hEvent);
+	    /* some other stuff on lpMMThd->hVxD */
+	}
+	break;
+#if 0
+    case 4:
+	/* this is an undocumented DCB_ value for... I don't know */
+	break;
+#endif
+    default:
+	WARN("Unknown callback type %d\n", uFlags & DCB_TYPEMASK);
+	return FALSE;
+    }
+    TRACE("Done\n");
+    return TRUE;
+}
+
+/******************************************************************
+ *		DRIVER_UnloadAll
+ *
+ *
+ */
+void    DRIVER_UnloadAll(void)
+{
+    LPWINE_DRIVER 	lpDrv;
+    LPWINE_DRIVER 	lpNextDrv = NULL;
+    unsigned            count = 0;
+
+    for (lpDrv = lpDrvItemList; lpDrv != NULL; lpDrv = lpNextDrv)
+    {
+        lpNextDrv = lpDrv->lpNextItem;
+        CloseDriver((HDRVR)lpDrv, 0, 0);
+        count++;
+    }
+    TRACE("Unloaded %u drivers\n", count);
+}

Added: vendor/wine/dlls/winmm/current/joystick.c
--- vendor/wine/dlls/winmm/current/joystick.c	2004-12-31 16:30:04 UTC (rev 12637)
+++ vendor/wine/dlls/winmm/current/joystick.c	2004-12-31 16:34:31 UTC (rev 12638)
@@ -0,0 +1,308 @@
+/* -*- tab-width: 8; c-basic-offset: 4 -*- */
+/*
+ * joystick functions
+ *
+ * Copyright 1997 Andreas Mohr
+ *	     2000 Wolfgang Schwotzer
+ *                Eric Pouech
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+
+#include "config.h"
+
+#ifdef HAVE_UNISTD_H
+# include <unistd.h>
+#endif
+#include <stdarg.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <fcntl.h>
+#ifdef HAVE_SYS_IOCTL_H
+#include <sys/ioctl.h>
+#endif
+
+#include "windef.h"
+#include "winbase.h"
+#include "mmsystem.h"
+#include "wingdi.h"
+#include "winuser.h"
+#include "winnls.h"
+
+#include "mmddk.h"
+
+#include "wine/debug.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(winmm);
+
+#define MAXJOYSTICK	(JOYSTICKID2 + 1)
+#define JOY_PERIOD_MIN	(10)	/* min Capture time period */
+#define JOY_PERIOD_MAX	(1000)	/* max Capture time period */
+
+typedef struct tagWINE_JOYSTICK {
+    JOYINFO	ji;
+    HWND	hCapture;
+    UINT	wTimer;
+    DWORD	threshold;
+    BOOL	bChanged;
+    HDRVR	hDriver;
+} WINE_JOYSTICK;
+
+static	WINE_JOYSTICK	JOY_Sticks[MAXJOYSTICK];
+
+/**************************************************************************
+ * 				JOY_LoadDriver		[internal]
+ */
+static	BOOL JOY_LoadDriver(DWORD dwJoyID)
+{
+    if (dwJoyID >= MAXJOYSTICK)
+	return FALSE;
+    if (JOY_Sticks[dwJoyID].hDriver)
+	return TRUE;
+
+    JOY_Sticks[dwJoyID].hDriver = OpenDriverA("joystick.drv", 0, dwJoyID);
+    return (JOY_Sticks[dwJoyID].hDriver != 0);
+}
+
+/**************************************************************************
+ * 				JOY_Timer		[internal]
+ */
+static	void	CALLBACK	JOY_Timer(HWND hWnd, UINT wMsg, UINT wTimer, DWORD dwTime)
+{
+    int			i;
+    WINE_JOYSTICK*	joy;
+    JOYINFO		ji;
+    LONG		pos;
+    unsigned 		buttonChange;
+
+    for (i = 0; i < MAXJOYSTICK; i++) {
+	joy = &JOY_Sticks[i];
+
+	if (joy->hCapture != hWnd) continue;
+
+	joyGetPos(i, &ji);
+	pos = MAKELONG(ji.wXpos, ji.wYpos);
+
+	if (!joy->bChanged ||
+	    abs(joy->ji.wXpos - ji.wXpos) > joy->threshold ||
+	    abs(joy->ji.wYpos - ji.wYpos) > joy->threshold) {
+	    SendMessageA(joy->hCapture, MM_JOY1MOVE + i, ji.wButtons, pos);
+	    joy->ji.wXpos = ji.wXpos;
+	    joy->ji.wYpos = ji.wYpos;
+	}
+	if (!joy->bChanged ||
+	    abs(joy->ji.wZpos - ji.wZpos) > joy->threshold) {
+	    SendMessageA(joy->hCapture, MM_JOY1ZMOVE + i, ji.wButtons, pos);
+	    joy->ji.wZpos = ji.wZpos;
+	}
+	if ((buttonChange = joy->ji.wButtons ^ ji.wButtons) != 0) {
+	    if (ji.wButtons & buttonChange)
+		SendMessageA(joy->hCapture, MM_JOY1BUTTONDOWN + i,
+			     (buttonChange << 8) | (ji.wButtons & buttonChange), pos);
+	    if (joy->ji.wButtons & buttonChange)
+		SendMessageA(joy->hCapture, MM_JOY1BUTTONUP + i,
+			     (buttonChange << 8) | (joy->ji.wButtons & buttonChange), pos);
+	    joy->ji.wButtons = ji.wButtons;
+	}
+    }
+}
+
+/**************************************************************************
+ * 				joyGetNumDevs		[WINMM.@]
+ */
+UINT WINAPI joyGetNumDevs(void)
+{
+    UINT	ret = 0;
+    int		i;
+
+    for (i = 0; i < MAXJOYSTICK; i++) {
+	if (JOY_LoadDriver(i)) {
+	    ret += SendDriverMessage(JOY_Sticks[i].hDriver, JDD_GETNUMDEVS, 0L, 0L);
+	}
+    }
+    return ret;
+}
+
+/**************************************************************************
+ * 				joyGetDevCapsA		[WINMM.@]
+ */
+MMRESULT WINAPI joyGetDevCapsA(UINT_PTR wID, LPJOYCAPSA lpCaps, UINT wSize)
+{
+    if (wID >= MAXJOYSTICK)	return JOYERR_PARMS;
+    if (!JOY_LoadDriver(wID))	return MMSYSERR_NODRIVER;
+
+    lpCaps->wPeriodMin = JOY_PERIOD_MIN; /* FIXME */
+    lpCaps->wPeriodMax = JOY_PERIOD_MAX; /* FIXME (same as MS Joystick Driver) */
+
+    return SendDriverMessage(JOY_Sticks[wID].hDriver, JDD_GETDEVCAPS, (DWORD)lpCaps, wSize);
+}
+
+/**************************************************************************
+ * 				joyGetDevCapsW		[WINMM.@]
+ */
+MMRESULT WINAPI joyGetDevCapsW(UINT_PTR wID, LPJOYCAPSW lpCaps, UINT wSize)
+{
+    JOYCAPSA	jca;
+    MMRESULT	ret = joyGetDevCapsA(wID, &jca, sizeof(jca));
+
+    if (ret != JOYERR_NOERROR) return ret;
+    lpCaps->wMid = jca.wMid;
+    lpCaps->wPid = jca.wPid;
+    MultiByteToWideChar( CP_ACP, 0, jca.szPname, -1, lpCaps->szPname,
+                         sizeof(lpCaps->szPname)/sizeof(WCHAR) );
+    lpCaps->wXmin = jca.wXmin;
+    lpCaps->wXmax = jca.wXmax;
+    lpCaps->wYmin = jca.wYmin;
+    lpCaps->wYmax = jca.wYmax;
+    lpCaps->wZmin = jca.wZmin;
+    lpCaps->wZmax = jca.wZmax;
+    lpCaps->wNumButtons = jca.wNumButtons;
+    lpCaps->wPeriodMin = jca.wPeriodMin;
+    lpCaps->wPeriodMax = jca.wPeriodMax;
+
+    if (wSize >= sizeof(JOYCAPSW)) { /* Win95 extensions ? */
+	lpCaps->wRmin = jca.wRmin;
+	lpCaps->wRmax = jca.wRmax;
+	lpCaps->wUmin = jca.wUmin;
+	lpCaps->wUmax = jca.wUmax;
+	lpCaps->wVmin = jca.wVmin;
+	lpCaps->wVmax = jca.wVmax;
+	lpCaps->wCaps = jca.wCaps;
+	lpCaps->wMaxAxes = jca.wMaxAxes;
+	lpCaps->wNumAxes = jca.wNumAxes;
+	lpCaps->wMaxButtons = jca.wMaxButtons;
+        MultiByteToWideChar( CP_ACP, 0, jca.szRegKey, -1, lpCaps->szRegKey,
+                         sizeof(lpCaps->szRegKey)/sizeof(WCHAR) );
+        MultiByteToWideChar( CP_ACP, 0, jca.szOEMVxD, -1, lpCaps->szOEMVxD,
+                         sizeof(lpCaps->szOEMVxD)/sizeof(WCHAR) );
+    }
+
+    return ret;
+}
+
+/**************************************************************************
+ *                              joyGetPosEx             [WINMM.@]
+ */
+MMRESULT WINAPI joyGetPosEx(UINT wID, LPJOYINFOEX lpInfo)
+{
+    TRACE("(%d, %p);\n", wID, lpInfo);
+
+    if (wID >= MAXJOYSTICK)	return JOYERR_PARMS;
+    if (!JOY_LoadDriver(wID))	return MMSYSERR_NODRIVER;
+
+    lpInfo->dwXpos = 0;
+    lpInfo->dwYpos = 0;
+    lpInfo->dwZpos = 0;
+    lpInfo->dwRpos = 0;
+    lpInfo->dwUpos = 0;
+    lpInfo->dwVpos = 0;
+    lpInfo->dwButtons = 0;
+    lpInfo->dwButtonNumber = 0;
+    lpInfo->dwPOV = 0;
+    lpInfo->dwReserved1 = 0;
+    lpInfo->dwReserved2 = 0;
+
+    return SendDriverMessage(JOY_Sticks[wID].hDriver, JDD_GETPOSEX, (DWORD)lpInfo, 0L);
+}
+
+/**************************************************************************
+ * 				joyGetPos	       	[WINMM.@]
+ */
+MMRESULT WINAPI joyGetPos(UINT wID, LPJOYINFO lpInfo)
+{
+    TRACE("(%d, %p);\n", wID, lpInfo);
+
+    if (wID >= MAXJOYSTICK)	return JOYERR_PARMS;
+    if (!JOY_LoadDriver(wID))	return MMSYSERR_NODRIVER;
+
+    lpInfo->wXpos = 0;
+    lpInfo->wYpos = 0;
+    lpInfo->wZpos = 0;
+    lpInfo->wButtons = 0;
+
+    return SendDriverMessage(JOY_Sticks[wID].hDriver, JDD_GETPOS, (DWORD)lpInfo, 0L);
+}
+
+/**************************************************************************
+ * 				joyGetThreshold		[WINMM.@]
+ */
+MMRESULT WINAPI joyGetThreshold(UINT wID, LPUINT lpThreshold)
+{
+    TRACE("(%04X, %p);\n", wID, lpThreshold);
+
+    if (wID >= MAXJOYSTICK)	return JOYERR_PARMS;
+
+    *lpThreshold = JOY_Sticks[wID].threshold;
+    return JOYERR_NOERROR;
+}
+
+/**************************************************************************
+ * 				joyReleaseCapture	[WINMM.@]
+ */
+MMRESULT WINAPI joyReleaseCapture(UINT wID)
+{
+    TRACE("(%04X);\n", wID);
+
+    if (wID >= MAXJOYSTICK)		return JOYERR_PARMS;
+    if (!JOY_LoadDriver(wID))		return MMSYSERR_NODRIVER;
+    if (!JOY_Sticks[wID].hCapture)	return JOYERR_NOCANDO;
+
+    KillTimer(JOY_Sticks[wID].hCapture, JOY_Sticks[wID].wTimer);
+    JOY_Sticks[wID].hCapture = 0;
+    JOY_Sticks[wID].wTimer = 0;
+
+    return JOYERR_NOERROR;
+}
+
+/**************************************************************************
+ * 				joySetCapture		[WINMM.@]
+ */
+MMRESULT WINAPI joySetCapture(HWND hWnd, UINT wID, UINT wPeriod, BOOL bChanged)
+{
+    TRACE("(%p, %04X, %d, %d);\n",  hWnd, wID, wPeriod, bChanged);
+
+    if (wID >= MAXJOYSTICK || hWnd == 0) return JOYERR_PARMS;
+    if (wPeriod<JOY_PERIOD_MIN || wPeriod>JOY_PERIOD_MAX) return JOYERR_PARMS;
+    if (!JOY_LoadDriver(wID)) return MMSYSERR_NODRIVER;
+
+    if (JOY_Sticks[wID].hCapture || !IsWindow(hWnd))
+	return JOYERR_NOCANDO; /* FIXME: what should be returned ? */
+
+    if (joyGetPos(wID, &JOY_Sticks[wID].ji) != JOYERR_NOERROR)
+	return JOYERR_UNPLUGGED;
+
+    if ((JOY_Sticks[wID].wTimer = SetTimer(hWnd, 0, wPeriod, JOY_Timer)) == 0)
+	return JOYERR_NOCANDO;
+
+    JOY_Sticks[wID].hCapture = hWnd;
+    JOY_Sticks[wID].bChanged = bChanged;
+
+    return JOYERR_NOERROR;
+}
+
+/**************************************************************************
+ * 				joySetThreshold		[WINMM.@]
+ */
+MMRESULT WINAPI joySetThreshold(UINT wID, UINT wThreshold)
+{
+    TRACE("(%04X, %d);\n", wID, wThreshold);
+
+    if (wID >= MAXJOYSTICK) return MMSYSERR_INVALPARAM;
+
+    JOY_Sticks[wID].threshold = wThreshold;
+
+    return JOYERR_NOERROR;
+}

Added: vendor/wine/dlls/winmm/current/lolvldrv.c
--- vendor/wine/dlls/winmm/current/lolvldrv.c	2004-12-31 16:30:04 UTC (rev 12637)
+++ vendor/wine/dlls/winmm/current/lolvldrv.c	2004-12-31 16:34:31 UTC (rev 12638)
@@ -0,0 +1,850 @@
+/* -*- tab-width: 8; c-basic-offset: 4 -*- */
+
+/*
+ * MMSYTEM low level drivers handling functions
+ *
+ * Copyright 1999 Eric Pouech
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+
+#include <string.h>
+#include <stdarg.h>
+#include <stdio.h>
+#include <assert.h>
+#include "windef.h"
+#include "winbase.h"
+#include "winreg.h"
+#include "winver.h"
+#include "winemm.h"
+#include "wine/debug.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(winmm);
+
+LRESULT         (*pFnCallMMDrvFunc16)(DWORD,WORD,WORD,LONG,LONG,LONG) /* = NULL */;
+unsigned        (*pFnLoadMMDrvFunc16)(LPCSTR,LPWINE_DRIVER, LPWINE_MM_DRIVER) /* = NULL */;
+
+/* each known type of driver has an instance of this structure */
+typedef struct tagWINE_LLTYPE {
+    /* those attributes depend on the specification of the type */
+    LPCSTR		typestr;	/* name (for debugging) */
+    BOOL		bSupportMapper;	/* if type is allowed to support mapper */
+    MMDRV_MAPFUNC	Map16To32A;	/* those are function pointers to handle */
+    MMDRV_UNMAPFUNC	UnMap16To32A;	/*   the parameter conversion (16 vs 32 bit) */
+    MMDRV_MAPFUNC	Map32ATo16; 	/*   when hi-func (in mmsystem or winmm) and */
+    MMDRV_UNMAPFUNC	UnMap32ATo16;	/*   low-func (in .drv) do not match */
+    LPDRVCALLBACK	Callback;       /* handles callback for a specified type */
+    /* those attributes reflect the loaded/current situation for the type */
+    UINT		wMaxId;		/* number of loaded devices (sum across all loaded drivers */
+    LPWINE_MLD		lpMlds;		/* "static" mlds to access the part though device IDs */
+    int			nMapper;	/* index to mapper */
+} WINE_LLTYPE;
+
+static int		MMDrvsHi /* = 0 */;
+static WINE_MM_DRIVER	MMDrvs[8];
+static LPWINE_MLD	MM_MLDrvs[40];
+#define MAX_MM_MLDRVS	(sizeof(MM_MLDrvs) / sizeof(MM_MLDrvs[0]))
+
+#define A(_x,_y) {#_y, _x, NULL, NULL, NULL, NULL, NULL, 0, NULL, -1}
+/* Note: the indices of this array must match the definitions
+ *	 of the MMDRV_???? manifest constants
+ */
+static WINE_LLTYPE	llTypes[MMDRV_MAX] = {
+    A(TRUE,  Aux),
+    A(FALSE, Mixer),
+    A(TRUE,  MidiIn),
+    A(TRUE,  MidiOut),
+    A(TRUE,  WaveIn),
+    A(TRUE,  WaveOut),
+};
[truncated at 1000 lines; 19399 more skipped]