Take advantage of the new winproc handling to move some more functions
to 16-bit files.
TIMER_IsTimerValid is no longer necessary now that winprocs are never
freed.

diff --git a/dlls/user/msg16.c b/dlls/user/msg16.c
index ab2e228..3c7a7c6 100644
--- a/dlls/user/msg16.c
+++ b/dlls/user/msg16.c
@@ -260,16 +260,8 @@
     if ((msg->message == WM_TIMER) || (msg->message == WM_SYSTIMER))
     {
         if (msg->lParam)
-        {
-            /* before calling window proc, verify whether timer is still valid;
-               there's a slim chance that the application kills the timer
-	       between GetMessage and DispatchMessage API calls */
-            if (!TIMER_IsTimerValid(hwnd, (UINT) msg->wParam, (WNDPROC)msg->lParam))
-                return 0; /* invalid winproc */
-
             return CallWindowProc16( (WNDPROC16)msg->lParam, msg->hwnd,
                                      msg->message, msg->wParam, GetTickCount() );
-        }
     }
 
     if (!(wndPtr = WIN_GetPtr( hwnd )))
diff --git a/dlls/user/winproc.h b/dlls/user/winproc.h
index 6cfc515..ff26c65 100644
--- a/dlls/user/winproc.h
+++ b/dlls/user/winproc.h
@@ -132,6 +132,5 @@
 /* Timer functions */
 extern void TIMER_RemoveWindowTimers( HWND hwnd );
 extern void TIMER_RemoveThreadTimers(void);
-extern BOOL TIMER_IsTimerValid( HWND hwnd, UINT_PTR id, WNDPROC proc );
 
 #endif  /* __WINE_WINPROC_H */
diff --git a/dlls/user/wnd16.c b/dlls/user/wnd16.c
index 15ca5d5..3f73e69 100644
--- a/dlls/user/wnd16.c
+++ b/dlls/user/wnd16.c
@@ -22,6 +22,7 @@
 #include "wownt32.h"
 #include "user.h"
 #include "win.h"
+#include "winproc.h"
 #include "stackframe.h"
 
 /* handle <--> handle16 conversions */
@@ -67,6 +68,26 @@
 }
 
 
+/***********************************************************************
+ *		SetTimer (USER.10)
+ */
+UINT16 WINAPI SetTimer16( HWND16 hwnd, UINT16 id, UINT16 timeout, TIMERPROC16 proc )
+{
+    TIMERPROC proc32 = (TIMERPROC)WINPROC_AllocProc( (WNDPROC)proc, WIN_PROC_16 );
+    return SetTimer( WIN_Handle32(hwnd), id, timeout, proc32 );
+}
+
+
+/***********************************************************************
+ *		SetSystemTimer (USER.11)
+ */
+UINT16 WINAPI SetSystemTimer16( HWND16 hwnd, UINT16 id, UINT16 timeout, TIMERPROC16 proc )
+{
+    TIMERPROC proc32 = (TIMERPROC)WINPROC_AllocProc( (WNDPROC)proc, WIN_PROC_16 );
+    return SetSystemTimer( WIN_Handle32(hwnd), id, timeout, proc32 );
+}
+
+
 /**************************************************************************
  *              KillTimer   (USER.12)
  */
@@ -413,6 +434,29 @@
 }
 
 
+/***********************************************************************
+ *		RegisterClass (USER.57)
+ */
+ATOM WINAPI RegisterClass16( const WNDCLASS16 *wc )
+{
+    WNDCLASSEX16 wcex;
+
+    wcex.cbSize        = sizeof(wcex);
+    wcex.style         = wc->style;
+    wcex.lpfnWndProc   = wc->lpfnWndProc;
+    wcex.cbClsExtra    = wc->cbClsExtra;
+    wcex.cbWndExtra    = wc->cbWndExtra;
+    wcex.hInstance     = wc->hInstance;
+    wcex.hIcon         = wc->hIcon;
+    wcex.hCursor       = wc->hCursor;
+    wcex.hbrBackground = wc->hbrBackground;
+    wcex.lpszMenuName  = wc->lpszMenuName;
+    wcex.lpszClassName = wc->lpszClassName;
+    wcex.hIconSm       = 0;
+    return RegisterClassEx16( &wcex );
+}
+
+
 /**************************************************************************
  *              GetClassName   (USER.58)
  */
