fix bug 838 (Sol.exe is missing it's menubar)
[reactos.git] / reactos / subsys / win32k / ntuser / window.c
index 114a883..d0f24bd 100644 (file)
@@ -239,7 +239,8 @@ static void IntSendDestroyMsg(HWND hWnd)
    Window = UserGetWindowObject(hWnd);
    if (Window)
    {
-//      UserRefObjectCo(Window);
+//      USER_REFERENCE_ENTRY Ref;
+//      UserRefObjectCo(Window, &Ref);
       
       if (!IntGetOwner(Window) && !IntGetParent(Window))
       {
@@ -569,8 +570,8 @@ co_DestroyThreadWindows(struct _ETHREAD *Thread)
    PW32THREAD WThread;
    PLIST_ENTRY Current;
    PWINDOW_OBJECT Wnd;
-
-   WThread = Thread->Tcb.Win32Thread;
+   USER_REFERENCE_ENTRY Ref;
+   WThread = (PW32THREAD)Thread->Tcb.Win32Thread;
    
    while (!IsListEmpty(&WThread->WindowListHead))
    {
@@ -588,7 +589,7 @@ co_DestroyThreadWindows(struct _ETHREAD *Thread)
       
       //ASSERT(co_UserDestroyWindow(Wnd));
       
-      UserRefObjectCo(Wnd);//faxme: temp hack??
+      UserRefObjectCo(Wnd, &Ref);//faxme: temp hack??
       if (!co_UserDestroyWindow(Wnd))
       {
          DPRINT1("Unable to destroy window 0x%x at thread cleanup... This is _VERY_ bad!\n", Wnd);
@@ -1120,7 +1121,7 @@ NtUserBuildHwndList(
          SetLastWin32Error(ERROR_INVALID_PARAMETER);
          return 0;
       }
-      if(!(W32Thread = Thread->Tcb.Win32Thread))
+      if(!(W32Thread = (PW32THREAD)Thread->Tcb.Win32Thread))
       {
          ObDereferenceObject(Thread);
          DPRINT("Thread is not a GUI Thread!\n");
@@ -1355,6 +1356,7 @@ co_IntCreateWindowEx(DWORD dwExStyle,
    BOOL MenuChanged;
    DECLARE_RETURN(HWND);
    BOOL HasOwner;
+   USER_REFERENCE_ENTRY ParentRef, Ref;
 
    ParentWindowHandle = PsGetWin32Thread()->Desktop->DesktopWindow;
    OwnerWindowHandle = NULL;
@@ -1388,7 +1390,7 @@ co_IntCreateWindowEx(DWORD dwExStyle,
 //   {
    ParentWindow = UserGetWindowObject(ParentWindowHandle);
 
-   if (ParentWindow) UserRefObjectCo(ParentWindow);
+   if (ParentWindow) UserRefObjectCo(ParentWindow, &ParentRef);
 //   }
 //   else
 //   {
@@ -1441,7 +1443,7 @@ co_IntCreateWindowEx(DWORD dwExStyle,
       RETURN( (HWND)0);
    }
 
-   UserRefObjectCo(Window);
+   UserRefObjectCo(Window, &Ref);
 
    ObDereferenceObject(WinSta);
 
@@ -1460,6 +1462,10 @@ co_IntCreateWindowEx(DWORD dwExStyle,
    Window->IDMenu = 0;
    Window->Instance = hInstance;
    Window->hSelf = hWnd;
+
+   if (!hMenu)
+       hMenu = Class->hMenu;
+
    if (0 != (dwStyle & WS_CHILD))
    {
       Window->IDMenu = (UINT) hMenu;
@@ -1620,7 +1626,7 @@ co_IntCreateWindowEx(DWORD dwExStyle,
       PRTL_USER_PROCESS_PARAMETERS ProcessParams;
       BOOL CalculatedDefPosSize = FALSE;
 
-      IntGetDesktopWorkArea(Window->OwnerThread->Tcb.Win32Thread->Desktop, &WorkArea);
+      IntGetDesktopWorkArea(((PW32THREAD)Window->OwnerThread->Tcb.Win32Thread)->Desktop, &WorkArea);
 
       rc = WorkArea;
       ProcessParams = PsGetCurrentProcess()->Peb->ProcessParameters;
@@ -1710,18 +1716,18 @@ co_IntCreateWindowEx(DWORD dwExStyle,
       /* WinPosGetMinMaxInfo sends the WM_GETMINMAXINFO message */
       co_WinPosGetMinMaxInfo(Window, &MaxSize, &MaxPos, &MinTrack,
                              &MaxTrack);
-      if (MaxSize.x < nWidth)
-         nWidth = MaxSize.x;
-      if (MaxSize.y < nHeight)
-         nHeight = MaxSize.y;
-      if (nWidth < MinTrack.x )
-         nWidth = MinTrack.x;
-      if (nHeight < MinTrack.y )
-         nHeight = MinTrack.y;
-      if (nWidth < 0)
-         nWidth = 0;
-      if (nHeight < 0)
-         nHeight = 0;
+      if (MaxSize.x < Size.cx)
+         Size.cx = MaxSize.x;
+      if (MaxSize.y < Size.cy)
+         Size.cy = MaxSize.y;
+      if (Size.cx < MinTrack.x )
+         Size.cx = MinTrack.x;
+      if (Size.cy < MinTrack.y )
+         Size.cy = MinTrack.y;
+      if (Size.cx < 0)
+         Size.cx = 0;
+      if (Size.cy < 0)
+         Size.cy = 0;
    }
 
    Window->WindowRect.left = Pos.x;
@@ -1744,7 +1750,7 @@ co_IntCreateWindowEx(DWORD dwExStyle,
    Cs.y = Pos.y;
 
    DPRINT("[win32k.window] IntCreateWindowEx style %d, exstyle %d, parent %d\n", Cs.style, Cs.dwExStyle, Cs.hwndParent);
-   DPRINT("IntCreateWindowEx(): (%d,%d-%d,%d)\n", x, y, nWidth, nHeight);
+   DPRINT("IntCreateWindowEx(): (%d,%d-%d,%d)\n", x, y, Size.cx, Size.cy);
    DPRINT("IntCreateWindowEx(): About to send NCCREATE message.\n");
    Result = co_IntSendMessage(Window->hSelf, WM_NCCREATE, 0, (LPARAM) &Cs);
    if (!Result)
@@ -2032,8 +2038,8 @@ BOOLEAN FASTCALL co_UserDestroyWindow(PWINDOW_OBJECT Window)
 
    ASSERT_REFS_CO(Window); //fixme: temp hack?
 
-   /* Check for owner thread and desktop window */
-   if ((Window->OwnerThread != PsGetCurrentThread()) || IntIsDesktopWindow(Window))
+   /* Check for owner thread */
+   if ((Window->OwnerThread != PsGetCurrentThread()))
    {
       SetLastWin32Error(ERROR_ACCESS_DENIED);
       return FALSE;
@@ -2101,7 +2107,8 @@ BOOLEAN FASTCALL co_UserDestroyWindow(PWINDOW_OBJECT Window)
          HWND *ChildHandle;
          PWINDOW_OBJECT Child, Desktop;
 
-         Desktop = UserGetWindowObject(IntGetDesktopWindow());
+         Desktop = IntIsDesktopWindow(Window) ? Window :
+                   UserGetWindowObject(IntGetDesktopWindow());
          Children = IntWinListChildren(Desktop);
 
          if (Children)
@@ -2118,8 +2125,8 @@ BOOLEAN FASTCALL co_UserDestroyWindow(PWINDOW_OBJECT Window)
 
                if (IntWndBelongsToThread(Child, PsGetWin32Thread()))
                {
-
-                  UserRefObjectCo(Child);//temp hack?
+                  USER_REFERENCE_ENTRY ChildRef;
+                  UserRefObjectCo(Child, &ChildRef);//temp hack?
                   co_UserDestroyWindow(Child);
                   UserDerefObjectCo(Child);//temp hack?
 
@@ -2165,6 +2172,7 @@ NtUserDestroyWindow(HWND Wnd)
    PWINDOW_OBJECT Window;
    DECLARE_RETURN(BOOLEAN);
    BOOLEAN ret;
+   USER_REFERENCE_ENTRY Ref;
 
    DPRINT("Enter NtUserDestroyWindow\n");
    UserEnterExclusive();
@@ -2174,7 +2182,7 @@ NtUserDestroyWindow(HWND Wnd)
       RETURN(FALSE);
    }
 
-   UserRefObjectCo(Window);//faxme: dunno if win should be reffed during destroy..
+   UserRefObjectCo(Window, &Ref);//faxme: dunno if win should be reffed during destroy..
    ret = co_UserDestroyWindow(Window);
    UserDerefObjectCo(Window);//faxme: dunno if win should be reffed during destroy..
 
@@ -2270,7 +2278,7 @@ IntFindWindow(PWINDOW_OBJECT Parent,
          /* Do not send WM_GETTEXT messages in the kernel mode version!
             The user mode version however calls GetWindowText() which will
             send WM_GETTEXT messages to windows belonging to its processes */
-         if((!CheckWindowName || !RtlCompareUnicodeString(WindowName, &(Child->WindowName), FALSE)) &&
+         if((!CheckWindowName || !RtlCompareUnicodeString(WindowName, &(Child->WindowName), TRUE)) &&
                (!ClassAtom || Child->Class->Atom == ClassAtom))
          {
             Ret = Child->hSelf;
@@ -2449,7 +2457,7 @@ NtUserFindWindowEx(HWND hwndParent,
                The user mode version however calls GetWindowText() which will
                send WM_GETTEXT messages to windows belonging to its processes */
             WindowMatches = !CheckWindowName || !RtlCompareUnicodeString(
-                               &WindowName, &TopLevelWindow->WindowName, FALSE);
+                               &WindowName, &TopLevelWindow->WindowName, TRUE);
             ClassMatches = !CheckClassName ||
                            ClassAtom == TopLevelWindow->Class->Atom;
 
@@ -2778,6 +2786,7 @@ co_UserSetParent(HWND hWndChild, HWND hWndNewParent)
 {
    PWINDOW_OBJECT Wnd = NULL, WndParent = NULL, WndOldParent;
    HWND hWndOldParent = NULL;
+   USER_REFERENCE_ENTRY Ref, ParentRef;
 
    if (IntIsBroadcastHwnd(hWndChild) || IntIsBroadcastHwnd(hWndNewParent))
    {
@@ -2811,8 +2820,8 @@ co_UserSetParent(HWND hWndChild, HWND hWndNewParent)
       return( NULL);
    }
 
-   UserRefObjectCo(Wnd);
-   UserRefObjectCo(WndParent);
+   UserRefObjectCo(Wnd, &Ref);
+   UserRefObjectCo(WndParent, &ParentRef);
    
    WndOldParent = co_IntSetParent(Wnd, WndParent);
    
@@ -2930,6 +2939,7 @@ NtUserSetShellWindowEx(HWND hwndShell, HWND hwndListView)
    PWINSTATION_OBJECT WinStaObject;
    PWINDOW_OBJECT WndShell;
    DECLARE_RETURN(BOOL);
+   USER_REFERENCE_ENTRY Ref;
 
    DPRINT("Enter NtUserSetShellWindowEx\n");
    UserEnterExclusive();
@@ -2985,7 +2995,7 @@ NtUserSetShellWindowEx(HWND hwndShell, HWND hwndListView)
       RETURN( FALSE);
    }
 
-   UserRefObjectCo(WndShell);
+   UserRefObjectCo(WndShell, &Ref);
    co_WinPosSetWindowPos(WndShell, HWND_BOTTOM, 0, 0, 0, 0, SWP_NOMOVE|SWP_NOSIZE|SWP_NOACTIVATE);
 
    WinStaObject->ShellWindow = hwndShell;
@@ -3357,7 +3367,7 @@ co_UserSetWindowLong(HWND hWnd, DWORD Index, LONG NewValue, BOOL Ansi)
             /*
              * Remove extended window style bit WS_EX_TOPMOST for shell windows.
              */
-            WindowStation = Window->OwnerThread->Tcb.Win32Thread->Desktop->WindowStation;
+            WindowStation = ((PW32THREAD)Window->OwnerThread->Tcb.Win32Thread)->Desktop->WindowStation;
             if(WindowStation)
             {
                if (hWnd == WindowStation->ShellWindow || hWnd == WindowStation->ShellListView)
@@ -3548,7 +3558,23 @@ NtUserGetWindowPlacement(HWND hWnd,
    }
 
    Safepl.flags = 0;
-   Safepl.showCmd = ((Window->Flags & WINDOWOBJECT_RESTOREMAX) ? SW_MAXIMIZE : SW_SHOWNORMAL);
+   if (0 == (Window->Style & WS_VISIBLE))
+   {
+      Safepl.showCmd = SW_HIDE;
+   }
+   else if (0 != (Window->Flags & WINDOWOBJECT_RESTOREMAX) ||
+            0 != (Window->Style & WS_MAXIMIZE))
+   {
+      Safepl.showCmd = SW_MAXIMIZE;
+   }
+   else if (0 != (Window->Style & WS_MINIMIZE))
+   {
+      Safepl.showCmd = SW_MINIMIZE;
+   }
+   else if (0 != (Window->Style & WS_MINIMIZE))
+   {
+      Safepl.showCmd = SW_SHOWNORMAL;
+   }
 
    Size.x = Window->WindowRect.left;
    Size.y = Window->WindowRect.top;
@@ -3876,7 +3902,9 @@ NtUserSetMenu(
 
    if (Changed && Repaint)
    {
-      UserRefObjectCo(Window);
+      USER_REFERENCE_ENTRY Ref;
+
+      UserRefObjectCo(Window, &Ref);
       co_WinPosSetWindowPos(Window, 0, 0, 0, 0, 0, SWP_NOSIZE | SWP_NOMOVE |
                             SWP_NOACTIVATE | SWP_NOZORDER | SWP_FRAMECHANGED);
 
@@ -3917,6 +3945,7 @@ NtUserSetWindowPlacement(HWND hWnd,
    WINDOWPLACEMENT Safepl;
    NTSTATUS Status;
    DECLARE_RETURN(BOOL);
+   USER_REFERENCE_ENTRY Ref;
 
    DPRINT("Enter NtUserSetWindowPlacement\n");
    UserEnterExclusive();
@@ -3936,7 +3965,7 @@ NtUserSetWindowPlacement(HWND hWnd,
       RETURN( FALSE);
    }
 
-   UserRefObjectCo(Window);
+   UserRefObjectCo(Window, &Ref);
 
    if ((Window->Style & (WS_MAXIMIZE | WS_MINIMIZE)) == 0)
    {
@@ -3982,6 +4011,7 @@ NtUserSetWindowPos(
    DECLARE_RETURN(BOOL);
    PWINDOW_OBJECT Window;
    BOOL ret;
+   USER_REFERENCE_ENTRY Ref;
 
    DPRINT("Enter NtUserSetWindowPos\n");
    UserEnterExclusive();
@@ -3991,7 +4021,7 @@ NtUserSetWindowPos(
       RETURN(FALSE);
    }
 
-   UserRefObjectCo(Window);
+   UserRefObjectCo(Window, &Ref);
    ret = co_WinPosSetWindowPos(Window, hWndInsertAfter, X, Y, cx, cy, uFlags);
    UserDerefObjectCo(Window);
 
@@ -4114,7 +4144,8 @@ NtUserSetWindowRgn(
 
    if(bRedraw)
    {
-      UserRefObjectCo(Window);
+      USER_REFERENCE_ENTRY Ref;
+      UserRefObjectCo(Window, &Ref);
       co_UserRedrawWindow(Window, NULL, NULL, RDW_INVALIDATE);
       UserDerefObjectCo(Window);
    }
@@ -4137,6 +4168,7 @@ NtUserShowWindow(HWND hWnd, LONG nCmdShow)
    PWINDOW_OBJECT Window;
    BOOL ret;
    DECLARE_RETURN(BOOL);
+   USER_REFERENCE_ENTRY Ref;
 
    DPRINT("Enter NtUserShowWindow\n");
    UserEnterExclusive();
@@ -4146,7 +4178,7 @@ NtUserShowWindow(HWND hWnd, LONG nCmdShow)
       RETURN(FALSE);
    }
 
-   UserRefObjectCo(Window);
+   UserRefObjectCo(Window, &Ref);
    ret = co_WinPosShowWindow(Window, nCmdShow);
    UserDerefObjectCo(Window);
 
@@ -4162,13 +4194,15 @@ CLEANUP:
 /*
  * @unimplemented
  */
-DWORD STDCALL
-NtUserShowWindowAsync(DWORD Unknown0,
-                      DWORD Unknown1)
+BOOL STDCALL
+NtUserShowWindowAsync(HWND hWnd, LONG nCmdShow)
 {
+#if 0
    UNIMPLEMENTED
-
    return 0;
+#else
+   return NtUserShowWindow(hWnd, nCmdShow);
+#endif
 }
 
 
@@ -4204,6 +4238,7 @@ NtUserWindowFromPoint(LONG X, LONG Y)
    HWND Ret;
    PWINDOW_OBJECT DesktopWindow = NULL, Window = NULL;
    DECLARE_RETURN(HWND);
+   USER_REFERENCE_ENTRY Ref;
 
    DPRINT("Enter NtUserWindowFromPoint\n");
    UserEnterExclusive();
@@ -4217,7 +4252,7 @@ NtUserWindowFromPoint(LONG X, LONG Y)
 
       //hmm... threads live on desktops thus we have a reference on the desktop and indirectly the desktop window
       //its possible this referencing is useless, thou it shouldnt hurt...
-      UserRefObjectCo(DesktopWindow);
+      UserRefObjectCo(DesktopWindow, &Ref);
       
       Hit = co_WinPosWindowFromPoint(DesktopWindow, PsGetWin32Thread()->MessageQueue, &pt, &Window);