3 * COPYRIGHT: See COPYING in the top level directory
4 * PROJECT: ReactOS system libraries
5 * FILE: subsys/csrss/win32csr/guiconsole.c
6 * PURPOSE: Implementation of gui-mode consoles
9 /* INCLUDES ******************************************************************/
16 /* Not defined in any header file */
17 extern VOID STDCALL
PrivateCsrssManualGuiCheck(LONG Check
);
19 /* GLOBALS *******************************************************************/
21 typedef struct GUI_CONSOLE_DATA_TAG
29 CRITICAL_SECTION Lock
;
33 HMODULE ConsoleLibrary
;
35 WCHAR FontName
[LF_FACESIZE
];
43 } GUI_CONSOLE_DATA
, *PGUI_CONSOLE_DATA
;
48 #define PM_CREATE_CONSOLE (WM_APP + 1)
49 #define PM_DESTROY_CONSOLE (WM_APP + 2)
51 #define CURSOR_BLINK_TIME 500
53 static BOOL ConsInitialized
= FALSE
;
54 static HWND NotifyWnd
;
56 typedef struct _GUICONSOLE_MENUITEM
59 const struct _GUICONSOLE_MENUITEM
*SubMenu
;
61 } GUICONSOLE_MENUITEM
, *PGUICONSOLE_MENUITEM
;
63 static const GUICONSOLE_MENUITEM GuiConsoleEditMenuItems
[] =
65 { IDS_MARK
, NULL
, ID_SYSTEM_EDIT_MARK
},
66 { IDS_COPY
, NULL
, ID_SYSTEM_EDIT_COPY
},
67 { IDS_PASTE
, NULL
, ID_SYSTEM_EDIT_PASTE
},
68 { IDS_SELECTALL
, NULL
, ID_SYSTEM_EDIT_SELECTALL
},
69 { IDS_SCROLL
, NULL
, ID_SYSTEM_EDIT_SCROLL
},
70 { IDS_FIND
, NULL
, ID_SYSTEM_EDIT_FIND
},
72 { 0, NULL
, 0 } /* End of list */
75 static const GUICONSOLE_MENUITEM GuiConsoleMainMenuItems
[] =
77 { (UINT
)-1, NULL
, 0 }, /* Separator */
78 { IDS_EDIT
, GuiConsoleEditMenuItems
, 0 },
79 { IDS_DEFAULTS
, NULL
, ID_SYSTEM_DEFAULTS
},
80 { IDS_PROPERTIES
, NULL
, ID_SYSTEM_PROPERTIES
},
82 { 0, NULL
, 0 } /* End of list */
85 /* FUNCTIONS *****************************************************************/
88 GuiConsoleAppendMenuItems(HMENU hMenu
,
89 const GUICONSOLE_MENUITEM
*Items
)
92 WCHAR szMenuString
[255];
95 for (i
= 0; Items
[i
].uID
!= 0; i
++)
97 if (Items
[i
].uID
!= (UINT
)-1)
99 if (LoadStringW(Win32CsrDllHandle
,
102 sizeof(szMenuString
) / sizeof(szMenuString
[0])) > 0)
104 if (Items
[i
].SubMenu
!= NULL
)
106 hSubMenu
= CreatePopupMenu();
107 if (hSubMenu
!= NULL
)
109 GuiConsoleAppendMenuItems(hSubMenu
,
112 if (!AppendMenuW(hMenu
,
113 MF_STRING
| MF_POPUP
,
117 DestroyMenu(hSubMenu
);
141 GuiConsoleCreateSysMenu(PCSRSS_CONSOLE Console
)
145 hMenu
= GetSystemMenu(Console
->hWindow
,
149 GuiConsoleAppendMenuItems(hMenu
,
150 GuiConsoleMainMenuItems
);
155 GuiConsoleGetDataPointers(HWND hWnd
, PCSRSS_CONSOLE
*Console
, PGUI_CONSOLE_DATA
*GuiData
)
157 *Console
= (PCSRSS_CONSOLE
) GetWindowLongPtrW(hWnd
, GWL_USERDATA
);
158 *GuiData
= (NULL
== *Console
? NULL
: (*Console
)->PrivateData
);
162 GuiConsoleOpenUserRegistryPathPerProcessId(DWORD ProcessId
, PHANDLE hProcHandle
, PHKEY hResult
, REGSAM samDesired
)
164 HANDLE hProcessToken
= NULL
;
169 UNICODE_STRING SidName
;
173 hProcess
= OpenProcess(PROCESS_QUERY_INFORMATION
| PROCESS_VM_READ
| READ_CONTROL
, FALSE
, ProcessId
);
176 DPRINT("Error: OpenProcess failed(0x%x)\n", GetLastError());
180 if (!OpenProcessToken(hProcess
, TOKEN_QUERY
, &hProcessToken
))
182 DPRINT("Error: OpenProcessToken failed(0x%x)\n", GetLastError());
183 CloseHandle(hProcess
);
187 if (!GetTokenInformation(hProcessToken
, TokenUser
, (PVOID
)Buffer
, sizeof(Buffer
), &Length
))
189 DPRINT("Error: GetTokenInformation failed(0x%x)\n",GetLastError());
190 CloseHandle(hProcess
);
191 CloseHandle(hProcessToken
);
195 TokUser
= ((PTOKEN_USER
)Buffer
)->User
.Sid
;
196 if (!NT_SUCCESS(RtlConvertSidToUnicodeString(&SidName
, TokUser
, TRUE
)))
198 DPRINT("Error: RtlConvertSidToUnicodeString failed(0x%x)\n", GetLastError());
202 res
= RegOpenKeyExW(HKEY_USERS
, SidName
.Buffer
, 0, samDesired
, hResult
);
203 RtlFreeUnicodeString(&SidName
);
205 CloseHandle(hProcessToken
);
207 *hProcHandle
= hProcess
;
209 CloseHandle(hProcess
);
211 if (res
!= ERROR_SUCCESS
)
218 GuiConsoleOpenUserSettings(HWND hWnd
, DWORD ProcessId
, PHKEY hSubKey
, REGSAM samDesired
)
220 WCHAR szProcessName
[MAX_PATH
];
221 WCHAR szBuffer
[MAX_PATH
];
222 UINT fLength
, wLength
;
223 DWORD dwBitmask
, dwLength
;
224 WCHAR CurDrive
[] = { 'A',':', 0 };
228 static const WCHAR szSystemRoot
[] = { '%','S','y','s','t','e','m','R','o','o','t','%', 0 };
232 * console properties are stored under
235 * There are 3 ways to store console properties
237 * 1. use console title as subkey name
240 * 2. use application name as subkey name
242 * 3. use unexpanded path to console application.
243 * i.e. %SystemRoot%_system32_cmd.exe
246 if (!GuiConsoleOpenUserRegistryPathPerProcessId(ProcessId
, &hProcess
, &hKey
, samDesired
))
249 fLength
= GetProcessImageFileNameW(hProcess
, szProcessName
, MAX_PATH
);
250 CloseHandle(hProcess
);
254 DPRINT1("GetProcessImageFileNameW failed(0x%x)ProcessId %d\n", GetLastError(),hProcess
);
259 ptr
= wcsrchr(szProcessName
, L
'\\');
260 swprintf(szBuffer
, L
"Console%s",ptr
);
262 if (RegOpenKeyExW(hKey
, szBuffer
, 0, samDesired
, hSubKey
) == ERROR_SUCCESS
)
268 dwBitmask
= GetLogicalDrives();
273 dwLength
= QueryDosDeviceW(CurDrive
, szBuffer
, MAX_PATH
);
276 if (!memcmp(szBuffer
, szProcessName
, (dwLength
-2)*sizeof(WCHAR
)))
278 wcscpy(szBuffer
, CurDrive
);
279 wcscat(&szBuffer
[(sizeof(CurDrive
)/sizeof(WCHAR
))-1], &szProcessName
[dwLength
-2]);
284 dwBitmask
= (dwBitmask
>> 1);
288 wLength
= GetWindowsDirectoryW(szProcessName
, MAX_PATH
);
290 if (!wcsncmp(szProcessName
, szBuffer
, wLength
))
292 wcscpy(szProcessName
, szSystemRoot
);
293 wcscpy(&szProcessName
[(sizeof(szSystemRoot
) / sizeof(WCHAR
))-1], &szBuffer
[wLength
]);
294 ptr
= res
= szProcessName
;
298 ptr
= res
= szBuffer
;
301 while((ptr
= wcschr(szProcessName
, L
'\\')))
304 if (RegOpenKeyExW(hKey
, res
, 0, samDesired
, hSubKey
) == ERROR_SUCCESS
)
313 GuiConsoleReadUserSettings(HKEY hKey
, PCSRSS_CONSOLE Console
, PGUI_CONSOLE_DATA GuiData
, PCSRSS_SCREEN_BUFFER Buffer
)
315 DWORD dwNumSubKeys
= 0;
320 WCHAR szValueName
[MAX_PATH
];
321 WCHAR szValue
[MAX_PATH
];
324 RegQueryInfoKey(hKey
, NULL
, NULL
, NULL
, &dwNumSubKeys
, NULL
, NULL
, NULL
, NULL
, NULL
, NULL
, NULL
);
326 for (dwIndex
= 0; dwIndex
< dwNumSubKeys
; dwIndex
++)
328 dwValue
= sizeof(Value
);
329 dwValueName
= MAX_PATH
;
331 if (RegEnumValueW(hKey
, dwIndex
, szValueName
, &dwValueName
, NULL
, &dwType
, (BYTE
*)&Value
, &dwValue
) != ERROR_SUCCESS
)
333 if (dwType
== REG_SZ
)
336 * retry in case of string value
338 dwValue
= sizeof(szValue
);
339 dwValueName
= MAX_PATH
;
340 if (RegEnumValueW(hKey
, dwIndex
, szValueName
, &dwValueName
, NULL
, NULL
, (BYTE
*)szValue
, &dwValue
) != ERROR_SUCCESS
)
347 if (!wcscmp(szValueName
, L
"CursorSize"))
350 GuiData
->CursorSize
= Value
;
351 else if (Value
== 0x64)
352 GuiData
->CursorSize
= Value
;
354 else if (!wcscmp(szValueName
, L
"FaceName"))
356 wcscpy(GuiData
->FontName
, szValue
);
358 else if (!wcscmp(szValueName
, L
"FontSize"))
360 GuiData
->FontSize
= Value
;
362 else if (!wcscmp(szValueName
, L
"FontWeight"))
364 GuiData
->FontWeight
= Value
;
366 else if (!wcscmp(szValueName
, L
"HistoryNoDup"))
368 GuiData
->HistoryNoDup
= Value
;
370 else if (!wcscmp(szValueName
, L
"WindowSize"))
372 Console
->Size
.X
= LOWORD(Value
);
373 Console
->Size
.Y
= HIWORD(Value
);
375 else if (!wcscmp(szValueName
, L
"ScreenBufferSize"))
379 Buffer
->MaxX
= LOWORD(Value
);
380 Buffer
->MaxY
= HIWORD(Value
);
383 else if (!wcscmp(szValueName
, L
"FullScreen"))
385 GuiData
->FullScreen
= Value
;
387 else if (!wcscmp(szValueName
, L
"QuickEdit"))
389 GuiData
->QuickEdit
= Value
;
391 else if (!wcscmp(szValueName
, L
"InsertMode"))
393 GuiData
->InsertMode
= Value
;
398 GuiConsoleUseDefaults(PCSRSS_CONSOLE Console
, PGUI_CONSOLE_DATA GuiData
, PCSRSS_SCREEN_BUFFER Buffer
)
401 * init guidata with default properties
404 wcscpy(GuiData
->FontName
, L
"Bitstream Vera Sans Mono");
405 GuiData
->FontSize
= 0x0008000C; // font is 8x12
406 GuiData
->FontWeight
= FW_NORMAL
;
407 GuiData
->CursorSize
= 0;
408 GuiData
->HistoryNoDup
= FALSE
;
409 GuiData
->FullScreen
= FALSE
;
410 GuiData
->QuickEdit
= FALSE
;
411 GuiData
->InsertMode
= TRUE
;
413 Console
->Size
.X
= 80;
414 Console
->Size
.Y
= 25;
426 GuiConsoleHandleNcCreate(HWND hWnd
, CREATESTRUCTW
*Create
)
429 PCSRSS_CONSOLE Console
= (PCSRSS_CONSOLE
) Create
->lpCreateParams
;
430 PGUI_CONSOLE_DATA GuiData
= (PGUI_CONSOLE_DATA
)Console
->PrivateData
;
434 PCSRSS_PROCESS_DATA ProcessData
;
437 Console
->hWindow
= hWnd
;
441 DPRINT1("GuiConsoleNcCreate: HeapAlloc failed\n");
445 GuiConsoleUseDefaults(Console
, GuiData
, Console
->ActiveBuffer
);
446 if (Console
->ProcessList
.Flink
!= &Console
->ProcessList
)
448 ProcessData
= CONTAINING_RECORD(Console
->ProcessList
.Flink
, CSRSS_PROCESS_DATA
, ProcessEntry
);
449 if (GuiConsoleOpenUserSettings(hWnd
, PtrToUlong(ProcessData
->ProcessId
), &hKey
, KEY_READ
))
451 GuiConsoleReadUserSettings(hKey
, Console
, GuiData
, Console
->ActiveBuffer
);
456 InitializeCriticalSection(&GuiData
->Lock
);
458 GuiData
->LineBuffer
= (PWCHAR
)HeapAlloc(Win32CsrApiHeap
, HEAP_ZERO_MEMORY
,
459 Console
->Size
.X
* sizeof(WCHAR
));
461 GuiData
->Font
= CreateFontW(LOWORD(GuiData
->FontSize
),
462 0, //HIWORD(GuiData->FontSize),
470 OUT_DEFAULT_PRECIS
, CLIP_DEFAULT_PRECIS
,
471 NONANTIALIASED_QUALITY
, FIXED_PITCH
| FF_DONTCARE
,
473 if (NULL
== GuiData
->Font
)
475 DPRINT1("GuiConsoleNcCreate: CreateFont failed\n");
476 DeleteCriticalSection(&GuiData
->Lock
);
477 HeapFree(Win32CsrApiHeap
, 0, GuiData
);
483 DPRINT1("GuiConsoleNcCreate: GetDC failed\n");
484 DeleteObject(GuiData
->Font
);
485 DeleteCriticalSection(&GuiData
->Lock
);
486 HeapFree(Win32CsrApiHeap
, 0, GuiData
);
489 OldFont
= SelectObject(Dc
, GuiData
->Font
);
492 DPRINT1("GuiConsoleNcCreate: SelectObject failed\n");
494 DeleteObject(GuiData
->Font
);
495 DeleteCriticalSection(&GuiData
->Lock
);
496 HeapFree(Win32CsrApiHeap
, 0, GuiData
);
499 if (! GetTextMetricsW(Dc
, &Metrics
))
501 DPRINT1("GuiConsoleNcCreate: GetTextMetrics failed\n");
502 SelectObject(Dc
, OldFont
);
504 DeleteObject(GuiData
->Font
);
505 DeleteCriticalSection(&GuiData
->Lock
);
506 HeapFree(Win32CsrApiHeap
, 0, GuiData
);
509 GuiData
->CharWidth
= Metrics
.tmMaxCharWidth
;
510 GuiData
->CharHeight
= Metrics
.tmHeight
+ Metrics
.tmExternalLeading
;
511 SelectObject(Dc
, OldFont
);
514 GuiData
->CursorBlinkOn
= TRUE
;
515 GuiData
->ForceCursorOff
= FALSE
;
517 GuiData
->Selection
.left
= -1;
518 DPRINT("Console %p GuiData %p\n", Console
, GuiData
);
519 Console
->PrivateData
= GuiData
;
520 SetWindowLongPtrW(hWnd
, GWL_USERDATA
, (DWORD_PTR
) Console
);
522 GetWindowRect(hWnd
, &Rect
);
523 Rect
.right
= Rect
.left
+ Console
->Size
.X
* GuiData
->CharWidth
+
524 2 * GetSystemMetrics(SM_CXFIXEDFRAME
);
525 Rect
.bottom
= Rect
.top
+ Console
->Size
.Y
* GuiData
->CharHeight
+
526 2 * GetSystemMetrics(SM_CYFIXEDFRAME
) + GetSystemMetrics(SM_CYCAPTION
);
527 MoveWindow(hWnd
, Rect
.left
, Rect
.top
, Rect
.right
- Rect
.left
,
528 Rect
.bottom
- Rect
.top
, FALSE
);
530 SetTimer(hWnd
, 1, CURSOR_BLINK_TIME
, NULL
);
531 SetEvent(GuiData
->hGuiInitEvent
);
533 GuiConsoleCreateSysMenu(Console
);
535 return (BOOL
) DefWindowProcW(hWnd
, WM_NCCREATE
, 0, (LPARAM
) Create
);
538 static COLORREF FASTCALL
539 GuiConsoleRGBFromAttribute(BYTE Attribute
)
541 int Red
= (Attribute
& 0x04 ? (Attribute
& 0x08 ? 0xff : 0x80) : 0x00);
542 int Green
= (Attribute
& 0x02 ? (Attribute
& 0x08 ? 0xff : 0x80) : 0x00);
543 int Blue
= (Attribute
& 0x01 ? (Attribute
& 0x08 ? 0xff : 0x80) : 0x00);
545 return RGB(Red
, Green
, Blue
);
549 GuiConsoleSetTextColors(HDC Dc
, BYTE Attribute
)
551 SetTextColor(Dc
, GuiConsoleRGBFromAttribute(Attribute
& 0x0f));
552 SetBkColor(Dc
, GuiConsoleRGBFromAttribute((Attribute
& 0xf0) >> 4));
556 GuiConsoleGetLogicalCursorPos(PCSRSS_SCREEN_BUFFER Buff
, ULONG
*CursorX
, ULONG
*CursorY
)
558 *CursorX
= Buff
->CurrentX
;
559 if (Buff
->CurrentY
< Buff
->ShowY
)
561 *CursorY
= Buff
->MaxY
- Buff
->ShowY
+ Buff
->CurrentY
;
565 *CursorY
= Buff
->CurrentY
- Buff
->ShowY
;
571 GuiConsoleUpdateSelection(HWND hWnd
, PRECT rc
, PGUI_CONSOLE_DATA GuiData
)
573 RECT oldRect
= GuiData
->Selection
;
577 RECT changeRect
= *rc
;
579 GuiData
->Selection
= *rc
;
581 changeRect
.left
*= GuiData
->CharWidth
;
582 changeRect
.top
*= GuiData
->CharHeight
;
583 changeRect
.right
*= GuiData
->CharWidth
;
584 changeRect
.bottom
*= GuiData
->CharHeight
;
586 if(rc
->left
!= oldRect
.left
||
587 rc
->top
!= oldRect
.top
||
588 rc
->right
!= oldRect
.right
||
589 rc
->bottom
!= oldRect
.bottom
)
591 if(oldRect
.left
!= -1)
595 oldRect
.left
*= GuiData
->CharWidth
;
596 oldRect
.top
*= GuiData
->CharHeight
;
597 oldRect
.right
*= GuiData
->CharWidth
;
598 oldRect
.bottom
*= GuiData
->CharHeight
;
600 /* calculate the region that needs to be updated */
601 if((rgn1
= CreateRectRgnIndirect(&oldRect
)))
603 if((rgn2
= CreateRectRgnIndirect(&changeRect
)))
605 if(CombineRgn(rgn1
, rgn2
, rgn1
, RGN_XOR
) != ERROR
)
607 InvalidateRgn(hWnd
, rgn1
, FALSE
);
617 InvalidateRect(hWnd
, &changeRect
, FALSE
);
621 else if(oldRect
.left
!= -1)
623 /* clear the selection */
624 GuiData
->Selection
.left
= -1;
625 oldRect
.left
*= GuiData
->CharWidth
;
626 oldRect
.top
*= GuiData
->CharHeight
;
627 oldRect
.right
*= GuiData
->CharWidth
;
628 oldRect
.bottom
*= GuiData
->CharHeight
;
629 InvalidateRect(hWnd
, &oldRect
, FALSE
);
635 GuiConsolePaint(PCSRSS_CONSOLE Console
,
636 PGUI_CONSOLE_DATA GuiData
,
640 PCSRSS_SCREEN_BUFFER Buff
;
641 ULONG TopLine
, BottomLine
, LeftChar
, RightChar
;
642 ULONG Line
, Char
, Start
;
645 BYTE LastAttribute
, Attribute
;
646 ULONG CursorX
, CursorY
, CursorHeight
;
647 HBRUSH CursorBrush
, OldBrush
;
650 Buff
= Console
->ActiveBuffer
;
652 TopLine
= rc
->top
/ GuiData
->CharHeight
;
653 BottomLine
= (rc
->bottom
+ (GuiData
->CharHeight
- 1)) / GuiData
->CharHeight
- 1;
654 LeftChar
= rc
->left
/ GuiData
->CharWidth
;
655 RightChar
= (rc
->right
+ (GuiData
->CharWidth
- 1)) / GuiData
->CharWidth
- 1;
656 LastAttribute
= Buff
->Buffer
[(TopLine
* Buff
->MaxX
+ LeftChar
) * 2 + 1];
658 GuiConsoleSetTextColors(hDC
,
661 EnterCriticalSection(&Buff
->Header
.Lock
);
663 OldFont
= SelectObject(hDC
,
666 for (Line
= TopLine
; Line
<= BottomLine
; Line
++)
668 if (Line
+ Buff
->ShowY
< Buff
->MaxY
)
670 From
= Buff
->Buffer
+ ((Line
+ Buff
->ShowY
) * Buff
->MaxX
+ LeftChar
) * 2;
674 From
= Buff
->Buffer
+
675 ((Line
- (Buff
->MaxY
- Buff
->ShowY
)) * Buff
->MaxX
+ LeftChar
) * 2;
678 To
= GuiData
->LineBuffer
;
680 for (Char
= LeftChar
; Char
<= RightChar
; Char
++)
682 if (*(From
+ 1) != LastAttribute
)
685 Start
* GuiData
->CharWidth
,
686 Line
* GuiData
->CharHeight
,
690 To
= GuiData
->LineBuffer
;
691 Attribute
= *(From
+ 1);
692 if (Attribute
!= LastAttribute
)
694 GuiConsoleSetTextColors(hDC
,
696 LastAttribute
= Attribute
;
700 MultiByteToWideChar(Console
->OutputCodePage
,
711 Start
* GuiData
->CharWidth
,
712 Line
* GuiData
->CharHeight
,
714 RightChar
- Start
+ 1);
717 if (Buff
->CursorInfo
.bVisible
&& GuiData
->CursorBlinkOn
&&
718 !GuiData
->ForceCursorOff
)
720 GuiConsoleGetLogicalCursorPos(Buff
,
723 if (LeftChar
<= CursorX
&& CursorX
<= RightChar
&&
724 TopLine
<= CursorY
&& CursorY
<= BottomLine
)
726 CursorHeight
= (GuiData
->CharHeight
* Buff
->CursorInfo
.dwSize
) / 100;
727 if (CursorHeight
< 1)
731 From
= Buff
->Buffer
+ (Buff
->CurrentY
* Buff
->MaxX
+ Buff
->CurrentX
) * 2 + 1;
732 CursorBrush
= CreateSolidBrush(GuiConsoleRGBFromAttribute(*From
));
733 OldBrush
= SelectObject(hDC
,
736 CursorX
* GuiData
->CharWidth
,
737 CursorY
* GuiData
->CharHeight
+ (GuiData
->CharHeight
- CursorHeight
),
743 DeleteObject(CursorBrush
);
747 LeaveCriticalSection(&Buff
->Header
.Lock
);
754 GuiConsoleHandlePaint(HWND hWnd
, HDC hDCPaint
)
758 PCSRSS_CONSOLE Console
;
759 PGUI_CONSOLE_DATA GuiData
;
761 hDC
= BeginPaint(hWnd
, &ps
);
763 ps
.rcPaint
.left
< ps
.rcPaint
.right
&&
764 ps
.rcPaint
.top
< ps
.rcPaint
.bottom
)
766 GuiConsoleGetDataPointers(hWnd
,
769 if (Console
!= NULL
&& GuiData
!= NULL
&&
770 Console
->ActiveBuffer
!= NULL
)
772 if (Console
->ActiveBuffer
->Buffer
!= NULL
)
774 EnterCriticalSection(&GuiData
->Lock
);
776 GuiConsolePaint(Console
,
781 if (GuiData
->Selection
.left
!= -1)
783 RECT rc
= GuiData
->Selection
;
785 rc
.left
*= GuiData
->CharWidth
;
786 rc
.top
*= GuiData
->CharHeight
;
787 rc
.right
*= GuiData
->CharWidth
;
788 rc
.bottom
*= GuiData
->CharHeight
;
790 /* invert the selection */
791 if (IntersectRect(&rc
,
804 LeaveCriticalSection(&GuiData
->Lock
);
813 GuiConsoleHandleKey(HWND hWnd
, UINT msg
, WPARAM wParam
, LPARAM lParam
)
815 PCSRSS_CONSOLE Console
;
816 PGUI_CONSOLE_DATA GuiData
;
819 GuiConsoleGetDataPointers(hWnd
, &Console
, &GuiData
);
821 Message
.message
= msg
;
822 Message
.wParam
= wParam
;
823 Message
.lParam
= lParam
;
825 if(msg
== WM_CHAR
|| msg
== WM_SYSKEYDOWN
)
827 /* clear the selection */
828 GuiConsoleUpdateSelection(hWnd
, NULL
, GuiData
);
831 ConioProcessKey(&Message
, Console
, FALSE
);
835 GuiIntDrawRegion(PGUI_CONSOLE_DATA GuiData
, HWND Wnd
, RECT
*Region
)
839 RegionRect
.left
= Region
->left
* GuiData
->CharWidth
;
840 RegionRect
.top
= Region
->top
* GuiData
->CharHeight
;
841 RegionRect
.right
= (Region
->right
+ 1) * GuiData
->CharWidth
;
842 RegionRect
.bottom
= (Region
->bottom
+ 1) * GuiData
->CharHeight
;
844 InvalidateRect(Wnd
, &RegionRect
, FALSE
);
848 GuiDrawRegion(PCSRSS_CONSOLE Console
, RECT
*Region
)
850 PGUI_CONSOLE_DATA GuiData
= (PGUI_CONSOLE_DATA
) Console
->PrivateData
;
852 if (NULL
!= Console
->hWindow
&& NULL
!= GuiData
)
854 GuiIntDrawRegion(GuiData
, Console
->hWindow
, Region
);
859 GuiInvalidateCell(PGUI_CONSOLE_DATA GuiData
, HWND Wnd
, UINT x
, UINT y
)
868 GuiIntDrawRegion(GuiData
, Wnd
, &CellRect
);
872 GuiWriteStream(PCSRSS_CONSOLE Console
, RECT
*Region
, LONG CursorStartX
, LONG CursorStartY
,
873 UINT ScrolledLines
, CHAR
*Buffer
, UINT Length
)
875 PGUI_CONSOLE_DATA GuiData
= (PGUI_CONSOLE_DATA
) Console
->PrivateData
;
876 PCSRSS_SCREEN_BUFFER Buff
= Console
->ActiveBuffer
;
877 LONG CursorEndX
, CursorEndY
;
880 if (NULL
== Console
->hWindow
|| NULL
== GuiData
)
885 if (0 != ScrolledLines
)
889 ScrollRect
.right
= Console
->Size
.X
* GuiData
->CharWidth
;
890 ScrollRect
.bottom
= Region
->top
* GuiData
->CharHeight
;
892 if (GuiData
->Selection
.left
!= -1)
894 /* scroll the selection */
895 if (GuiData
->Selection
.top
> ScrolledLines
)
897 GuiData
->Selection
.top
-= ScrolledLines
;
898 GuiData
->Selection
.bottom
-= ScrolledLines
;
900 else if (GuiData
->Selection
.bottom
< ScrolledLines
)
902 GuiData
->Selection
.left
= -1;
906 GuiData
->Selection
.top
= 0;
907 GuiData
->Selection
.bottom
-= ScrolledLines
;
911 ScrollWindowEx(Console
->hWindow
,
913 -(ScrolledLines
* GuiData
->CharHeight
),
921 GuiIntDrawRegion(GuiData
, Console
->hWindow
, Region
);
923 if (CursorStartX
< Region
->left
|| Region
->right
< CursorStartX
924 || CursorStartY
< Region
->top
|| Region
->bottom
< CursorStartY
)
926 GuiInvalidateCell(GuiData
, Console
->hWindow
, CursorStartX
, CursorStartY
);
929 ConioPhysicalToLogical(Buff
, Buff
->CurrentX
, Buff
->CurrentY
,
930 &CursorEndX
, &CursorEndY
);
931 if ((CursorEndX
< Region
->left
|| Region
->right
< CursorEndX
932 || CursorEndY
< Region
->top
|| Region
->bottom
< CursorEndY
)
933 && (CursorEndX
!= CursorStartX
|| CursorEndY
!= CursorStartY
))
935 GuiInvalidateCell(GuiData
, Console
->hWindow
, CursorEndX
, CursorEndY
);
940 GuiSetCursorInfo(PCSRSS_CONSOLE Console
, PCSRSS_SCREEN_BUFFER Buff
)
944 if (Console
->ActiveBuffer
== Buff
)
946 ConioPhysicalToLogical(Buff
, Buff
->CurrentX
, Buff
->CurrentY
,
947 &UpdateRect
.left
, &UpdateRect
.top
);
948 UpdateRect
.right
= UpdateRect
.left
;
949 UpdateRect
.bottom
= UpdateRect
.top
;
950 ConioDrawRegion(Console
, &UpdateRect
);
957 GuiSetScreenInfo(PCSRSS_CONSOLE Console
, PCSRSS_SCREEN_BUFFER Buff
, UINT OldCursorX
, UINT OldCursorY
)
961 if (Console
->ActiveBuffer
== Buff
)
963 /* Redraw char at old position (removes cursor) */
964 UpdateRect
.left
= OldCursorX
;
965 UpdateRect
.top
= OldCursorY
;
966 UpdateRect
.right
= OldCursorX
;
967 UpdateRect
.bottom
= OldCursorY
;
968 ConioDrawRegion(Console
, &UpdateRect
);
969 /* Redraw char at new position (shows cursor) */
970 ConioPhysicalToLogical(Buff
, Buff
->CurrentX
, Buff
->CurrentY
,
971 &(UpdateRect
.left
), &(UpdateRect
.top
));
972 UpdateRect
.right
= UpdateRect
.left
;
973 UpdateRect
.bottom
= UpdateRect
.top
;
974 ConioDrawRegion(Console
, &UpdateRect
);
981 GuiConsoleHandleTimer(HWND hWnd
)
983 PCSRSS_CONSOLE Console
;
984 PGUI_CONSOLE_DATA GuiData
;
986 ULONG CursorX
, CursorY
;
988 GuiConsoleGetDataPointers(hWnd
, &Console
, &GuiData
);
989 GuiData
->CursorBlinkOn
= ! GuiData
->CursorBlinkOn
;
991 GuiConsoleGetLogicalCursorPos(Console
->ActiveBuffer
, &CursorX
, &CursorY
);
992 CursorRect
.left
= CursorX
;
993 CursorRect
.top
= CursorY
;
994 CursorRect
.right
= CursorX
;
995 CursorRect
.bottom
= CursorY
;
996 GuiDrawRegion(Console
, &CursorRect
);
1000 GuiConsoleHandleClose(HWND hWnd
)
1002 PCSRSS_CONSOLE Console
;
1003 PGUI_CONSOLE_DATA GuiData
;
1004 PLIST_ENTRY current_entry
;
1005 PCSRSS_PROCESS_DATA current
;
1007 GuiConsoleGetDataPointers(hWnd
, &Console
, &GuiData
);
1009 EnterCriticalSection(&Console
->Header
.Lock
);
1011 current_entry
= Console
->ProcessList
.Flink
;
1012 while (current_entry
!= &Console
->ProcessList
)
1014 current
= CONTAINING_RECORD(current_entry
, CSRSS_PROCESS_DATA
, ProcessEntry
);
1015 current_entry
= current_entry
->Flink
;
1017 ConioConsoleCtrlEvent(CTRL_CLOSE_EVENT
, current
);
1020 LeaveCriticalSection(&Console
->Header
.Lock
);
1023 static VOID FASTCALL
1024 GuiConsoleHandleNcDestroy(HWND hWnd
)
1026 PCSRSS_CONSOLE Console
;
1027 PGUI_CONSOLE_DATA GuiData
;
1029 GuiConsoleGetDataPointers(hWnd
, &Console
, &GuiData
);
1031 Console
->PrivateData
= NULL
;
1032 DeleteCriticalSection(&GuiData
->Lock
);
1033 GetSystemMenu(hWnd
, TRUE
);
1034 if (GuiData
->ConsoleLibrary
)
1035 FreeLibrary(GuiData
->ConsoleLibrary
);
1037 HeapFree(Win32CsrApiHeap
, 0, GuiData
);
1040 static VOID FASTCALL
1041 GuiConsoleLeftMouseDown(HWND hWnd
, LPARAM lParam
)
1043 PCSRSS_CONSOLE Console
;
1044 PGUI_CONSOLE_DATA GuiData
;
1048 GuiConsoleGetDataPointers(hWnd
, &Console
, &GuiData
);
1049 if (Console
== NULL
|| GuiData
== NULL
) return;
1051 pt
= MAKEPOINTS(lParam
);
1053 rc
.left
= pt
.x
/ GuiData
->CharWidth
;
1054 rc
.top
= pt
.y
/ GuiData
->CharHeight
;
1055 rc
.right
= rc
.left
+ 1;
1056 rc
.bottom
= rc
.top
+ 1;
1058 GuiData
->SelectionStart
.x
= rc
.left
;
1059 GuiData
->SelectionStart
.y
= rc
.top
;
1063 GuiData
->MouseDown
= TRUE
;
1065 GuiConsoleUpdateSelection(hWnd
, &rc
, GuiData
);
1068 static VOID FASTCALL
1069 GuiConsoleLeftMouseUp(HWND hWnd
, LPARAM lParam
)
1071 PCSRSS_CONSOLE Console
;
1072 PGUI_CONSOLE_DATA GuiData
;
1076 GuiConsoleGetDataPointers(hWnd
, &Console
, &GuiData
);
1077 if (Console
== NULL
|| GuiData
== NULL
) return;
1078 if (GuiData
->Selection
.left
== -1 || !GuiData
->MouseDown
) return;
1080 pt
= MAKEPOINTS(lParam
);
1082 rc
.left
= GuiData
->SelectionStart
.x
;
1083 rc
.top
= GuiData
->SelectionStart
.y
;
1084 rc
.right
= (pt
.x
>= 0 ? (pt
.x
/ GuiData
->CharWidth
) + 1 : 0);
1085 rc
.bottom
= (pt
.y
>= 0 ? (pt
.y
/ GuiData
->CharHeight
) + 1 : 0);
1087 /* exchange left/top with right/bottom if required */
1088 if(rc
.left
>= rc
.right
)
1092 rc
.left
= max(rc
.right
- 1, 0);
1095 if(rc
.top
>= rc
.bottom
)
1099 rc
.top
= max(rc
.bottom
- 1, 0);
1100 rc
.bottom
= tmp
+ 1;
1103 GuiData
->MouseDown
= FALSE
;
1105 GuiConsoleUpdateSelection(hWnd
, &rc
, GuiData
);
1110 static VOID FASTCALL
1111 GuiConsoleMouseMove(HWND hWnd
, WPARAM wParam
, LPARAM lParam
)
1113 PCSRSS_CONSOLE Console
;
1114 PGUI_CONSOLE_DATA GuiData
;
1118 if (!(wParam
& MK_LBUTTON
)) return;
1120 GuiConsoleGetDataPointers(hWnd
, &Console
, &GuiData
);
1121 if (Console
== NULL
|| GuiData
== NULL
|| !GuiData
->MouseDown
) return;
1123 pt
= MAKEPOINTS(lParam
);
1125 rc
.left
= GuiData
->SelectionStart
.x
;
1126 rc
.top
= GuiData
->SelectionStart
.y
;
1127 rc
.right
= (pt
.x
>= 0 ? (pt
.x
/ GuiData
->CharWidth
) + 1 : 0);
1128 if (Console
->Size
.X
< rc
.right
)
1130 rc
.right
= Console
->Size
.X
;
1132 rc
.bottom
= (pt
.y
>= 0 ? (pt
.y
/ GuiData
->CharHeight
) + 1 : 0);
1133 if (Console
->Size
.Y
< rc
.bottom
)
1135 rc
.bottom
= Console
->Size
.Y
;
1138 /* exchange left/top with right/bottom if required */
1139 if(rc
.left
>= rc
.right
)
1143 rc
.left
= max(rc
.right
- 1, 0);
1146 if(rc
.top
>= rc
.bottom
)
1150 rc
.top
= max(rc
.bottom
- 1, 0);
1151 rc
.bottom
= tmp
+ 1;
1154 GuiConsoleUpdateSelection(hWnd
, &rc
, GuiData
);
1157 static VOID FASTCALL
1158 GuiConsoleRightMouseDown(HWND hWnd
)
1160 PCSRSS_CONSOLE Console
;
1161 PGUI_CONSOLE_DATA GuiData
;
1163 GuiConsoleGetDataPointers(hWnd
, &Console
, &GuiData
);
1164 if (Console
== NULL
|| GuiData
== NULL
) return;
1166 if (GuiData
->Selection
.left
== -1)
1168 /* FIXME - paste text from clipboard */
1172 /* FIXME - copy selection to clipboard */
1174 GuiConsoleUpdateSelection(hWnd
, NULL
, GuiData
);
1180 GuiConsoleShowConsoleProperties(HWND hWnd
, BOOL Defaults
)
1182 PCSRSS_CONSOLE Console
;
1183 PGUI_CONSOLE_DATA GuiData
;
1184 APPLET_PROC CPLFunc
;
1185 TCHAR szBuffer
[MAX_PATH
];
1187 GuiConsoleGetDataPointers(hWnd
, &Console
, &GuiData
);
1189 if (GuiData
== NULL
)
1191 DPRINT1("GuiConsoleGetDataPointers failed\n");
1194 if (GuiData
->ConsoleLibrary
== NULL
)
1196 GetWindowsDirectory(szBuffer
,MAX_PATH
);
1197 _tcscat(szBuffer
, _T("\\system32\\console.dll"));
1198 GuiData
->ConsoleLibrary
= LoadLibrary(szBuffer
);
1200 if (GuiData
->ConsoleLibrary
== NULL
)
1202 DPRINT1("failed to load console.dll");
1207 CPLFunc
= (APPLET_PROC
) GetProcAddress(GuiData
->ConsoleLibrary
, _T("CPlApplet"));
1210 DPRINT("Error: Console.dll misses CPlApplet export\n");
1214 if (!CPLFunc(hWnd
, CPL_INIT
, 0, 0))
1216 DPRINT("Error: failed to initialize console.dll\n");
1220 if (CPLFunc(hWnd
, CPL_GETCOUNT
, 0, 0) != 1)
1222 DPRINT("Error: console.dll returned unexpected CPL count\n");
1226 CPLFunc(hWnd
, CPL_DBLCLK
, 0, Defaults
);
1230 // read back the changes from console.dll
1232 // if the changes are system-wide then
1233 // console.dll should have written it to
1236 // if the changes only apply to this session
1237 // then exchange this info with console.dll in
1240 static BOOL FASTCALL
1241 GuiConsoleHandleSysMenuCommand(HWND hWnd
, WPARAM wParam
)
1247 case ID_SYSTEM_EDIT_MARK
:
1248 case ID_SYSTEM_EDIT_COPY
:
1249 case ID_SYSTEM_EDIT_PASTE
:
1250 case ID_SYSTEM_EDIT_SELECTALL
:
1251 case ID_SYSTEM_EDIT_SCROLL
:
1252 case ID_SYSTEM_EDIT_FIND
:
1255 case ID_SYSTEM_DEFAULTS
:
1256 GuiConsoleShowConsoleProperties(hWnd
, TRUE
);
1259 case ID_SYSTEM_PROPERTIES
:
1260 GuiConsoleShowConsoleProperties(hWnd
, FALSE
);
1271 static LRESULT CALLBACK
1272 GuiConsoleWndProc(HWND hWnd
, UINT msg
, WPARAM wParam
, LPARAM lParam
)
1279 Result
= (LRESULT
) GuiConsoleHandleNcCreate(hWnd
, (CREATESTRUCTW
*) lParam
);
1282 GuiConsoleHandlePaint(hWnd
, (HDC
)wParam
);
1289 GuiConsoleHandleKey(hWnd
, msg
, wParam
, lParam
);
1292 GuiConsoleHandleTimer(hWnd
);
1295 GuiConsoleHandleClose(hWnd
);
1298 GuiConsoleHandleNcDestroy(hWnd
);
1300 case WM_LBUTTONDOWN
:
1301 GuiConsoleLeftMouseDown(hWnd
, lParam
);
1304 GuiConsoleLeftMouseUp(hWnd
, lParam
);
1306 case WM_RBUTTONDOWN
:
1307 GuiConsoleRightMouseDown(hWnd
);
1310 GuiConsoleMouseMove(hWnd
, wParam
, lParam
);
1313 if (!GuiConsoleHandleSysMenuCommand(hWnd
, wParam
))
1314 Result
= DefWindowProcW(hWnd
, msg
, wParam
, lParam
);
1317 Result
= DefWindowProcW(hWnd
, msg
, wParam
, lParam
);
1324 static LRESULT CALLBACK
1325 GuiConsoleNotifyWndProc(HWND hWnd
, UINT msg
, WPARAM wParam
, LPARAM lParam
)
1330 PWCHAR Buffer
, Title
;
1331 PCSRSS_CONSOLE Console
= (PCSRSS_CONSOLE
) lParam
;
1338 SetWindowLongW(hWnd
, GWL_USERDATA
, 0);
1340 case PM_CREATE_CONSOLE
:
1341 Buffer
= HeapAlloc(Win32CsrApiHeap
, 0,
1342 Console
->Title
.Length
+ sizeof(WCHAR
));
1345 memcpy(Buffer
, Console
->Title
.Buffer
, Console
->Title
.Length
);
1346 Buffer
[Console
->Title
.Length
/ sizeof(WCHAR
)] = L
'\0';
1353 NewWindow
= CreateWindowW(L
"ConsoleWindowClass",
1355 WS_OVERLAPPED
| WS_CAPTION
| WS_SYSMENU
| WS_MINIMIZEBOX
, // | WS_HSCROLL | WS_VSCROLL,
1362 (HINSTANCE
) GetModuleHandleW(NULL
),
1366 HeapFree(Win32CsrApiHeap
, 0, Buffer
);
1368 if (NULL
!= NewWindow
)
1370 //ShowScrollBar(NewWindow, SB_VERT, FALSE);
1371 //ShowScrollBar(NewWindow, SB_HORZ, FALSE);
1372 SetWindowLongW(hWnd
, GWL_USERDATA
, GetWindowLongW(hWnd
, GWL_USERDATA
) + 1);
1373 ShowWindow(NewWindow
, SW_SHOW
);
1375 return (LRESULT
) NewWindow
;
1376 case PM_DESTROY_CONSOLE
:
1377 /* Window creation is done using a PostMessage(), so it's possible that the
1378 * window that we want to destroy doesn't exist yet. So first empty the message
1380 while(PeekMessageW(&Msg
, NULL
, 0, 0, PM_REMOVE
))
1382 TranslateMessage(&Msg
);
1383 DispatchMessageW(&Msg
);
1385 DestroyWindow(Console
->hWindow
);
1386 Console
->hWindow
= NULL
;
1387 WindowCount
= GetWindowLongW(hWnd
, GWL_USERDATA
);
1389 SetWindowLongW(hWnd
, GWL_USERDATA
, WindowCount
);
1390 if (0 == WindowCount
)
1393 DestroyWindow(hWnd
);
1394 PrivateCsrssManualGuiCheck(-1);
1399 return DefWindowProcW(hWnd
, msg
, wParam
, lParam
);
1403 static DWORD STDCALL
1404 GuiConsoleGuiThread(PVOID Data
)
1407 PHANDLE GraphicsStartupEvent
= (PHANDLE
) Data
;
1409 NotifyWnd
= CreateWindowW(L
"Win32CsrCreateNotify",
1411 WS_OVERLAPPEDWINDOW
,
1418 (HINSTANCE
) GetModuleHandleW(NULL
),
1420 if (NULL
== NotifyWnd
)
1422 PrivateCsrssManualGuiCheck(-1);
1423 SetEvent(*GraphicsStartupEvent
);
1427 SetEvent(*GraphicsStartupEvent
);
1429 while(GetMessageW(&msg
, NULL
, 0, 0))
1431 TranslateMessage(&msg
);
1432 DispatchMessageW(&msg
);
1438 static BOOL FASTCALL
1443 if (NULL
== NotifyWnd
)
1445 PrivateCsrssManualGuiCheck(+1);
1448 wc
.cbSize
= sizeof(WNDCLASSEXW
);
1449 wc
.lpszClassName
= L
"Win32CsrCreateNotify";
1450 wc
.lpfnWndProc
= GuiConsoleNotifyWndProc
;
1452 wc
.hInstance
= (HINSTANCE
) GetModuleHandleW(NULL
);
1455 wc
.hbrBackground
= NULL
;
1456 wc
.lpszMenuName
= NULL
;
1460 if (RegisterClassExW(&wc
) == 0)
1462 DPRINT1("Failed to register notify wndproc\n");
1466 wc
.cbSize
= sizeof(WNDCLASSEXW
);
1467 wc
.lpszClassName
= L
"ConsoleWindowClass";
1468 wc
.lpfnWndProc
= GuiConsoleWndProc
;
1470 wc
.hInstance
= (HINSTANCE
) GetModuleHandleW(NULL
);
1471 wc
.hIcon
= LoadIconW(Win32CsrDllHandle
, MAKEINTRESOURCEW(1));
1472 wc
.hCursor
= LoadCursorW(NULL
, MAKEINTRESOURCEW(IDC_ARROW
));
1473 wc
.hbrBackground
= NULL
;
1474 wc
.lpszMenuName
= NULL
;
1477 wc
.hIconSm
= LoadImageW(Win32CsrDllHandle
, MAKEINTRESOURCEW(1), IMAGE_ICON
,
1478 GetSystemMetrics(SM_CXSMICON
), GetSystemMetrics(SM_CYSMICON
),
1480 if (RegisterClassExW(&wc
) == 0)
1482 DPRINT1("Failed to register console wndproc\n");
1490 GuiInitScreenBuffer(PCSRSS_CONSOLE Console
, PCSRSS_SCREEN_BUFFER Buffer
)
1492 Buffer
->DefaultAttrib
= 0x0f;
1496 GuiChangeTitle(PCSRSS_CONSOLE Console
)
1498 PWCHAR Buffer
, Title
;
1500 Buffer
= HeapAlloc(Win32CsrApiHeap
, 0,
1501 Console
->Title
.Length
+ sizeof(WCHAR
));
1504 memcpy(Buffer
, Console
->Title
.Buffer
, Console
->Title
.Length
);
1505 Buffer
[Console
->Title
.Length
/ sizeof(WCHAR
)] = L
'\0';
1512 SendMessageW(Console
->hWindow
, WM_SETTEXT
, 0, (LPARAM
) Title
);
1515 HeapFree(Win32CsrApiHeap
, 0, Buffer
);
1522 GuiChangeIcon(PCSRSS_CONSOLE Console
)
1524 SendMessageW(Console
->hWindow
, WM_SETICON
, ICON_BIG
, (LPARAM
)Console
->hWindowIcon
);
1525 SendMessageW(Console
->hWindow
, WM_SETICON
, ICON_SMALL
, (LPARAM
)Console
->hWindowIcon
);
1531 GuiCleanupConsole(PCSRSS_CONSOLE Console
)
1533 SendMessageW(NotifyWnd
, PM_DESTROY_CONSOLE
, 0, (LPARAM
) Console
);
1536 static CSRSS_CONSOLE_VTBL GuiVtbl
=
1538 GuiInitScreenBuffer
,
1549 GuiInitConsole(PCSRSS_CONSOLE Console
)
1551 HANDLE GraphicsStartupEvent
;
1552 HANDLE ThreadHandle
;
1553 PGUI_CONSOLE_DATA GuiData
;
1555 if (! ConsInitialized
)
1557 ConsInitialized
= TRUE
;
1560 ConsInitialized
= FALSE
;
1561 return STATUS_UNSUCCESSFUL
;
1565 Console
->Vtbl
= &GuiVtbl
;
1566 if (NULL
== NotifyWnd
)
1568 GraphicsStartupEvent
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
1569 if (NULL
== GraphicsStartupEvent
)
1571 return STATUS_UNSUCCESSFUL
;
1574 ThreadHandle
= CreateThread(NULL
,
1576 GuiConsoleGuiThread
,
1577 (PVOID
) &GraphicsStartupEvent
,
1580 if (NULL
== ThreadHandle
)
1582 NtClose(GraphicsStartupEvent
);
1583 DPRINT1("Win32Csr: Failed to create graphics console thread. Expect problems\n");
1584 return STATUS_UNSUCCESSFUL
;
1586 SetThreadPriority(ThreadHandle
, THREAD_PRIORITY_HIGHEST
);
1587 CloseHandle(ThreadHandle
);
1589 WaitForSingleObject(GraphicsStartupEvent
, INFINITE
);
1590 CloseHandle(GraphicsStartupEvent
);
1592 if (NULL
== NotifyWnd
)
1594 DPRINT1("Win32Csr: Failed to create notification window.\n");
1595 return STATUS_UNSUCCESSFUL
;
1598 GuiData
= HeapAlloc(Win32CsrApiHeap
, HEAP_ZERO_MEMORY
,
1599 sizeof(GUI_CONSOLE_DATA
));
1602 DPRINT1("Win32Csr: Failed to create GUI_CONSOLE_DATA\n");
1603 return STATUS_UNSUCCESSFUL
;
1606 Console
->PrivateData
= (PVOID
) GuiData
;
1608 * we need to wait untill the GUI has been fully initialized
1609 * to retrieve custom settings i.e. WindowSize etc..
1610 * Ideally we could use SendNotifyMessage for this but its not
1614 GuiData
->hGuiInitEvent
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
1615 /* create console */
1616 PostMessageW(NotifyWnd
, PM_CREATE_CONSOLE
, 0, (LPARAM
) Console
);
1618 /* wait untill initialization has finished */
1619 WaitForSingleObject(GuiData
->hGuiInitEvent
, INFINITE
);
1620 DPRINT1("received event Console %p GuiData %p X %d Y %d\n", Console
, Console
->PrivateData
, Console
->Size
.X
, Console
->Size
.Y
);
1621 CloseHandle(GuiData
->hGuiInitEvent
);
1622 GuiData
->hGuiInitEvent
= NULL
;
1624 return STATUS_SUCCESS
;