@@ -1270,6 +1314,66 @@
 }
 
 
+/***********************************************************************
+ *		RegisterClassEx (USER.397)
+ */
+ATOM WINAPI RegisterClassEx16( const WNDCLASSEX16 *wc )
+{
+    WNDCLASSEXA wc32;
+
+    wc32.cbSize        = sizeof(wc32);
+    wc32.style         = wc->style;
+    wc32.lpfnWndProc   = WINPROC_AllocProc( (WNDPROC)wc->lpfnWndProc, WIN_PROC_16 );
+    wc32.cbClsExtra    = wc->cbClsExtra;
+    wc32.cbWndExtra    = wc->cbWndExtra;
+    wc32.hInstance     = HINSTANCE_32(GetExePtr(wc->hInstance));
+    if (!wc32.hInstance) wc32.hInstance = HINSTANCE_32(GetModuleHandle16(NULL));
+    wc32.hIcon         = HICON_32(wc->hIcon);
+    wc32.hCursor       = HCURSOR_32(wc->hCursor);
+    wc32.hbrBackground = HBRUSH_32(wc->hbrBackground);
+    wc32.lpszMenuName  = MapSL(wc->lpszMenuName);
+    wc32.lpszClassName = MapSL(wc->lpszClassName);
+    wc32.hIconSm       = HICON_32(wc->hIconSm);
+    return RegisterClassExA( &wc32 );
+}
+
+
+/***********************************************************************
+ *		GetClassInfoEx (USER.398)
+ *
+ * FIXME: this is just a guess, I have no idea if GetClassInfoEx() is the
+ * same in Win16 as in Win32. --AJ
+ */
+BOOL16 WINAPI GetClassInfoEx16( HINSTANCE16 hInst16, SEGPTR name, WNDCLASSEX16 *wc )
+{
+    WNDCLASSEXA wc32;
+    HINSTANCE hInstance;
+    BOOL ret;
+
+    if (hInst16 == GetModuleHandle16("user")) hInstance = user32_module;
+    else hInstance = HINSTANCE_32(GetExePtr( hInst16 ));
+
+    ret = GetClassInfoExA( hInstance, MapSL(name), &wc32 );
+
+    if (ret)
+    {
+        WNDPROC proc = WINPROC_AllocProc( wc32.lpfnWndProc, WIN_PROC_32A );
+        wc->lpfnWndProc   = WINPROC_GetProc( proc, WIN_PROC_16 );
+        wc->style         = wc32.style;
+        wc->cbClsExtra    = wc32.cbClsExtra;
+        wc->cbWndExtra    = wc32.cbWndExtra;
+        wc->hInstance     = (wc32.hInstance == user32_module) ? GetModuleHandle16("user") : HINSTANCE_16(wc32.hInstance);
+        wc->hIcon         = HICON_16(wc32.hIcon);
+        wc->hIconSm       = HICON_16(wc32.hIconSm);
+        wc->hCursor       = HCURSOR_16(wc32.hCursor);
+        wc->hbrBackground = HBRUSH_16(wc32.hbrBackground);
+        wc->lpszClassName = 0;
+        wc->lpszMenuName  = MapLS(wc32.lpszMenuName);  /* FIXME: leak */
+    }
+    return ret;
+}
+
+
 /**************************************************************************
  *              ChildWindowFromPointEx   (USER.399)
  */
@@ -1296,6 +1400,41 @@
 }
 
 
