[CONSRV][WIN32K]
authorHermès Bélusca-Maïto <hermes.belusca-maito@reactos.org>
Sun, 20 Oct 2013 22:35:15 +0000 (22:35 +0000)
committerHermès Bélusca-Maïto <hermes.belusca-maito@reactos.org>
Sun, 20 Oct 2013 22:35:15 +0000 (22:35 +0000)
- Fix console palette setting; introduce the ConsoleMakePalettePublic control code for NtUserConsoleControl API which
  is called by the SetConsolePalette to make the given palette handle public (indeed, the caller to SetConsoleHandle
  gives to this API a GDI palette handle which is aimed at being used by another process, i.e. by CSRSS.EXE; in normal
  operation this is impossible unless saying to GDI that the handle is meant to be public; that's what it's done there).

  Thanks to Aleksander and David (who provided tests) and Timo (see revision 60725) for having helped me in understanding
  what happened exactly there.

- Remove now-unneeded DPRINT1s and the hacked palette that was introduced in revision 60629/60641.

Part 1/2

svn path=/trunk/; revision=60726

reactos/win32ss/include/ntuser.h
reactos/win32ss/user/ntuser/ntstubs.c
reactos/win32ss/user/winsrv/consrv/condrv/conoutput.c
reactos/win32ss/user/winsrv/consrv/conoutput.c

index 1677a76..862fae5 100644 (file)
@@ -1571,6 +1571,7 @@ NtUserCloseWindowStation(
 typedef enum _CONSOLECONTROL
 {
     GuiConsoleWndClassAtom,
+    ConsoleMakePalettePublic = 5,
     ConsoleAcquireDisplayOwnership,
 } CONSOLECONTROL, *PCONSOLECONTROL;
 
@@ -1579,7 +1580,7 @@ APIENTRY
 NtUserConsoleControl(
     IN CONSOLECONTROL ConsoleCtrl,
     IN PVOID ConsoleCtrlInfo,
-    IN DWORD ConsoleCtrlInfoLength);
+    IN ULONG ConsoleCtrlInfoLength);
 
 HANDLE
 NTAPI
