Commit in reactos/subsys/win32k/ntuser on win32k_user_rewrite
ntuser.c+1901added 1.1.4.1
userlock.c+70added 1.1.4.1
+1971
2 added files
forget those two files...

reactos/subsys/win32k/ntuser
ntuser.c added at 1.1.4.1
diff -N ntuser.c
--- /dev/null	1 Jan 1970 00:00:00 -0000
+++ ntuser.c	15 Jul 2004 20:12:55 -0000	1.1.4.1
@@ -0,0 +1,1901 @@
+/*
+ *  ReactOS W32 Subsystem
+ *  Copyright (C) 1998 - 2004 ReactOS Team
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License as published by
+ *  the Free Software Foundation; either version 2 of the License, or
+ *  (at your option) any later version.
+ *
+ *  This program 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 General Public License for more details.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with this program; if not, write to the Free Software
+ *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+/* $Id: ntuser.c,v 1.1.4.1 2004/07/15 20:12:55 weiden Exp $
+ *
+ * COPYRIGHT:        See COPYING in the top level directory
+ * PROJECT:          ReactOS kernel
+ * PURPOSE:          Entry points for user mode calls
+ * FILE:             subsys/win32k/ntuser/ntuser.c
+ * PROGRAMER:        Thomas Weidenmueller <w3seek@reactos.com>
+ * REVISION HISTORY:
+ *       06-22-2004  Created
+ */
+#include <w32k.h>
+
+/*
+ * NtUser handling macros
+ */
+
+#define BEGIN_NTUSER(ReturnType, ErrorReturn) \
+  ReturnType Result, ErrorResult = ErrorReturn
+
+#define BEGIN_NTUSER_NOERR(ReturnType) \
+  ReturnType Result
+
+#define END_NTUSER() \
+  if(IN_CRITICAL()) \
+  { \
+    LEAVE_CRITICAL(); \
+  } \
+  return Result; \
+error: \
+  return ErrorResult;
+
+#define END_NTUSER_NOERR() \
+  return Result;
+
+#define NTUSER_USER_OBJECT(Type, Variable) \
+  P##Type##_OBJECT Variable = NULL
+
+#define NTUSER_FAIL_ERROR(ErrorCode) \
+  if(ErrorCode != 0) \
+  { \
+    SetLastWin32Error(ErrorCode); \
+  } \
+  goto error
+
+#define NTUSER_FAIL_INVALID_PARAMETER(Variable, FailCondition) \
+  if((Variable) == (FailCondition)) \
+  { \
+    SetLastWin32Error(ERROR_INVALID_PARAMETER); \
+    goto error; \
+  }
+
+/* FIXME - Prope SizeMember first!!! */
+#define NTUSER_FAIL_INVALID_STRUCT(StructType, StructAddr, SizeMember) \
+  if((StructAddr)->SizeMember != sizeof(StructType)) \
+  { \
+    SetLastWin32Error(ERROR_INVALID_PARAMETER); \
+    goto error; \
+  }
+
+#define NTUSER_FAIL() \
+  goto error
+
+#define NTUSER_FAIL_NTERROR(ErrorCode) \
+  SetLastNtError(ErrorCode); \
+  goto error
+
+#define BEGIN_BUFFERS() \
+  NTSTATUS NtStatus
+
+#define NTUSER_COPY_BUFFER(Dest, Src, Length) \
+  Status = MmCopyFromCaller(&(Dest), (Src), (Length))
+
+#define NTUSER_COPY_BUFFER_W32ERROR(Dest, Src, Length, ErrorCode) \
+  if(!NT_SUCCESS((NtStatus = MmCopyFromCaller((Dest), (Src), (Length))))) \
+  { \
+    SetLastWin32Error(ErrorCode); \
+    goto error; \
+  }
+
+#define NTUSER_COPY_BUFFER_NTERROR(Dest, Src, Length) \
+  if(!NT_SUCCESS((NtStatus = MmCopyFromCaller((Dest), (Src), (Length))))) \
+  { \
+    SetLastNtError(NtStatus); \
+    goto error; \
+  }
+
+#define NTUSER_COPY_BUFFER_BACK(Dest, Src, Length) \
+  NtStatus = MmCopyFromCaller(&(Dest), (Src), (Length))
+
+#define NTUSER_COPY_BUFFER_BACK_W32ERROR(Dest, Src, Length, ErrorCode) \
+  if(!NT_SUCCESS((NtStatus = MmCopyToCaller((Dest), (Src), (Length))))) \
+  { \
+    SetLastWin32Error(ErrorCode); \
+    goto error; \
+  }
+
+#define NTUSER_COPY_BUFFER_BACK_NTERROR(Dest, Src, Length) \
+  if(!NT_SUCCESS((NtStatus = MmCopyToCaller((Dest), (Src), (Length))))) \
+  { \
+    SetLastNtError(NtStatus); \
+    goto error; \
+  }
+
+#define VALIDATE_USER_OBJECT(ObjectType, Handle, Object) \
+  if(!(Object = ObmGetObject(PsGetWin32Process()->WindowStation->HandleTable,  \
+                             (Handle), ot##ObjectType ))) \
+  { \
+    LEAVE_CRITICAL(); \
+    DPRINT1("%s(): Invalid %s handle: 0x%x !!!\n", __FUNCTION__, #ObjectType , Handle); \
+    SetLastWin32Error(ERROR_INVALID_##ObjectType##_HANDLE); \
+    goto error; \
+  } \
+
+#define VALIDATE_USER_OBJECT_NOERR(ObjectType, Handle, Object) \
+  if(!(Object = ObmGetObject(PsGetWin32Process()->WindowStation->HandleTable,  \
+                             (Handle), ot##ObjectType ))) \
+  { \
+    LEAVE_CRITICAL(); \
+    DPRINT1("%s(): Invalid %s handle: 0x%x !!!\n", __FUNCTION__, #ObjectType , Handle); \
+    goto error; \
+  } \
+
+/*
+ * Locking macros
+ */
+
+#define ENTER_CRITICAL() \
+  IntUserEnterCritical()
+
+#define ENTER_CRITICAL_SHARED() \
+  IntUserEnterCriticalShared()
+
+#define LEAVE_CRITICAL() \
+  IntUserLeaveCritical()
+
+#define IN_CRITICAL() \
+  IntUserIsInCritical()
+
+/*
+ * User entry points
+ */
+
+HDC STDCALL
+NtUserBeginPaint(HWND hWnd, PAINTSTRUCT* lPs)
+{
+  PAINTSTRUCT SafePs;
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(HDC, NULL);
+  
+  /* FIXME - what should we do if there's no write access to lPs? */
+  
+  ENTER_CRITICAL();
+  if(hWnd != NULL)
+  {
+    VALIDATE_USER_OBJECT(WINDOW, hWnd, Window);
+  }
+  else
+  {
+    if(!(Window = IntGetDesktopWindow()))
+    {
+      LEAVE_CRITICAL();
+      DPRINT1("GetWindowDC(): Unable to get desktop window!\n");
+      NTUSER_FAIL_ERROR(ERROR_ACCESS_DENIED);
+    }
+  }
+  
+  Result = IntBeginPaint(Window, &SafePs);
+  
+  LEAVE_CRITICAL();
+  
+  /* Apparently windows always sets the last error to ERROR_NOACCESS in case it can't copy
+     back the buffer */
+  NTUSER_COPY_BUFFER_BACK_W32ERROR(lPs, &SafePs, sizeof(PAINTSTRUCT), ERROR_NOACCESS);
+  
+  END_NTUSER();
+}
+
+DWORD STDCALL
+NtUserCallNoParam(DWORD Routine)
+{
+  BEGIN_NTUSER(DWORD, 0);
+  
+  switch(Routine)
+  {
+    case NOPARAM_ROUTINE_REGISTER_PRIMITIVE:
+      ENTER_CRITICAL();
+      W32kRegisterPrimitiveMessageQueue();
+      LEAVE_CRITICAL();
+      Result = TRUE;
+      break;
+    
+    case NOPARAM_ROUTINE_DESTROY_CARET:
+      ENTER_CRITICAL();
+      #if 0
+      Result = (DWORD)IntDestroyCaret(PsGetCurrentThread()->Win32Thread);
+      #else
+      Result = FALSE;
+      #endif
+      LEAVE_CRITICAL();
+      break;
+    
+    case NOPARAM_ROUTINE_INIT_MESSAGE_PUMP:
+      ENTER_CRITICAL();
+      Result = (DWORD)IntInitMessagePumpHook();
+      LEAVE_CRITICAL();
+      break;
+
+    case NOPARAM_ROUTINE_UNINIT_MESSAGE_PUMP:
+      ENTER_CRITICAL();
+      Result = (DWORD)IntUninitMessagePumpHook();
+      LEAVE_CRITICAL();
+      break;
+    
+    case NOPARAM_ROUTINE_GETMESSAGEEXTRAINFO:
+      ENTER_CRITICAL_SHARED();
+      Result = (DWORD)MsqGetMessageExtraInfo();
+      LEAVE_CRITICAL();
+      break;
+    
+    case NOPARAM_ROUTINE_ANYPOPUP:
+      ENTER_CRITICAL_SHARED();
+      Result = (DWORD)IntAnyPopup();
+      LEAVE_CRITICAL();
+      break;
+
+    case NOPARAM_ROUTINE_CSRSS_INITIALIZED:
+      Result = (DWORD)CsrInit();
+      break;
+    
+    default:
+      DPRINT1("Calling invalid routine number 0x%x in NtUserCallNoParam\n", Routine);
+      NTUSER_FAIL_ERROR(ERROR_INVALID_PARAMETER);
+      break;
+  }
+  
+  END_NTUSER();
+}
+
+DWORD STDCALL
+NtUserCallTwoParam(DWORD Param1,
+                   DWORD Param2,
+                   DWORD Routine)
+{
+  BEGIN_NTUSER(DWORD, 0);
+  
+  switch(Routine)
+  {
+    case TWOPARAM_ROUTINE_SETDCPENCOLOR:
+      /* FIXME */
+      Result = (DWORD)IntSetDCColor((HDC)Param1, OBJ_PEN, (COLORREF)Param2);
+      break;
+    
+    case TWOPARAM_ROUTINE_SETDCBRUSHCOLOR:
+      /* FIXME */
+      Result = (DWORD)IntSetDCColor((HDC)Param1, OBJ_BRUSH, (COLORREF)Param2);
+      break;
+    
+    case TWOPARAM_ROUTINE_GETDCCOLOR:
+      /* FIXME */
+      Result = (DWORD)IntGetDCColor((HDC)Param1, (ULONG)Param2);
+      break;
+    
+    case TWOPARAM_ROUTINE_GETWINDOWRGNBOX:
+    {
+      RECT SafeRect;
+      NTUSER_USER_OBJECT(WINDOW, Window);
+      BEGIN_BUFFERS();
+      
+      ENTER_CRITICAL_SHARED();
+      VALIDATE_USER_OBJECT(WINDOW, (HWND)Param1, Window);
+      Result = (DWORD)IntGetWindowRgnBox(Window, &SafeRect);
+      LEAVE_CRITICAL();
+      
+      ErrorResult = ERROR; /* return ERROR in case we fail */
+      NTUSER_COPY_BUFFER_BACK_NTERROR((PVOID)Param2, &SafeRect, sizeof(RECT));
+      break;
+    }
+    
+    case TWOPARAM_ROUTINE_GETWINDOWRGN:
+    {
+      NTUSER_USER_OBJECT(WINDOW, Window);
+      
+      ENTER_CRITICAL_SHARED();
+      VALIDATE_USER_OBJECT(WINDOW, (HWND)Param1, Window);
+      Result = (DWORD)IntGetWindowRgn(Window, (HRGN)Param2);
+      LEAVE_CRITICAL();
+      break;
+    }
+    
+    case TWOPARAM_ROUTINE_SETMENUBARHEIGHT:
+      DPRINT1("TWOPARAM_ROUTINE_SETMENUBARHEIGHT is unimplemented!\n");
+      break;
+    
+    case TWOPARAM_ROUTINE_SETMENUITEMRECT:
+      DPRINT1("TWOPARAM_ROUTINE_SETMENUITEMRECT is unimplemented!\n");
+      break;
+    
+    case TWOPARAM_ROUTINE_SETGUITHRDHANDLE:
+    {
+      PUSER_MESSAGE_QUEUE MsgQueue;
+      NTUSER_USER_OBJECT(WINDOW, Window);
+      
+      ENTER_CRITICAL();
+      VALIDATE_USER_OBJECT(WINDOW, (HWND)Param2, Window);
+      MsgQueue = PsGetCurrentThread()->Win32Thread->MessageQueue;
+      if(Window->MessageQueue != MsgQueue)
+      {
+        NTUSER_FAIL_ERROR(ERROR_ACCESS_DENIED);
+      }
+      Result = (DWORD)MsqSetStateWindow(MsgQueue, (ULONG)Param1, Window);
+      LEAVE_CRITICAL();
+      
+      break;
+    }
+    
+    case TWOPARAM_ROUTINE_VALIDATERGN:
+    {
+      /* FIXME !!!!! REMOVE THIS ROUTINE AND EXPORT NtUserValidateRgn() INSTEAD! */
+      Result = NtUserValidateRgn((HWND)Param1, (HRGN)Param2);
+      break;
+    }
+    
+    case TWOPARAM_ROUTINE_SETWNDCONTEXTHLPID:
+    {
+      NTUSER_USER_OBJECT(WINDOW, Window);
+      
+      ENTER_CRITICAL();
+      VALIDATE_USER_OBJECT(WINDOW, (HWND)Param1, Window);
+      Window->ContextHelpId = Param2;
+      LEAVE_CRITICAL();
+      
+      Result = (DWORD)TRUE;
+      break;
+    }
+    
+    case TWOPARAM_ROUTINE_SETCARETPOS:
+      DPRINT1("TWOPARAM_ROUTINE_SETCARETPOS is unimplemented!\n");
+      break;
+    
+    case TWOPARAM_ROUTINE_GETWINDOWINFO:
+    {
+      WINDOWINFO SafeWi;
+      NTUSER_USER_OBJECT(WINDOW, Window);
+      BEGIN_BUFFERS();
+      
+      ENTER_CRITICAL_SHARED();
+      VALIDATE_USER_OBJECT(WINDOW, (HWND)Param1, Window);
+      Result = (DWORD)IntGetWindowInfo(Window, &SafeWi);
+      LEAVE_CRITICAL();
+      
+      if(Result)
+      {
+        NTUSER_COPY_BUFFER_BACK_NTERROR((PVOID)Param2, &SafeWi, sizeof(WINDOWINFO));
+      }
+      break;
+    }
+    
+    case TWOPARAM_ROUTINE_REGISTERLOGONPROC:
+      Result = (DWORD)IntRegisterLogonProcess(Param1, (BOOL)Param2);
+      break;
+    
+    default:
+      DPRINT1("Calling invalid routine number 0x%x in NtUserCallTwoParam\n", Routine);
+      NTUSER_FAIL_ERROR(ERROR_INVALID_PARAMETER);
+      break;
+  }
+  
+  END_NTUSER();
+}
+
+HANDLE STDCALL
+NtUserCreateCursorIconHandle(PICONINFO IconInfo, BOOL Indirect)
+{
+  ICONINFO SafeInfo;
+  PBITMAPOBJ bmp;
+  SIZE sz;
+  NTUSER_USER_OBJECT(CURSOR, Cursor);
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(HANDLE, NULL);
+  
+  NTUSER_FAIL_INVALID_PARAMETER(IconInfo, NULL);
+  
+  NTUSER_COPY_BUFFER_NTERROR(&SafeInfo, IconInfo, sizeof(ICONINFO));
+  
+  if(Indirect)
+  {
+    /* Copy the bitmaps */
+    SafeInfo.hbmMask = BITMAPOBJ_CopyBitmap(SafeInfo.hbmMask);
+    SafeInfo.hbmColor = BITMAPOBJ_CopyBitmap(SafeInfo.hbmColor);
+  }
+  
+  /* Calculate the icon/cursor size from bitmap(s) */
+  if(SafeInfo.hbmColor && 
+     (bmp = BITMAPOBJ_LockBitmap(SafeInfo.hbmColor)))
+  {
+    sz.cx = bmp->SurfObj.sizlBitmap.cx;
+    sz.cy = bmp->SurfObj.sizlBitmap.cy;
+    BITMAPOBJ_UnlockBitmap(SafeInfo.hbmColor);
+  }
+  else if(SafeInfo.hbmMask && 
+          (bmp = BITMAPOBJ_LockBitmap(SafeInfo.hbmMask)))
+  {
+    sz.cx = bmp->SurfObj.sizlBitmap.cx;
+    sz.cy = bmp->SurfObj.sizlBitmap.cy / 2;
+    BITMAPOBJ_UnlockBitmap(SafeInfo.hbmMask);
+  }
+  
+  ENTER_CRITICAL();
+  Cursor = IntCreateCursorObject(&Result);
+  if(Cursor != NULL)
+  {
+    Cursor->IconInfo = SafeInfo;
+    Cursor->Size = sz;
+  }
+  else
+  {
+    LEAVE_CRITICAL();
+    if(Indirect)
+    {
+      if(SafeInfo.hbmMask)
+        NtGdiDeleteObject(SafeInfo.hbmMask);
+      if(SafeInfo.hbmColor)
+        NtGdiDeleteObject(SafeInfo.hbmColor);
+    }
+    NTUSER_FAIL();
+  }
+  LEAVE_CRITICAL();
+  
+  END_NTUSER();
+}
+
+HWND STDCALL
+NtUserCreateWindowEx(DWORD dwExStyle,
+		     PUNICODE_STRING UnsafeClassName,
+		     PUNICODE_STRING UnsafeWindowName,
+		     DWORD dwStyle,
+		     LONG x,
+		     LONG y,
+		     LONG nWidth,
+		     LONG nHeight,
+		     HWND hWndParent,
+		     HMENU hMenu,
+		     HINSTANCE hInstance,
+		     LPVOID lpParam,
+		     DWORD dwShowMode,
+		     BOOL bUnicodeWindow)
+{
+  UNICODE_STRING SafeClassName, SafeWindowName;
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  NTUSER_USER_OBJECT(WINDOW, Parent);
+  NTSTATUS Status;
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(HWND, NULL);
+  
+  if(UnsafeWindowName != NULL)
+  {
+    Status = IntSafeCopyUnicodeString(&SafeWindowName, UnsafeWindowName);
+    if(!NT_SUCCESS(Status))
+    {
+      NTUSER_FAIL_NTERROR(Status);
+    }
+  }
+  else
+  {
+    RtlInitUnicodeString(&SafeWindowName, NULL);
+  }
+  
+  /* copy class name (NULL-Terminated! for class atom lookup */
+  NTUSER_COPY_BUFFER_NTERROR(&SafeClassName, UnsafeClassName, sizeof(UNICODE_STRING));
+  if(!IS_ATOM(SafeClassName.Buffer))
+  {
+    Status = IntSafeCopyUnicodeString(&SafeClassName, UnsafeClassName);
+    if(!NT_SUCCESS(Status))
+    {
+      NTUSER_FAIL_NTERROR(Status);
+    }
+  }
+  
+  ENTER_CRITICAL();
+  if(hWndParent != NULL)
+  {
+    VALIDATE_USER_OBJECT(WINDOW, hWndParent, Parent);
+  }
+  Window = IntCreateWindow(dwExStyle,
+                           &SafeClassName,
+			   &SafeWindowName,
+			   dwStyle,
+			   x,
+			   y,
+			   nWidth,
+			   nHeight,
+			   Parent,
+			   NULL, /* FIXME - Menu */
+			   0, /* FIXME - WindowID */
+			   hInstance,
+			   lpParam,
+			   dwShowMode,
+			   bUnicodeWindow);
+  Result = (Window != NULL ? Window->Handle : NULL);
+  LEAVE_CRITICAL();
+  
+  RtlFreeUnicodeString(&SafeWindowName);
+  if(!IS_ATOM(SafeClassName.Buffer))
+  {
+    RtlFreeUnicodeString(&SafeClassName);
+  }
+  
+  END_NTUSER();
+}
+
+BOOL STDCALL
+NtUserDestroyCursorIcon(HANDLE Handle,
+                        DWORD Unknown)
+{
+  NTUSER_USER_OBJECT(CURSOR, Cursor);
+  BEGIN_NTUSER(BOOL, FALSE);
+  
+  ENTER_CRITICAL();
+  VALIDATE_USER_OBJECT(CURSOR, Handle, Cursor);
+  Result = IntDestroyCursorObject(Cursor, TRUE);
+  LEAVE_CRITICAL();
+  
+  END_NTUSER();
+}
+
+BOOL STDCALL
+NtUserDestroyWindow(HWND hWnd)
+{
+  PW32PROCESS W32Process;
+  PETHREAD Thread;
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_NTUSER(BOOLEAN, FALSE);
+  
+  Thread = PsGetCurrentThread();
+  W32Process = PsGetWin32Process();
+  
+  ENTER_CRITICAL();
+  VALIDATE_USER_OBJECT(WINDOW, hWnd, Window);
+  
+  /* Check for owner thread and desktop window */
+  if(!IntWndBelongsToThread(Window, Thread->Win32Thread) || IntIsDesktopWindow(Window))
+  {
+    LEAVE_CRITICAL();
+    NTUSER_FAIL_ERROR(ERROR_ACCESS_DENIED);
+  }
+  
+  /* FIXME - send messages if the thread is already terminating? */
+  Result = IntDestroyWindow(Window, W32Process, Thread->Win32Thread, TRUE);
+  
+  LEAVE_CRITICAL();
+  
+  END_NTUSER();
+}
+
+LRESULT STDCALL
+NtUserDispatchMessage(PNTUSERDISPATCHMESSAGEINFO UnsafeMsgInfo)
+{
+  NTUSERDISPATCHMESSAGEINFO MsgInfo;
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(LRESULT, 0);
+  
+  NTUSER_COPY_BUFFER_NTERROR(&MsgInfo, UnsafeMsgInfo, sizeof(NTUSERDISPATCHMESSAGEINFO));
+  
+  ENTER_CRITICAL();
+  if(MsgInfo.Msg.hwnd != NULL)
+  {
+    /* win doesn't set a last error in this case */
+    VALIDATE_USER_OBJECT_NOERR(WINDOW, MsgInfo.Msg.hwnd, Window);
+    
+    if(!IntWndBelongsToThread(Window, PsGetWin32Thread()))
+    {
+      LEAVE_CRITICAL();
+      DPRINT1("Window doesn't belong to the calling thread!\n");
+      MsgInfo.HandledByKernel = TRUE;
+      goto finish;
+    }
+  }
+  Result = IntDispatchMessage(&MsgInfo, Window);
+  LEAVE_CRITICAL();
+  
+finish:
+  NTUSER_COPY_BUFFER_BACK_NTERROR(UnsafeMsgInfo, &MsgInfo, sizeof(NTUSERDISPATCHMESSAGEINFO));
+  
+  END_NTUSER();
+}
+
+BOOL STDCALL
+NtUserDrawIconEx(HDC hdc,           
+                 int xLeft,
+                 int yTop,
+                 HICON hIcon,
+                 int cxWidth,
+                 int cyWidth,
+                 UINT istepIfAniCur,
+                 HBRUSH hbrFlickerFreeDraw,
+                 UINT diFlags,
+                 DWORD Unknown0,
+                 DWORD Unknown1)
+{
+  NTUSER_USER_OBJECT(CURSOR, Cursor);
+  BEGIN_NTUSER(BOOL, FALSE);
+  
+  ENTER_CRITICAL_SHARED();
+  VALIDATE_USER_OBJECT(CURSOR, hIcon, Cursor);
+  Result = IntDrawIconEx(hdc, xLeft, yTop, Cursor, cxWidth, cyWidth, istepIfAniCur, hbrFlickerFreeDraw, diFlags);
+  LEAVE_CRITICAL();
+  
+  END_NTUSER();
+}
+
+BOOL STDCALL
+NtUserEndPaint(HWND hWnd, CONST PAINTSTRUCT* lPs)
+{
+  PAINTSTRUCT SafePs;
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(BOOL, FALSE);
+  
+  /* Apparently windows always sets the last error to ERROR_NOACCESS in case it can't copy
+     back the buffer */
+  NTUSER_COPY_BUFFER_W32ERROR(&SafePs, lPs, sizeof(PAINTSTRUCT), ERROR_NOACCESS);
+  
+  ENTER_CRITICAL();
+  if(hWnd != NULL)
+  {
+    VALIDATE_USER_OBJECT(WINDOW, hWnd, Window);
+  }
+  else
+  {
+    if(!(Window = IntGetDesktopWindow()))
+    {
+      LEAVE_CRITICAL();
+      DPRINT1("GetWindowDC(): Unable to get desktop window!\n");
+      NTUSER_FAIL_ERROR(ERROR_ACCESS_DENIED);
+    }
+  }
+  
+  Result = IntEndPaint(Window, &SafePs);
+  
+  LEAVE_CRITICAL();
+  
+  END_NTUSER();
+}
+
+HICON STDCALL
+NtUserFindExistingCursorIcon(HMODULE hModule,
+                             HRSRC hRsrc,
+                             LONG cx,
+                             LONG cy)
+{
+  NTUSER_USER_OBJECT(CURSOR, Cursor);
+  BEGIN_NTUSER(HICON, (HICON)0);
+  
+  ENTER_CRITICAL_SHARED();
+  Cursor = IntFindExistingCursorObject(hModule, hRsrc, cx, cy);
+  if(Cursor == NULL)
+  {
+     LEAVE_CRITICAL();
+     NTUSER_FAIL_ERROR(0);
+  }
+  Result = Cursor->Handle;
+  LEAVE_CRITICAL();
+  
+  END_NTUSER();
+}
+
+HWND STDCALL
+NtUserGetActiveWindow(VOID)
+{
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_NTUSER_NOERR(HWND);
+  
+  ENTER_CRITICAL_SHARED();
+  Window = IntGetActiveWindow();
+  Result = (Window != NULL ? Window->Handle : NULL);
+  LEAVE_CRITICAL();
+  
+  END_NTUSER_NOERR();
+}
+
+HWND STDCALL
+NtUserGetAncestor(HWND hWnd, UINT Type)
+{
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  NTUSER_USER_OBJECT(WINDOW, Ancestor);
+  BEGIN_NTUSER(HWND, NULL);
+  
+  switch(Type)
+  {
+    case GA_PARENT:
+    case GA_ROOT:
+    case GA_ROOTOWNER:
+    {
+      ENTER_CRITICAL();
+      VALIDATE_USER_OBJECT(WINDOW, hWnd, Window);
+      Ancestor = IntGetAncestor(Window, Type);
+      Result = (Ancestor != NULL ? Ancestor->Handle : NULL);
+      LEAVE_CRITICAL();
+      break;
+    }
+    default:
+    {
+      NTUSER_FAIL_ERROR(ERROR_INVALID_PARAMETER);
+      break;
+    }
+  }
+  
+  END_NTUSER();
+}
+
+HWND STDCALL
+NtUserGetCapture(VOID)
+{
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_NTUSER_NOERR(HWND);
+  
+  ENTER_CRITICAL_SHARED();
+  Window = IntGetCaptureWindow();
+  Result = (Window != NULL ? Window->Handle : NULL);
+  LEAVE_CRITICAL();
+  
+  END_NTUSER_NOERR();
+}
+
+DWORD STDCALL
+NtUserGetClassLong(HWND hWnd, INT Offset, BOOL Ansi)
+{
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_NTUSER(DWORD, 0);
+  
+  ENTER_CRITICAL_SHARED();
+  VALIDATE_USER_OBJECT(WINDOW, hWnd, Window);
+  Result = IntGetClassLong(Window, Offset, Ansi);
+  LEAVE_CRITICAL();
+  
+  END_NTUSER();
+}
+
+BOOL STDCALL
+NtUserGetClientOrigin(HWND hWnd, LPPOINT Point)
+{
+  POINT ClientOrigin;
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(BOOL, FALSE);
+  
+  NTUSER_FAIL_INVALID_PARAMETER(Point, NULL);
+  
+  ENTER_CRITICAL_SHARED();
+  if(hWnd != NULL)
+  {
+    VALIDATE_USER_OBJECT(WINDOW, hWnd, Window);
+  }
+  Result = IntGetClientOrigin((hWnd != NULL ? Window : NULL), &ClientOrigin);
+  LEAVE_CRITICAL();
+  
+  NTUSER_COPY_BUFFER_BACK_NTERROR(Point, &ClientOrigin, sizeof(POINT));
+  
+  END_NTUSER();
+}
+
+BOOL STDCALL
+NtUserGetClientRect(HWND hWnd, LPRECT Rect)
+{
+  RECT ClientRect;
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(BOOL, FALSE);
+  
+  NTUSER_FAIL_INVALID_PARAMETER(Rect, NULL);
+  
+  ENTER_CRITICAL_SHARED();
+  VALIDATE_USER_OBJECT(WINDOW, hWnd, Window);
+  IntGetClientRect(Window, &ClientRect);
+  LEAVE_CRITICAL();
+  
+  NTUSER_COPY_BUFFER_BACK_NTERROR(Rect, &ClientRect, sizeof(RECT));
+  
+  END_NTUSER();
+}
+
+BOOL STDCALL
+NtUserGetClipCursor(RECT *lpRect)
+{
+  RECT SafeRect;
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(BOOL, FALSE);
+  
+  NTUSER_FAIL_INVALID_PARAMETER(lpRect, NULL);
+  
+  ENTER_CRITICAL_SHARED();
+  IntGetClipCursor(&SafeRect);
+  LEAVE_CRITICAL();
+  
+  NTUSER_COPY_BUFFER_BACK_NTERROR(lpRect, &SafeRect, sizeof(RECT));
+  
+  END_NTUSER();
+}
+
+BOOL STDCALL
+NtUserGetCursorIconInfo(HANDLE Handle,
+                        PICONINFO IconInfo)
+{
+  ICONINFO SafeInfo;
+  NTUSER_USER_OBJECT(CURSOR, Cursor);
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(BOOL, FALSE);
+  
+  NTUSER_FAIL_INVALID_PARAMETER(IconInfo, NULL);
+  
+  ENTER_CRITICAL();
+  VALIDATE_USER_OBJECT(CURSOR, Handle, Cursor);
+  IntGetCursorIconInfo(Cursor, &SafeInfo);
+  LEAVE_CRITICAL();
+  
+  NTUSER_COPY_BUFFER_BACK_NTERROR(IconInfo, &SafeInfo, sizeof(ICONINFO));
+  
+  Result = TRUE;
+  
+  END_NTUSER();
+}
+
+BOOL STDCALL
+NtUserGetCursorIconSize(HANDLE Handle,
+                        BOOL *fIcon,
+                        SIZE *Size)
+{
+  BOOL SafeIsIcon;
+  SIZE SafeSize;
+  NTUSER_USER_OBJECT(CURSOR, Cursor);
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(BOOL, FALSE);
+  
+  /* FIXME - Does windows check these parameters, too? */
+  NTUSER_FAIL_INVALID_PARAMETER(fIcon, NULL);
+  NTUSER_FAIL_INVALID_PARAMETER(Size, NULL);
+  
+  ENTER_CRITICAL();
+  VALIDATE_USER_OBJECT(CURSOR, Handle, Cursor);
+  Result = IntGetCursorIconSize(Cursor, &SafeIsIcon, &SafeSize);
+  LEAVE_CRITICAL();
+  
+  /* Copy back the umode */
+  NTUSER_COPY_BUFFER_BACK_NTERROR(fIcon, &SafeIsIcon, sizeof(BOOL));
+  NTUSER_COPY_BUFFER_BACK_NTERROR(Size, &SafeSize, sizeof(SIZE));
+  
+  END_NTUSER();
+}
+
+BOOL STDCALL
+NtUserGetCursorInfo(
+  PCURSORINFO pci)
+{
+  CURSORINFO SafeCI;
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(BOOL, FALSE);
+  
+  NTUSER_FAIL_INVALID_PARAMETER(pci, NULL);
+  NTUSER_FAIL_INVALID_STRUCT(CURSORINFO, pci, cbSize);
+  
+  ENTER_CRITICAL();
+  Result = IntGetCursorInfo(&SafeCI);
+  LEAVE_CRITICAL();
+  
+  NTUSER_COPY_BUFFER_BACK_NTERROR(pci, &SafeCI, sizeof(CURSORINFO));
+  
+  END_NTUSER();
+}
+
+HDC STDCALL
+NtUserGetDC(HWND hWnd)
+{
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_NTUSER(HDC, NULL);
+  
+  ENTER_CRITICAL();
+  if(hWnd != NULL)
+  {
+    VALIDATE_USER_OBJECT(WINDOW, hWnd, Window);
+  }
+  else
+  {
+    if(!(Window = IntGetDesktopWindow()))
+    {
+      LEAVE_CRITICAL();
+      DPRINT1("GetWindowDC(): Unable to get desktop window!\n");
+      NTUSER_FAIL_ERROR(ERROR_ACCESS_DENIED);
+    }
+  }
+  
+  Result = IntGetDCEx(Window, NULL, (hWnd == NULL ? DCX_CACHE | DCX_WINDOW : DCX_USESTYLE));
+  
+  LEAVE_CRITICAL();
+  
+  END_NTUSER();
+}
+
+HDC STDCALL
+NtUserGetDCEx(HWND hWnd, HANDLE ClipRegion, ULONG Flags)
+{
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_NTUSER(HDC, NULL);
+  
+  ENTER_CRITICAL();
+  if(hWnd != NULL)
+  {
+    VALIDATE_USER_OBJECT(WINDOW, hWnd, Window);
+  }
+  else
+  {
+    if(!(Window = IntGetDesktopWindow()))
+    {
+      LEAVE_CRITICAL();
+      DPRINT1("GetWindowDC(): Unable to get desktop window!\n");
+      NTUSER_FAIL_ERROR(ERROR_ACCESS_DENIED);
+    }
+  }
+  
+  Result = IntGetDCEx(Window, ClipRegion, Flags);
+  
+  LEAVE_CRITICAL();
+  
+  END_NTUSER();
+}
+
+HWND STDCALL
+NtUserGetDesktopWindow()
+{
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_NTUSER_NOERR(HWND);
+  
+  ENTER_CRITICAL();
+  Window = IntGetDesktopWindow();
+  Result = (Window != NULL ? Window->Handle : NULL);
+  LEAVE_CRITICAL();
+  
+  END_NTUSER_NOERR();
+}
+
+HWND STDCALL
+NtUserGetForegroundWindow(VOID)
+{
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_NTUSER_NOERR(HWND);
+  
+  ENTER_CRITICAL_SHARED();
+  Window = IntGetForegroundWindow();
+  Result = (Window != NULL ? Window->Handle : NULL);
+  LEAVE_CRITICAL();
+  
+  END_NTUSER_NOERR();
+}
+
+BOOL STDCALL
+NtUserGetMessage(PNTUSERGETMESSAGEINFO UnsafeInfo,
+		 HWND Wnd,
+		 UINT MsgFilterMin,
+		 UINT MsgFilterMax)
+{
+  NTUSERGETMESSAGEINFO Info;
+  USER_MESSAGE Msg;
+  BOOL GotMessage;
+  NTUSER_USER_OBJECT(WINDOW, Window);
+  BEGIN_BUFFERS();
+  BEGIN_NTUSER(BOOL, FALSE);
+  
+  NTUSER_FAIL_INVALID_PARAMETER(UnsafeInfo, NULL);
+  
+  /* Fix the filter */
+  if(MsgFilterMax < MsgFilterMin)
+  {
+    MsgFilterMin = 0;
+    MsgFilterMax = 0;
+  }
+  
+  GotMessage = FALSE;
[truncated at 1000 lines; 905 more skipped]

reactos/subsys/win32k/ntuser
userlock.c added at 1.1.4.1
diff -N userlock.c
--- /dev/null	1 Jan 1970 00:00:00 -0000
+++ userlock.c	15 Jul 2004 20:12:56 -0000	1.1.4.1
@@ -0,0 +1,70 @@
+/*
+ *  ReactOS W32 Subsystem
+ *  Copyright (C) 1998 - 2004 ReactOS Team
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License as published by
+ *  the Free Software Foundation; either version 2 of the License, or
+ *  (at your option) any later version.
+ *
+ *  This program 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 General Public License for more details.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with this program; if not, write to the Free Software
+ *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+/* $Id: userlock.c,v 1.1.4.1 2004/07/15 20:12:56 weiden Exp $
+ *
+ * COPYRIGHT:        See COPYING in the top level directory
+ * PROJECT:          ReactOS kernel
+ * PURPOSE:          User locks
+ * FILE:             subsys/win32k/ntuser/userlock.c
+ * PROGRAMER:        Thomas Weidenmueller <w3seek@reactos.com>
+ * REVISION HISTORY:
+ *       06-06-2001  CSH  Created
+ */
+#include <w32k.h>
+
+static ERESOURCE UserLock;
+
+
+VOID FASTCALL
+IntInitUserResourceLocks(VOID)
+{
+  ExInitializeResourceLite(&UserLock);
+}
+
+VOID FASTCALL
+IntCleanupUserResourceLocks(VOID)
+{
+  ExDeleteResourceLite(&UserLock);
+}
+
+inline VOID
+IntUserEnterCritical(VOID)
+{
+  ExAcquireResourceExclusiveLite(&UserLock, TRUE);
+}
+
+inline VOID
+IntUserEnterCriticalShared(VOID)
+{
+  ExAcquireResourceSharedLite(&UserLock, TRUE);
+}
+
+inline VOID
+IntUserLeaveCritical(VOID)
+{
+  ExReleaseResourceLite(&UserLock);
+}
+
+inline BOOL
+IntUserIsInCritical(VOID)
+{
+  /* Exclusive locks are shared locks at the same time */
+  return ExIsResourceAcquiredSharedLite(&UserLock);
+}
+
CVSspam 0.2.8