+/***********************************************************************
+ *		UnregisterClass (USER.403)
+ */
+BOOL16 WINAPI UnregisterClass16( LPCSTR className, HINSTANCE16 hInstance )
+{
+    if (hInstance == GetModuleHandle16("user")) hInstance = 0;
+    return UnregisterClassA( className, HINSTANCE_32(GetExePtr( hInstance )) );
+}
+
+
+/***********************************************************************
+ *		GetClassInfo (USER.404)
+ */
+BOOL16 WINAPI GetClassInfo16( HINSTANCE16 hInst16, SEGPTR name, WNDCLASS16 *wc )
+{
+    WNDCLASSEX16 wcex;
+    UINT16 ret = GetClassInfoEx16( hInst16, name, &wcex );
+
+    if (ret)
+    {
+        wc->style         = wcex.style;
+        wc->lpfnWndProc   = wcex.lpfnWndProc;
+        wc->cbClsExtra    = wcex.cbClsExtra;
+        wc->cbWndExtra    = wcex.cbWndExtra;
+        wc->hInstance     = wcex.hInstance;
+        wc->hIcon         = wcex.hIcon;
+        wc->hCursor       = wcex.hCursor;
+        wc->hbrBackground = wcex.hbrBackground;
+        wc->lpszMenuName  = wcex.lpszMenuName;
+        wc->lpszClassName = wcex.lpszClassName;
+    }
+    return ret;
+}
+
+
 /**************************************************************************
  *              TrackPopupMenu   (USER.416)
  */
diff --git a/windows/class.c b/windows/class.c
index f8a0538..f6dd46e 100644
--- a/windows/class.c
+++ b/windows/class.c
@@ -27,13 +27,11 @@
 #include <stdlib.h>
 #include <string.h>
 
-#include "wine/winbase16.h"
 #include "winerror.h"
 #include "windef.h"
 #include "winbase.h"
 #include "wingdi.h"
 #include "wine/winuser16.h"
-#include "wownt32.h"
 #include "wine/unicode.h"
 #include "win.h"
 #include "user.h"
@@ -515,29 +513,6 @@
 
 
 /***********************************************************************
- *		RegisterClass (USER.57)
- */
-ATOM WINAPI RegisterClass16( const WNDCLASS16 *wc )
-{
-    WNDCLASSEX16 wcex;
-
-    wcex.cbSize        = sizeof(wcex);
-    wcex.style         = wc->style;
-    wcex.lpfnWndProc   = wc->lpfnWndProc;
-    wcex.cbClsExtra    = wc->cbClsExtra;
-    wcex.cbWndExtra    = wc->cbWndExtra;
-    wcex.hInstance     = wc->hInstance;
-    wcex.hIcon         = wc->hIcon;
-    wcex.hCursor       = wc->hCursor;
-    wcex.hbrBackground = wc->hbrBackground;
-    wcex.lpszMenuName  = wc->lpszMenuName;
-    wcex.lpszClassName = wc->lpszClassName;
-    wcex.hIconSm       = 0;
-    return RegisterClassEx16( &wcex );
-}
-
-
-/***********************************************************************
  *		RegisterClassA (USER32.@)
  * RETURNS
  *	>0: Unique identifier
@@ -587,40 +562,6 @@
 
 
 /***********************************************************************
- *		RegisterClassEx (USER.397)
- */
-ATOM WINAPI RegisterClassEx16( const WNDCLASSEX16 *wc )
-{
-    ATOM atom;
-    CLASS *classPtr;
-    HINSTANCE hInstance;
-
-    if (!(hInstance = HINSTANCE_32(GetExePtr(wc->hInstance))))
-        hInstance = HINSTANCE_32(GetModuleHandle16(NULL));
-
-    if (!(atom = GlobalAddAtomA( MapSL(wc->lpszClassName) ))) return 0;
-    if (!(classPtr = CLASS_RegisterClass( atom, hInstance, !(wc->style & CS_GLOBALCLASS),
-                                          wc->style, wc->cbClsExtra, wc->cbWndExtra )))
-        return 0;
-
-    TRACE("atom=%04x wndproc=%p hinst=%p bg=%04x style=%08x clsExt=%d winExt=%d class=%p\n",
-          atom, wc->lpfnWndProc, hInstance,
-          wc->hbrBackground, wc->style, wc->cbClsExtra,
-          wc->cbWndExtra, classPtr );
-
-    classPtr->hIcon         = HICON_32(wc->hIcon);
-    classPtr->hIconSm       = HICON_32(wc->hIconSm);
-    classPtr->hCursor       = HCURSOR_32(wc->hCursor);
-    classPtr->hbrBackground = HBRUSH_32(wc->hbrBackground);
-
-    classPtr->winprocA = WINPROC_AllocProc( (WNDPROC)wc->lpfnWndProc, WIN_PROC_16 );
-    CLASS_SetMenuNameA( classPtr, MapSL(wc->lpszMenuName) );
-    release_class_ptr( classPtr );
-    return atom;
-}
-
-
-/***********************************************************************
  *		RegisterClassExA (USER32.@)
  */
 ATOM WINAPI RegisterClassExA( const WNDCLASSEXA* wc )