index b421f57..ab165f4 100644 (file)
@@ -546,7 +546,7 @@ APIENTRY
 NtUserConsoleControl(
     IN CONSOLECONTROL ConsoleCtrl,
     IN PVOID ConsoleCtrlInfo,
-    IN DWORD ConsoleCtrlInfoLength)
+    IN ULONG ConsoleCtrlInfoLength)
 {
     NTSTATUS Status = STATUS_SUCCESS;
 
@@ -562,8 +562,8 @@ NtUserConsoleControl(
         {
             _SEH2_TRY
             {
-                ProbeForRead(ConsoleCtrlInfo, ConsoleCtrlInfoLength, 1);
                 ASSERT(ConsoleCtrlInfoLength == sizeof(ATOM));
+                ProbeForRead(ConsoleCtrlInfo, ConsoleCtrlInfoLength, 1);
                 gaGuiConsoleWndClass = *(ATOM*)ConsoleCtrlInfo;
             }
             _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
@@ -575,8 +575,33 @@ NtUserConsoleControl(
             break;
         }
 
+        case ConsoleMakePalettePublic:
+        {
+            _SEH2_TRY
+            {
+                ASSERT(ConsoleCtrlInfoLength == sizeof(HPALETTE));
+                ProbeForRead(ConsoleCtrlInfo, ConsoleCtrlInfoLength, 1);
+                /*
+                 * Make the palette handle public - Use the extended
+                 * function introduced by Timo in revision 60725.
+                 */
+                GreSetObjectOwnerEx(*(HPALETTE*)ConsoleCtrlInfo,
+                                    GDI_OBJ_HMGR_PUBLIC,
+                                    GDIOBJFLAG_IGNOREPID);
+            }
+            _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
+            {
+                Status = _SEH2_GetExceptionCode();
+            }
+            _SEH2_END;
+
+            break;
+        }
+
         case ConsoleAcquireDisplayOwnership:
         {
+            ERR("NtUserConsoleControl - ConsoleAcquireDisplayOwnership is UNIMPLEMENTED\n");
+            Status = STATUS_NOT_IMPLEMENTED;
             break;
         }
 
index a4f3887..27bbe48 100644 (file)
@@ -237,8 +237,6 @@ ConDrvSetConsolePalette(IN PCONSOLE Console,
 {
     BOOL Success;
 
-    DPRINT1("ConDrvSetConsolePalette\n");
-
     /*
      * Parameters validation
      */
@@ -256,11 +254,9 @@ ConDrvSetConsolePalette(IN PCONSOLE Console,
     ASSERT(Console == Buffer->Header.Console);
 
     /* Change the palette */
-    DPRINT1("ConDrvSetConsolePalette calling TermSetPalette\n");
     Success = TermSetPalette(Console, PaletteHandle, PaletteUsage);
     if (Success)
     {
-        DPRINT1("TermSetPalette succeeded\n");
         /* Free the old palette handle if there was already one set */
         if ( Buffer->PaletteHandle != NULL &&
              Buffer->PaletteHandle != PaletteHandle )
@@ -272,10 +268,6 @@ ConDrvSetConsolePalette(IN PCONSOLE Console,
         Buffer->PaletteHandle = PaletteHandle;
         Buffer->PaletteUsage  = PaletteUsage;
     }
-    else
-    {
-        DPRINT1("TermSetPalette failed\n");
-    }
 
     return (Success ? STATUS_SUCCESS : STATUS_UNSUCCESSFUL);
 }
index bca67fd..e7ea384 100644 (file)
@@ -63,38 +63,7 @@ CSR_API(SrvSetConsolePalette)
     // PGRAPHICS_SCREEN_BUFFER Buffer;
     PCONSOLE_SCREEN_BUFFER Buffer;
 
-
-/******************************************************************************\
-|************** HACK! HACK! HACK! HACK! HACK! HACK! HACK! HACK! ***************|
-\******************************************************************************/
-
-#define PALETTESIZE 256
-
-    LPLOGPALETTE LogPalette;                  /* Pointer to logical palette */
-    PALETTEENTRY MyPalette[] =
-    { {0,   0,   0x80,0} ,       // 1
-      {0,   0x80,0,   0} ,       // 2
-      {0,   0,   0,   0} ,       // 0
-      {0,   0x80,0x80,0} ,       // 3
-      {0x80,0,   0,   0} ,       // 4
-      {0x80,0,   0x80,0} ,       // 5
-      {0x80,0x80,0,   0} ,       // 6
-      {0xC0,0xC0,0xC0,0} ,       // 7
-      {0x80,0x80,0x80,0} ,       // 8
-      {0,   0,   0xFF,0} ,       // 9
-      {0,   0xFF,0,   0} ,       // 10
-      {0,   0xFF,0xFF,0} ,       // 11
-      {0xFF,0,   0,   0} ,       // 12
-      {0xFF,0,   0xFF,0} ,       // 13
-      {0xFF,0xFF,0,   0} ,       // 14
-      {0xFF,0xFF,0xFF,0} };      // 15
-
-/******************************************************************************\
-|************** HACK! HACK! HACK! HACK! HACK! HACK! HACK! HACK! ***************|
-\******************************************************************************/
-
-
-    DPRINT1("SrvSetConsolePalette\n");
+    DPRINT("SrvSetConsolePalette\n");
 
     // NOTE: Tests show that this function is used only for graphics screen buffers
     // and otherwise it returns FALSE + sets last error to invalid handle.
@@ -111,51 +80,21 @@ CSR_API(SrvSetConsolePalette)
                                    &Buffer, GENERIC_WRITE, TRUE);
     if (!NT_SUCCESS(Status)) return Status;
 
-
-/******************************************************************************\
-|************** HACK! HACK! HACK! HACK! HACK! HACK! HACK! HACK! ***************|
-\******************************************************************************/
-
-    DPRINT1("HACK: FIXME: SrvSetConsolePalette - Use hacked palette for testing purposes!!\n");
-
-    LogPalette = (LPLOGPALETTE)ConsoleAllocHeap(HEAP_ZERO_MEMORY,
-                                                (sizeof(LOGPALETTE) +
-                                                (sizeof(PALETTEENTRY) * PALETTESIZE)));
-    if (LogPalette)
-    {
-        UINT i;
-
-        LogPalette->palVersion = 0x300;
-        LogPalette->palNumEntries = PALETTESIZE;
-
-        for (i = 0 ; i < PALETTESIZE ; i++)
-        {
-            LogPalette->palPalEntry[i] = MyPalette[i % sizeof(MyPalette)/sizeof(MyPalette[0])];
-        }
-
-        SetPaletteRequest->PaletteHandle = CreatePalette(LogPalette);
-        SetPaletteRequest->Usage = SYSPAL_NOSTATIC256;
-        ConsoleFreeHeap(LogPalette);
-    }
-    else
-    {
-        DPRINT1("SrvSetConsolePalette - Hacked LogPalette is NULL\n");
-    }
-
-/******************************************************************************\
-|************** HACK! HACK! HACK! HACK! HACK! HACK! HACK! HACK! ***************|
-\******************************************************************************/
-
-
-    DPRINT1("ConDrvSetConsolePalette calling...\n");
+    /*
+     * Make the palette handle public, so that it can be
+     * used by other threads calling GDI functions on it.
+     * Indeed, the palette handle comes from a console app
+     * calling ourselves, running in CSRSS.
+     */
+    NtUserConsoleControl(ConsoleMakePalettePublic,
+                         &SetPaletteRequest->PaletteHandle,
+                         sizeof(SetPaletteRequest->PaletteHandle));
 
     Status = ConDrvSetConsolePalette(Buffer->Header.Console,
                                      Buffer,
                                      SetPaletteRequest->PaletteHandle,
                                      SetPaletteRequest->Usage);
 
-    DPRINT1("ConDrvSetConsolePalette returned Status 0x%08lx\n", Status);
-
     ConSrvReleaseScreenBuffer(Buffer, TRUE);
     return Status;
 }