@@ -697,15 +638,6 @@
 
 
 /***********************************************************************
- *		UnregisterClass (USER.403)
- */
-BOOL16 WINAPI UnregisterClass16( LPCSTR className, HINSTANCE16 hInstance )
-{
-    if (hInstance == GetModuleHandle16("user")) hInstance = 0;
-    return UnregisterClassA( className, HINSTANCE_32(GetExePtr( hInstance )) );
-}
-
-/***********************************************************************
  *		UnregisterClassA (USER32.@)
  */
 BOOL WINAPI UnregisterClassA( LPCSTR className, HINSTANCE hInstance )
@@ -1169,31 +1101,6 @@
 
 
 /***********************************************************************
- *		GetClassInfo (USER.404)
- */
-BOOL16 WINAPI GetClassInfo16( HINSTANCE16 hInst16, SEGPTR name, WNDCLASS16 *wc )
-{
-    WNDCLASSEX16 wcex;
-    UINT16 ret = GetClassInfoEx16( hInst16, name, &wcex );
-
-    if (ret)
-    {
-        wc->style         = wcex.style;
-        wc->lpfnWndProc   = wcex.lpfnWndProc;
-        wc->cbClsExtra    = wcex.cbClsExtra;
-        wc->cbWndExtra    = wcex.cbWndExtra;
-        wc->hInstance     = wcex.hInstance;
-        wc->hIcon         = wcex.hIcon;
-        wc->hCursor       = wcex.hCursor;
-        wc->hbrBackground = wcex.hbrBackground;
-        wc->lpszMenuName  = wcex.lpszMenuName;
-        wc->lpszClassName = wcex.lpszClassName;
-    }
-    return ret;
-}
-
-
-/***********************************************************************
  *		GetClassInfoA (USER32.@)
  */
 BOOL WINAPI GetClassInfoA( HINSTANCE hInstance, LPCSTR name, WNDCLASSA *wc )
@@ -1244,43 +1151,6 @@
 
 
 /***********************************************************************
- *		GetClassInfoEx (USER.398)
- *
- * FIXME: this is just a guess, I have no idea if GetClassInfoEx() is the
- * same in Win16 as in Win32. --AJ
- */
-BOOL16 WINAPI GetClassInfoEx16( HINSTANCE16 hInst16, SEGPTR name, WNDCLASSEX16 *wc )
-{
-    ATOM atom = HIWORD(name) ? GlobalFindAtomA( MapSL(name) ) : LOWORD(name);
-    CLASS *classPtr;
-    HINSTANCE hInstance;
-
-    if (hInst16 == GetModuleHandle16("user")) hInstance = user32_module;
-    else hInstance = HINSTANCE_32(GetExePtr( hInst16 ));
-
-    TRACE("%p %s %x %p\n", hInstance, debugstr_a( MapSL(name) ), atom, wc);
-
-    if (!atom || !(classPtr = CLASS_FindClassByAtom( atom, hInstance ))) return FALSE;
-    wc->style         = classPtr->style;
-    wc->lpfnWndProc   = CLASS_GetProc( classPtr, WIN_PROC_16 );
-    wc->cbClsExtra    = (INT16)classPtr->cbClsExtra;
-    wc->cbWndExtra    = (INT16)classPtr->cbWndExtra;
-    wc->hInstance     = (classPtr->hInstance == user32_module) ? GetModuleHandle16("user") : HINSTANCE_16(classPtr->hInstance);
-    wc->hIcon         = HICON_16(classPtr->hIcon);
-    wc->hIconSm       = HICON_16(classPtr->hIconSm);
-    wc->hCursor       = HCURSOR_16(classPtr->hCursor);
-    wc->hbrBackground = HBRUSH_16(classPtr->hbrBackground);
-    wc->lpszClassName = (SEGPTR)0;
-    wc->lpszMenuName  = CLASS_GetMenuName16( classPtr );
-    wc->lpszClassName = name;
-    release_class_ptr( classPtr );
-
-    /* We must return the atom of the class here instead of just TRUE. */
-    return atom;
-}
-
-
-/***********************************************************************
  *		GetClassInfoExA (USER32.@)
  */
 BOOL WINAPI GetClassInfoExA( HINSTANCE hInstance, LPCSTR name, WNDCLASSEXA *wc )
diff --git a/windows/message.c b/windows/message.c
index 02a116e..b0701a5 100644
--- a/windows/message.c
+++ b/windows/message.c
@@ -757,13 +757,6 @@
 	if (msg->lParam)
         {
 /*            HOOK_CallHooks32A( WH_CALLWNDPROC, HC_ACTION, 0, FIXME ); */
-
-            /* before calling window proc, verify whether timer is still valid;
-               there's a slim chance that the application kills the timer
-	       between GetMessage and DispatchMessage API calls */
-            if (!TIMER_IsTimerValid(msg->hwnd, (UINT) msg->wParam, (WNDPROC)msg->lParam))
-                return 0; /* invalid winproc */
-
 	    return CallWindowProcA( (WNDPROC)msg->lParam, msg->hwnd,
                                    msg->message, msg->wParam, GetTickCount() );
         }
@@ -835,13 +828,6 @@
 	if (msg->lParam)
         {
 /*            HOOK_CallHooks32W( WH_CALLWNDPROC, HC_ACTION, 0, FIXME ); */
-
-            /* before calling window proc, verify whether timer is still valid;
-               there's a slim chance that the application kills the timer
-	       between GetMessage and DispatchMessage API calls */
-            if (!TIMER_IsTimerValid(msg->hwnd, (UINT) msg->wParam, (WNDPROC)msg->lParam))
-                return 0; /* invalid winproc */
-
 	    return CallWindowProcW( (WNDPROC)msg->lParam, msg->hwnd,
                                    msg->message, msg->wParam, GetTickCount() );
         }
diff --git a/windows/timer.c b/windows/timer.c
index c3d2870..82de2cf 100644
--- a/windows/timer.c
+++ b/windows/timer.c
@@ -46,7 +46,6 @@
     UINT           msg;  /* WM_TIMER or WM_SYSTIMER */
     UINT           id;
     UINT           timeout;
-    WNDPROC        proc;
 } TIMER;
 
 #define NB_TIMERS            34
@@ -123,8 +122,7 @@
 /***********************************************************************
  *           TIMER_SetTimer
  */
-static UINT_PTR TIMER_SetTimer( HWND hwnd, UINT_PTR id, UINT timeout,
-                                WNDPROC proc, WINDOWPROCTYPE type, BOOL sys )
+static UINT_PTR TIMER_SetTimer( HWND hwnd, UINT_PTR id, UINT timeout, TIMERPROC proc, BOOL sys )
 {
     int i;
     TIMER * pTimer;
@@ -171,7 +169,7 @@
 
     if (!hwnd) id = i + 1;
 
-    if (proc) winproc = WINPROC_AllocProc( proc, type );
+    if (proc) winproc = WINPROC_AllocProc( (WNDPROC)proc, WIN_PROC_32A );
 
     SERVER_START_REQ( set_win_timer )
     {
@@ -191,10 +189,9 @@
     pTimer->msg     = sys ? WM_SYSTIMER : WM_TIMER;
     pTimer->id      = id;
     pTimer->timeout = timeout;
-    pTimer->proc    = winproc;
 
     TRACE("Timer added: %p, %p, %04x, %04x, %p\n",
-          pTimer, pTimer->hwnd, pTimer->msg, pTimer->id, pTimer->proc );
+          pTimer, pTimer->hwnd, pTimer->msg, pTimer->id, winproc );
 
     LeaveCriticalSection( &csTimer );
 
@@ -248,73 +245,22 @@
 
 
 /***********************************************************************
- *		SetTimer (USER.10)
- */
-UINT16 WINAPI SetTimer16( HWND16 hwnd, UINT16 id, UINT16 timeout,
-                          TIMERPROC16 proc )
-{
-    TRACE("%04x %d %d %08lx\n",
-                   hwnd, id, timeout, (LONG)proc );
-    return TIMER_SetTimer( WIN_Handle32(hwnd), id, timeout, (WNDPROC)proc,
-                           WIN_PROC_16, FALSE );
-}
-
-
-/***********************************************************************
  *		SetTimer (USER32.@)
  */
-UINT_PTR WINAPI SetTimer( HWND hwnd, UINT_PTR id, UINT timeout,
-                          TIMERPROC proc )
+UINT_PTR WINAPI SetTimer( HWND hwnd, UINT_PTR id, UINT timeout, TIMERPROC proc )
 {
     TRACE("%p %d %d %p\n", hwnd, id, timeout, proc );
-    return TIMER_SetTimer( hwnd, id, timeout, (WNDPROC)proc, WIN_PROC_32A, FALSE );
-}
-
-
-/***********************************************************************
- *           TIMER_IsTimerValid
- */
-BOOL TIMER_IsTimerValid( HWND hwnd, UINT_PTR id, WNDPROC proc )
-{
-    int i;
-    TIMER *pTimer;
-    BOOL ret = FALSE;
-
-    hwnd = WIN_GetFullHandle( hwnd );
-    EnterCriticalSection( &csTimer );
-
-    for (i = 0, pTimer = TimersArray; i < NB_TIMERS; i++, pTimer++)
-        if ((pTimer->hwnd == hwnd) && (pTimer->id == id) && (pTimer->proc == proc))
-        {
-            ret = TRUE;
-            break;
-        }
-
-   LeaveCriticalSection( &csTimer );
-   return ret;
-}
-
-
-/***********************************************************************
- *		SetSystemTimer (USER.11)
- */
-UINT16 WINAPI SetSystemTimer16( HWND16 hwnd, UINT16 id, UINT16 timeout,
-                                TIMERPROC16 proc )
-{
-    TRACE("%04x %d %d %08lx\n",
-                   hwnd, id, timeout, (LONG)proc );
-    return TIMER_SetTimer( WIN_Handle32(hwnd), id, timeout, (WNDPROC)proc, WIN_PROC_16, TRUE );
+    return TIMER_SetTimer( hwnd, id, timeout, proc, FALSE );
 }
 
 
 /***********************************************************************
  *		SetSystemTimer (USER32.@)
  */
-UINT_PTR WINAPI SetSystemTimer( HWND hwnd, UINT_PTR id, UINT timeout,
-                                TIMERPROC proc )
+UINT_PTR WINAPI SetSystemTimer( HWND hwnd, UINT_PTR id, UINT timeout, TIMERPROC proc )
 {
     TRACE("%p %d %d %p\n", hwnd, id, timeout, proc );
-    return TIMER_SetTimer( hwnd, id, timeout, (WNDPROC)proc, WIN_PROC_32A, TRUE );
+    return TIMER_SetTimer( hwnd, id, timeout, proc, TRUE );
 }