ReactOS 0.4.15-dev-7788-g1ad9096
winsta.c
Go to the documentation of this file.
1/*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS Win32k subsystem
4 * PURPOSE: Window stations
5 * FILE: win32ss/user/ntuser/winsta.c
6 * PROGRAMER: Casper S. Hornstrup (chorns@users.sourceforge.net)
7 * TODO: The process window station is created on
8 * the first USER32/GDI32 call not related
9 * to window station/desktop handling
10 */
11
12#include <win32k.h>
14
15/* GLOBALS *******************************************************************/
16
17/*
18 * The currently active window station. This is the
19 * only one interactive window station on the system.
20 */
22
23/* Winlogon SAS window */
25
26/* Full path to WindowStations directory */
28
29/* INITIALIZATION FUNCTIONS ****************************************************/
30
31CODE_SEG("INIT")
35{
36 GENERIC_MAPPING IntWindowStationMapping = { WINSTA_READ,
40
41 /* Set Winsta Object Attributes */
43 ExWindowStationObjectType->TypeInfo.GenericMapping = IntWindowStationMapping;
45
46 return STATUS_SUCCESS;
47}
48
52{
54 PPEB Peb;
56 HANDLE hWinstaDir;
57 WCHAR wstrWindowStationsDir[MAX_PATH];
58
59 /* Create the WindowStations directory and cache its path for later use */
60 Peb = NtCurrentPeb();
61 if(Peb->SessionId == 0)
62 {
64 {
66 }
67 }
68 else
69 {
70 Status = RtlStringCbPrintfW(wstrWindowStationsDir,
71 sizeof(wstrWindowStationsDir),
72 L"%ws\\%lu%ws",
76 if (!NT_SUCCESS(Status))
77 return Status;
78
79 if (!RtlCreateUnicodeString(&gustrWindowStationsDir, wstrWindowStationsDir))
80 {
82 }
83 }
84
88 NULL,
89 NULL);
91 if (!NT_SUCCESS(Status))
92 {
93 ERR("Could not create %wZ directory (Status 0x%X)\n", &gustrWindowStationsDir, Status);
94 return Status;
95 }
96
97 TRACE("Created directory %wZ for session %lu\n", &gustrWindowStationsDir, Peb->SessionId);
98
99 return Status;
100}
101
102/* OBJECT CALLBACKS ***********************************************************/
103
105NTAPI
108{
110 PWINSTATION_OBJECT WinSta = (PWINSTATION_OBJECT)DeleteParameters->Object;
111
112 TRACE("Deleting window station 0x%p\n", WinSta);
113
114 if (WinSta == InputWindowStation)
115 {
116 ERR("WARNING: Deleting the interactive window station '%wZ'!\n",
118
119 /* Only Winlogon can close and delete the interactive window station */
121
123 }
124
125 WinSta->Flags |= WSS_DYING;
126
128
130
132
133 return STATUS_SUCCESS;
134}
135
137NTAPI
140{
143
144 /* Assume we don't find anything */
145 *ParseParameters->Object = NULL;
146
147 /* Check for an empty name */
148 if (!RemainingName->Length)
149 {
150 /* Make sure this is a window station, can't parse a desktop now */
151 if (ParseParameters->ObjectType != ExWindowStationObjectType)
152 {
153 /* Fail */
155 }
156
157 /* Reference the window station and return */
158 ObReferenceObject(ParseParameters->ParseObject);
159 *ParseParameters->Object = ParseParameters->ParseObject;
160 return STATUS_SUCCESS;
161 }
162
163 /* Check for leading slash */
164 if (RemainingName->Buffer[0] == OBJ_NAME_PATH_SEPARATOR)
165 {
166 /* Skip it */
167 RemainingName->Buffer++;
168 RemainingName->Length -= sizeof(WCHAR);
169 RemainingName->MaximumLength -= sizeof(WCHAR);
170 }
171
172 /* Check if there is still a slash */
174 {
175 /* In this case, fail */
177 }
178
179 /*
180 * Check if we are parsing a desktop.
181 */
182 if (ParseParameters->ObjectType == ExDesktopObjectType)
183 {
184 /* Then call the desktop parse routine */
185 return IntDesktopObjectParse(ParseParameters->ParseObject,
186 ParseParameters->ObjectType,
187 ParseParameters->AccessState,
188 ParseParameters->AccessMode,
189 ParseParameters->Attributes,
190 ParseParameters->CompleteName,
192 ParseParameters->Context,
193 ParseParameters->SecurityQos,
194 ParseParameters->Object);
195 }
196
197 /* Should hopefully never get here */
199}
200
202NTAPI
205{
207 PPROCESSINFO ppi;
208
210
211 if (ppi && (OkToCloseParameters->Handle == ppi->hwinsta))
212 {
214 }
215
216 return STATUS_SUCCESS;
217}
218
219/* PRIVATE FUNCTIONS **********************************************************/
220
221/*
222 * IntValidateWindowStationHandle
223 *
224 * Validates the window station handle.
225 *
226 * Remarks
227 * If the function succeeds, the handle remains referenced. If the
228 * fucntion fails, last error is set.
229 */
230
233 HWINSTA WindowStation,
237 POBJECT_HANDLE_INFORMATION pObjectHandleInfo)
238{
240
241 if (WindowStation == NULL)
242 {
243 ERR("Invalid window station handle\n");
246 }
247
248 Status = ObReferenceObjectByHandle(WindowStation,
252 (PVOID*)Object,
253 pObjectHandleInfo);
254
255 if (!NT_SUCCESS(Status))
257
258 return Status;
259}
260
263{
264 TEXTMETRICW tmw;
265 UNICODE_STRING DriverName = RTL_CONSTANT_STRING(L"DISPLAY");
266 PDESKTOP pdesk;
267
269 {
270 ERR("PDEVOBJ_lChangeDisplaySettings() failed.\n");
271 return FALSE;
272 }
273
276 {
278 return FALSE;
279 }
281
283 {
284 return FALSE;
285 }
286
288
291
292 /* Update the system metrics */
293 InitMetrics();
294
295 /* Set new size of the monitor */
297
298 /* Update the SERVERINFO */
303 gpsi->BitCount = gpsi->Planes * gpsi->BitsPixel;
306 {
307 gpsi->PUSIFlags |= PUSIF_PALETTEDISPLAY;
308 }
309 else
310 {
311 gpsi->PUSIFlags &= ~PUSIF_PALETTEDISPLAY;
312 }
313 // Font is realized and this dc was previously set to internal DC_ATTR.
314 gpsi->cxSysFontChar = IntGetCharDimensions(hSystemBM, &tmw, (DWORD*)&gpsi->cySysFontChar);
315 gpsi->tmSysFont = tmw;
316
317 /* Put the pointer in the center of the screen */
318 gpsi->ptCursor.x = gpsi->aiSysMet[SM_CXSCREEN] / 2;
319 gpsi->ptCursor.y = gpsi->aiSysMet[SM_CYSCREEN] / 2;
320
321 /* Attach monitor */
323
324 /* Setup the cursor */
326
327 /* Setup the icons */
329
330 /* Setup Menu */
331 MenuInit();
332
333 /* Show the desktop */
334 pdesk = IntGetActiveDesktop();
335 ASSERT(pdesk);
336 co_IntShowDesktop(pdesk, gpsi->aiSysMet[SM_CXSCREEN], gpsi->aiSysMet[SM_CYSCREEN], TRUE);
337
338 /* HACK: display wallpaper on all secondary displays */
339 {
340 PGRAPHICS_DEVICE pGraphicsDevice;
341 UNICODE_STRING DriverName = RTL_CONSTANT_STRING(L"DISPLAY");
342 UNICODE_STRING DisplayName;
343 HDC hdc;
344 ULONG iDevNum;
345
346 for (iDevNum = 1; (pGraphicsDevice = EngpFindGraphicsDevice(NULL, iDevNum)) != NULL; iDevNum++)
347 {
348 RtlInitUnicodeString(&DisplayName, pGraphicsDevice->szWinDeviceName);
349 hdc = IntGdiCreateDC(&DriverName, &DisplayName, NULL, NULL, FALSE);
351 }
352 }
353
354 return TRUE;
355}
356
359{
361 { // No need to allocate a new dcattr.
365 }
368}
369
372{
373 return ScreenDeviceContext;
374}
375
378{
381 {
382 if (!(ppi->W32PF_flags & W32PF_IOWINSTA))
383 {
384 ERR("Requires Interactive Window Station\n");
386 return FALSE;
387 }
389 {
390 ERR("Access Denied\n");
392 return FALSE;
393 }
394 }
395 return TRUE;
396}
397
398// Win: _GetProcessWindowStation
401{
402 PWINSTATION_OBJECT pWinSta;
404 HWINSTA hWinSta = ppi->hwinsta;
405 if (phWinSta)
406 *phWinSta = hWinSta;
407 IntValidateWindowStationHandle(hWinSta, UserMode, 0, &pWinSta, 0);
408 return pWinSta;
409}
410
411/* PUBLIC FUNCTIONS ***********************************************************/
412
413/*
414 * NtUserCreateWindowStation
415 *
416 * Creates a new window station.
417 *
418 * Parameters
419 * lpszWindowStationName
420 * Pointer to a null-terminated string specifying the name of the
421 * window station to be created. Window station names are
422 * case-insensitive and cannot contain backslash characters (\‍).
423 * Only members of the Administrators group are allowed to specify a
424 * name.
425 *
426 * dwDesiredAccess
427 * Requested type of access
428 *
429 * lpSecurity
430 * Security descriptor
431 *
432 * Unknown3, Unknown4, Unknown5, Unknown6
433 * Unused
434 *
435 * Return Value
436 * If the function succeeds, the return value is a handle to the newly
437 * created window station. If the specified window station already
438 * exists, the function succeeds and returns a handle to the existing
439 * window station. If the function fails, the return value is NULL.
440 *
441 * Status
442 * @implemented
443 */
444
448 OUT HWINSTA* phWinSta,
451 IN KPROCESSOR_MODE OwnerMode,
452 IN ACCESS_MASK dwDesiredAccess,
453 DWORD Unknown2,
458{
460 HWINSTA hWinSta;
461 PWINSTATION_OBJECT WindowStation;
462
463 TRACE("IntCreateWindowStation called\n");
464
465 ASSERT(phWinSta);
466 *phWinSta = NULL;
467
471 NULL,
472 dwDesiredAccess,
473 NULL,
474 (PVOID*)&hWinSta);
475 if (NT_SUCCESS(Status))
476 {
477 TRACE("IntCreateWindowStation opened window station '%wZ'\n",
478 ObjectAttributes->ObjectName);
479 *phWinSta = hWinSta;
480 return Status;
481 }
482
483 /*
484 * No existing window station found, try to create a new one.
485 */
486
487 /* Create the window station object */
491 OwnerMode,
492 NULL,
493 sizeof(WINSTATION_OBJECT),
494 0,
495 0,
496 (PVOID*)&WindowStation);
497 if (!NT_SUCCESS(Status))
498 {
499 ERR("ObCreateObject failed for window station '%wZ', Status 0x%08lx\n",
500 ObjectAttributes->ObjectName, Status);
502 return Status;
503 }
504
505 /* Initialize the window station */
506 RtlZeroMemory(WindowStation, sizeof(WINSTATION_OBJECT));
507
508 InitializeListHead(&WindowStation->DesktopListHead);
509 WindowStation->dwSessionId = NtCurrentPeb()->SessionId;
510 Status = RtlCreateAtomTable(37, &WindowStation->AtomTable);
511 if (!NT_SUCCESS(Status))
512 {
513 ERR("RtlCreateAtomTable failed for window station '%wZ', Status 0x%08lx\n",
514 ObjectAttributes->ObjectName, Status);
515 ObDereferenceObject(WindowStation);
517 return Status;
518 }
519
520 Status = ObInsertObject(WindowStation,
521 NULL,
522 dwDesiredAccess,
523 0,
524 NULL,
525 (PVOID*)&hWinSta);
526 if (!NT_SUCCESS(Status))
527 {
528 ERR("ObInsertObject failed for window station, Status 0x%08lx\n", Status);
530 return Status;
531 }
532
533 // FIXME! TODO: Add this new window station to a linked list
534
536 {
537 ERR("Initializing input window station\n");
538
539 /* Only Winlogon can create the interactive window station */
541
542 InputWindowStation = WindowStation;
543 WindowStation->Flags &= ~WSS_NOIO;
544
546
549
550 /* Desktop functions require the desktop thread running so wait for it to initialize */
551 UserLeaveCo();
554 UserMode,
555 FALSE,
556 NULL);
557 UserEnterCo();
558 }
559 else
560 {
561 WindowStation->Flags |= WSS_NOIO;
562 }
563
564 TRACE("IntCreateWindowStation created window station '%wZ' object 0x%p handle 0x%p\n",
565 ObjectAttributes->ObjectName, WindowStation, hWinSta);
566
567 *phWinSta = hWinSta;
569
570 return STATUS_SUCCESS;
571}
572
573static VOID
575 IN OUT PUNICODE_STRING WindowStationName,
576 IN PUNICODE_STRING TebStaticUnicodeString,
577 IN OUT POBJECT_ATTRIBUTES UserModeObjectAttributes OPTIONAL,
578 IN POBJECT_ATTRIBUTES LocalObjectAttributes OPTIONAL)
579{
580 SIZE_T MemSize = 0;
581
582 /* Try to restore the user's UserModeObjectAttributes */
583 if (UserModeObjectAttributes && LocalObjectAttributes)
584 {
586 {
587 ProbeForWrite(UserModeObjectAttributes, sizeof(OBJECT_ATTRIBUTES), sizeof(ULONG));
588 *UserModeObjectAttributes = *LocalObjectAttributes;
589 }
591 {
592 NOTHING;
593 }
594 _SEH2_END;
595 }
596
597 /* Free the user-mode memory */
598 if (WindowStationName && (WindowStationName != TebStaticUnicodeString))
599 {
600 ZwFreeVirtualMemory(ZwCurrentProcess(),
601 (PVOID*)&WindowStationName,
602 &MemSize,
604 }
605}
606
607static NTSTATUS
609 IN OUT POBJECT_ATTRIBUTES UserModeObjectAttributes,
610 IN OUT POBJECT_ATTRIBUTES LocalObjectAttributes,
611 OUT PUNICODE_STRING* WindowStationName,
612 OUT PUNICODE_STRING* TebStaticUnicodeString)
613{
615 SIZE_T MemSize;
616
617 LUID CallerLuid;
618 PTEB Teb;
619 USHORT StrSize;
620
621 *WindowStationName = NULL;
622 *TebStaticUnicodeString = NULL;
623
624 /* Retrieve the current process LUID */
625 Status = GetProcessLuid(NULL, NULL, &CallerLuid);
626 if (!NT_SUCCESS(Status))
627 {
628 ERR("Failed to retrieve the caller LUID, Status 0x%08lx\n", Status);
629 return Status;
630 }
631
632 /* Compute the needed string size */
633 MemSize = _scwprintf(L"%wZ\\Service-0x%x-%x$",
635 CallerLuid.HighPart,
636 CallerLuid.LowPart);
637 MemSize = MemSize * sizeof(WCHAR) + sizeof(UNICODE_NULL);
638 if (MemSize > MAXUSHORT)
639 {
640 ERR("Window station name length is too long.\n");
642 }
643 StrSize = (USHORT)MemSize;
644
645 /*
646 * Check whether it's short enough so that we can use the static buffer
647 * in the TEB. Otherwise continue with virtual memory allocation.
648 */
649 Teb = NtCurrentTeb();
650 if (Teb && (StrSize <= sizeof(Teb->StaticUnicodeBuffer)))
651 {
652 /* We can use the TEB's static unicode string */
655
656 /* Remember the TEB's static unicode string address for later */
657 *TebStaticUnicodeString = &Teb->StaticUnicodeString;
658
659 *WindowStationName = *TebStaticUnicodeString;
660 (*WindowStationName)->Length = 0;
661 }
662 else
663 {
664 /* The TEB's static unicode string is too small, allocate some user-mode virtual memory */
665 MemSize += ALIGN_UP(sizeof(UNICODE_STRING), sizeof(PVOID));
666
667 /* Allocate the memory in user-mode */
668 Status = ZwAllocateVirtualMemory(ZwCurrentProcess(),
669 (PVOID*)WindowStationName,
670 0,
671 &MemSize,
674 if (!NT_SUCCESS(Status))
675 {
676 ERR("ZwAllocateVirtualMemory() failed, Status 0x%08lx\n", Status);
677 return Status;
678 }
679
680 RtlInitEmptyUnicodeString(*WindowStationName,
681 (PWCHAR)((ULONG_PTR)*WindowStationName +
682 ALIGN_UP(sizeof(UNICODE_STRING), sizeof(PVOID))),
683 StrSize);
684 }
685
686 /* Build a valid window station name from the LUID */
687 Status = RtlStringCbPrintfW((*WindowStationName)->Buffer,
688 (*WindowStationName)->MaximumLength,
689 L"%wZ\\Service-0x%x-%x$",
691 CallerLuid.HighPart,
692 CallerLuid.LowPart);
693 if (!NT_SUCCESS(Status))
694 {
695 ERR("Impossible to build a valid window station name, Status 0x%08lx\n", Status);
696 goto Quit;
697 }
698 (*WindowStationName)->Length = (USHORT)(wcslen((*WindowStationName)->Buffer) * sizeof(WCHAR));
699
700 /* Try to update the user's UserModeObjectAttributes */
702 {
703 ProbeForWrite(UserModeObjectAttributes, sizeof(OBJECT_ATTRIBUTES), sizeof(ULONG));
704 *LocalObjectAttributes = *UserModeObjectAttributes;
705
706 UserModeObjectAttributes->ObjectName = *WindowStationName;
707 UserModeObjectAttributes->RootDirectory = NULL;
708
710 }
712 {
714 }
715 _SEH2_END;
716
717Quit:
718 if (!NT_SUCCESS(Status))
719 {
720 /* Release the window station name */
721 FreeUserModeWindowStationName(*WindowStationName,
722 *TebStaticUnicodeString,
723 NULL, NULL);
724 }
725
726 return Status;
727}
728
729HWINSTA
733 IN ACCESS_MASK dwDesiredAccess,
734 DWORD Unknown2,
739{
741 HWINSTA hWinSta = NULL;
742 OBJECT_ATTRIBUTES LocalObjectAttributes;
743 PUNICODE_STRING WindowStationName = NULL;
744 PUNICODE_STRING TebStaticUnicodeString = NULL;
745 KPROCESSOR_MODE OwnerMode = UserMode;
746
747 TRACE("NtUserCreateWindowStation called\n");
748
749 /* Capture the object attributes and the window station name */
751 {
753 LocalObjectAttributes = *ObjectAttributes;
754 if (LocalObjectAttributes.Length != sizeof(OBJECT_ATTRIBUTES))
755 {
756 ERR("Invalid ObjectAttributes length!\n");
759 }
760
761 /*
762 * Check whether the caller provided a window station name together
763 * with a RootDirectory handle.
764 *
765 * If the caller did not provide a window station name, build a new one
766 * based on the logon session identifier for the calling process.
767 * The new name is allocated in user-mode, as the rest of ObjectAttributes
768 * already is, so that the validation performed by the Object Manager
769 * can be done adequately.
770 */
771 if ((LocalObjectAttributes.ObjectName == NULL ||
772 LocalObjectAttributes.ObjectName->Buffer == NULL ||
773 LocalObjectAttributes.ObjectName->Length == 0 ||
774 LocalObjectAttributes.ObjectName->Buffer[0] == UNICODE_NULL)
775 /* &&
776 LocalObjectAttributes.RootDirectory == NULL */)
777 {
778 /* No, build the new window station name */
780 &LocalObjectAttributes,
781 &WindowStationName,
782 &TebStaticUnicodeString);
783 if (!NT_SUCCESS(Status))
784 {
785 ERR("BuildUserModeWindowStationName() failed, Status 0x%08lx\n", Status);
787 }
788 OwnerMode = KernelMode;
789 }
790 }
792 {
794 ERR("ObjectAttributes capture failed, Status 0x%08lx\n", Status);
795 }
796 _SEH2_END;
797
798 if (!NT_SUCCESS(Status))
799 {
801 return NULL;
802 }
803
805
806 /* Create the window station */
809 UserMode,
810 OwnerMode,
811 dwDesiredAccess,
812 Unknown2,
813 Unknown3,
814 Unknown4,
815 Unknown5,
816 Unknown6);
817 UserLeave();
818
819 if (NT_SUCCESS(Status))
820 {
821 TRACE("NtUserCreateWindowStation created window station '%wZ' with handle 0x%p\n",
822 ObjectAttributes->ObjectName, hWinSta);
823 }
824 else
825 {
826 ASSERT(hWinSta == NULL);
827 ERR("NtUserCreateWindowStation failed to create window station '%wZ', Status 0x%08lx\n",
828 ObjectAttributes->ObjectName, Status);
829 }
830
831 /* Try to restore the user's ObjectAttributes and release the window station name */
832 FreeUserModeWindowStationName(WindowStationName,
833 TebStaticUnicodeString,
834 (OwnerMode == KernelMode ? ObjectAttributes : NULL),
835 &LocalObjectAttributes);
836
837 if (!NT_SUCCESS(Status))
838 {
839 ASSERT(hWinSta == NULL);
841 }
842
843 return hWinSta;
844}
845
846/*
847 * NtUserOpenWindowStation
848 *
849 * Opens an existing window station.
850 *
851 * Parameters
852 * lpszWindowStationName
853 * Name of the existing window station.
854 *
855 * dwDesiredAccess
856 * Requested type of access.
857 *
858 * Return Value
859 * If the function succeeds, the return value is the handle to the
860 * specified window station. If the function fails, the return value
861 * is NULL.
862 *
863 * Remarks
864 * The returned handle can be closed with NtUserCloseWindowStation.
865 *
866 * Status
867 * @implemented
868 */
869
870HWINSTA
874 IN ACCESS_MASK dwDesiredAccess)
875{
877 HWINSTA hWinSta = NULL;
878 OBJECT_ATTRIBUTES LocalObjectAttributes;
879 PUNICODE_STRING WindowStationName = NULL;
880 PUNICODE_STRING TebStaticUnicodeString = NULL;
881 KPROCESSOR_MODE OwnerMode = UserMode;
882
883 TRACE("NtUserOpenWindowStation called\n");
884
885 /* Capture the object attributes and the window station name */
887 {
889 LocalObjectAttributes = *ObjectAttributes;
890 if (LocalObjectAttributes.Length != sizeof(OBJECT_ATTRIBUTES))
891 {
892 ERR("Invalid ObjectAttributes length!\n");
895 }
896
897 /*
898 * Check whether the caller did not provide a window station name,
899 * or provided the special "Service-0x00000000-00000000$" name.
900 *
901 * NOTE: On Windows, the special "Service-0x00000000-00000000$" string
902 * is used instead of an empty name (observed when API-monitoring
903 * OpenWindowStation() called with an empty window station name).
904 */
905 if ((LocalObjectAttributes.ObjectName == NULL ||
906 LocalObjectAttributes.ObjectName->Buffer == NULL ||
907 LocalObjectAttributes.ObjectName->Length == 0 ||
908 LocalObjectAttributes.ObjectName->Buffer[0] == UNICODE_NULL)
909 /* &&
910 LocalObjectAttributes.RootDirectory == NULL */)
911 {
912 /* No, remember that for later */
913 LocalObjectAttributes.ObjectName = NULL;
914 }
915 if (LocalObjectAttributes.ObjectName &&
916 LocalObjectAttributes.ObjectName->Length ==
917 sizeof(L"Service-0x00000000-00000000$") - sizeof(UNICODE_NULL) &&
918 _wcsnicmp(LocalObjectAttributes.ObjectName->Buffer,
919 L"Service-0x00000000-00000000$",
920 LocalObjectAttributes.ObjectName->Length / sizeof(WCHAR)) == 0)
921 {
922 /* No, remember that for later */
923 LocalObjectAttributes.ObjectName = NULL;
924 }
925
926 /*
927 * If the caller did not provide a window station name, build a new one
928 * based on the logon session identifier for the calling process.
929 * The new name is allocated in user-mode, as the rest of ObjectAttributes
930 * already is, so that the validation performed by the Object Manager
931 * can be done adequately.
932 */
933 if (!LocalObjectAttributes.ObjectName)
934 {
935 /* No, build the new window station name */
937 &LocalObjectAttributes,
938 &WindowStationName,
939 &TebStaticUnicodeString);
940 if (!NT_SUCCESS(Status))
941 {
942 ERR("BuildUserModeWindowStationName() failed, Status 0x%08lx\n", Status);
944 }
945 OwnerMode = KernelMode;
946 }
947 }
949 {
951 ERR("ObjectAttributes capture failed, Status 0x%08lx\n", Status);
952 }
953 _SEH2_END;
954
955 if (!NT_SUCCESS(Status))
956 {
958 return NULL;
959 }
960
961 /* Open the window station */
964 UserMode,
965 NULL,
966 dwDesiredAccess,
967 NULL,
968 (PVOID*)&hWinSta);
969 if (NT_SUCCESS(Status))
970 {
971 TRACE("NtUserOpenWindowStation opened window station '%wZ' with handle 0x%p\n",
972 ObjectAttributes->ObjectName, hWinSta);
973 }
974 else
975 {
976 ASSERT(hWinSta == NULL);
977 ERR("NtUserOpenWindowStation failed to open window station '%wZ', Status 0x%08lx\n",
978 ObjectAttributes->ObjectName, Status);
979 }
980
981 /* Try to restore the user's ObjectAttributes and release the window station name */
982 FreeUserModeWindowStationName(WindowStationName,
983 TebStaticUnicodeString,
984 (OwnerMode == KernelMode ? ObjectAttributes : NULL),
985 &LocalObjectAttributes);
986
987 if (!NT_SUCCESS(Status))
988 {
989 ASSERT(hWinSta == NULL);
991 }
992
993 return hWinSta;
994}
995
996/*
997 * NtUserCloseWindowStation
998 *
999 * Closes a window station handle.
1000 *
1001 * Parameters
1002 * hWinSta
1003 * Handle to the window station.
1004 *
1005 * Return Value
1006 * Status
1007 *
1008 * Remarks
1009 * The window station handle can be created with NtUserCreateWindowStation
1010 * or NtUserOpenWindowStation. Attempts to close a handle to the window
1011 * station assigned to the calling process will fail.
1012 *
1013 * Status
1014 * @implemented
1015 */
1016
1017BOOL
1020 HWINSTA hWinSta)
1021{
1024
1025 TRACE("NtUserCloseWindowStation called (%p)\n", hWinSta);
1026
1027 if (hWinSta == UserGetProcessWindowStation())
1028 {
1029 ERR("Attempted to close process window station\n");
1030 return FALSE;
1031 }
1032
1034 UserMode,
1035 0,
1036 &Object,
1037 NULL);
1038 if (!NT_SUCCESS(Status))
1039 {
1040 ERR("Validation of window station handle (%p) failed\n", hWinSta);
1041 return FALSE;
1042 }
1043
1045
1046 TRACE("Closing window station handle (%p)\n", hWinSta);
1047
1048 Status = ObCloseHandle(hWinSta, UserMode);
1049 if (!NT_SUCCESS(Status))
1050 {
1052 return FALSE;
1053 }
1054
1055 return TRUE;
1056}
1057
1058/*
1059 * NtUserGetObjectInformation
1060 *
1061 * The NtUserGetObjectInformation function retrieves information about a
1062 * window station or desktop object.
1063 *
1064 * Parameters
1065 * hObj
1066 * Handle to the window station or desktop object for which to
1067 * return information. This can be a handle of type HDESK or HWINSTA
1068 * (for example, a handle returned by NtUserCreateWindowStation,
1069 * NtUserOpenWindowStation, NtUserCreateDesktop, or NtUserOpenDesktop).
1070 *
1071 * nIndex
1072 * Specifies the object information to be retrieved.
1073 *
1074 * pvInfo
1075 * Pointer to a buffer to receive the object information.
1076 *
1077 * nLength
1078 * Specifies the size, in bytes, of the buffer pointed to by the
1079 * pvInfo parameter.
1080 *
1081 * lpnLengthNeeded
1082 * Pointer to a variable receiving the number of bytes required to
1083 * store the requested information. If this variable's value is
1084 * greater than the value of the nLength parameter when the function
1085 * returns, the function returns FALSE, and none of the information
1086 * is copied to the pvInfo buffer. If the value of the variable pointed
1087 * to by lpnLengthNeeded is less than or equal to the value of nLength,
1088 * the entire information block is copied.
1089 *
1090 * Return Value
1091 * If the function succeeds, the return value is nonzero. If the function
1092 * fails, the return value is zero.
1093 *
1094 * Status
1095 * @unimplemented
1096 */
1097
1100 HANDLE hObject,
1101 DWORD nIndex,
1102 PVOID pvInformation,
1103 DWORD nLength,
1104 PDWORD nLengthNeeded)
1105{
1107 PWINSTATION_OBJECT WinStaObject = NULL;
1108 PDESKTOP DesktopObject = NULL;
1109 POBJECT_HEADER ObjectHeader;
1110 POBJECT_HEADER_NAME_INFO NameInfo;
1111 OBJECT_HANDLE_INFORMATION HandleInfo;
1112 USEROBJECTFLAGS ObjectFlags;
1113 PUNICODE_STRING pStrNameU = NULL;
1114 PVOID pvData = NULL;
1115 SIZE_T nDataSize = 0;
1116
1117 _SEH2_TRY
1118 {
1119 if (nLengthNeeded)
1120 ProbeForWrite(nLengthNeeded, sizeof(*nLengthNeeded), 1);
1121 ProbeForWrite(pvInformation, nLength, 1);
1122 }
1124 {
1126 return FALSE;
1127 }
1128 _SEH2_END;
1129
1130 /* Try window station */
1131 TRACE("Trying to open window station 0x%p\n", hObject);
1133 0,
1135 UserMode,
1136 (PVOID*)&WinStaObject,
1137 &HandleInfo);
1138
1140 {
1141 /* Try desktop */
1142 TRACE("Trying to open desktop %p\n", hObject);
1143 WinStaObject = NULL;
1145 UserMode,
1146 0,
1147 &DesktopObject);
1148 }
1149
1150 if (!NT_SUCCESS(Status))
1151 {
1152 ERR("Failed: 0x%x\n", Status);
1153 goto Exit;
1154 }
1155
1156 TRACE("WinSta or Desktop opened!\n");
1157
1158 /* Get data */
1159 switch (nIndex)
1160 {
1161 case UOI_FLAGS:
1162 {
1163 ObjectFlags.fReserved = FALSE;
1164 ObjectFlags.fInherit = !!(HandleInfo.HandleAttributes & OBJ_INHERIT);
1165
1166 ObjectFlags.dwFlags = 0;
1167 if (WinStaObject != NULL)
1168 {
1169 if (!(WinStaObject->Flags & WSS_NOIO))
1170 ObjectFlags.dwFlags |= WSF_VISIBLE;
1171 }
1172 else if (DesktopObject != NULL)
1173 {
1174 FIXME("Setting DF_ALLOWOTHERACCOUNTHOOK is unimplemented.\n");
1175 }
1176 else
1177 {
1178 ERR("No associated WinStaObject nor DesktopObject!\n");
1179 }
1180
1181 pvData = &ObjectFlags;
1182 nDataSize = sizeof(ObjectFlags);
1184 break;
1185 }
1186
1187 case UOI_NAME:
1188 {
1189 if (WinStaObject != NULL)
1190 {
1191 ObjectHeader = OBJECT_TO_OBJECT_HEADER(WinStaObject);
1192 NameInfo = OBJECT_HEADER_TO_NAME_INFO(ObjectHeader);
1193
1194 if (NameInfo && (NameInfo->Name.Length > 0))
1195 {
1196 /* Named window station */
1197 pStrNameU = &NameInfo->Name;
1198 nDataSize = pStrNameU->Length + sizeof(UNICODE_NULL);
1199 }
1200 else
1201 {
1202 /* Unnamed window station (should never happen!) */
1203 ASSERT(FALSE);
1204 pStrNameU = NULL;
1205 nDataSize = sizeof(UNICODE_NULL);
1206 }
1208 }
1209 else if (DesktopObject != NULL)
1210 {
1211 pvData = DesktopObject->pDeskInfo->szDesktopName;
1212 nDataSize = (wcslen(DesktopObject->pDeskInfo->szDesktopName) + 1) * sizeof(WCHAR);
1214 }
1215 else
1216 {
1218 }
1219 break;
1220 }
1221
1222 case UOI_TYPE:
1223 {
1224 if (WinStaObject != NULL)
1225 {
1226 ObjectHeader = OBJECT_TO_OBJECT_HEADER(WinStaObject);
1227 pStrNameU = &ObjectHeader->Type->Name;
1228 nDataSize = pStrNameU->Length + sizeof(UNICODE_NULL);
1230 }
1231 else if (DesktopObject != NULL)
1232 {
1233 ObjectHeader = OBJECT_TO_OBJECT_HEADER(DesktopObject);
1234 pStrNameU = &ObjectHeader->Type->Name;
1235 nDataSize = pStrNameU->Length + sizeof(UNICODE_NULL);
1237 }
1238 else
1239 {
1241 }
1242 break;
1243 }
1244
1245 case UOI_USER_SID:
1247 ERR("UOI_USER_SID unimplemented!\n");
1248 break;
1249
1250 default:
1252 break;
1253 }
1254
1255Exit:
1256 if ((Status == STATUS_SUCCESS) && (nLength < nDataSize))
1258
1259 _SEH2_TRY
1260 {
1261 if (nLengthNeeded)
1262 *nLengthNeeded = nDataSize;
1263
1264 /* Try to copy data to caller */
1265 if (Status == STATUS_SUCCESS && (nDataSize > 0))
1266 {
1267 TRACE("Trying to copy data to caller (len = %lu, len needed = %lu)\n", nLength, nDataSize);
1268 if (pvData)
1269 {
1270 /* Copy the data */
1271 RtlCopyMemory(pvInformation, pvData, nDataSize);
1272 }
1273 else if (pStrNameU)
1274 {
1275 /* Copy and NULL-terminate the string */
1276 RtlCopyMemory(pvInformation, pStrNameU->Buffer, pStrNameU->Length);
1277 ((PWCHAR)pvInformation)[pStrNameU->Length / sizeof(WCHAR)] = UNICODE_NULL;
1278 }
1279 else
1280 {
1281 /* Zero the memory */
1282 RtlZeroMemory(pvInformation, nDataSize);
1283 }
1284 }
1285 }
1287 {
1289 }
1290 _SEH2_END;
1291
1292 /* Release objects */
1293 if (DesktopObject != NULL)
1294 ObDereferenceObject(DesktopObject);
1295 if (WinStaObject != NULL)
1296 ObDereferenceObject(WinStaObject);
1297
1298 if (!NT_SUCCESS(Status))
1299 {
1301 return FALSE;
1302 }
1303
1304 return TRUE;
1305}
1306
1307/*
1308 * NtUserSetObjectInformation
1309 *
1310 * The NtUserSetObjectInformation function sets information about a
1311 * window station or desktop object.
1312 *
1313 * Parameters
1314 * hObj
1315 * Handle to the window station or desktop object for which to set
1316 * object information. This value can be a handle of type HDESK or
1317 * HWINSTA.
1318 *
1319 * nIndex
1320 * Specifies the object information to be set.
1321 *
1322 * pvInfo
1323 * Pointer to a buffer containing the object information.
1324 *
1325 * nLength
1326 * Specifies the size, in bytes, of the information contained in the
1327 * buffer pointed to by pvInfo.
1328 *
1329 * Return Value
1330 * If the function succeeds, the return value is nonzero. If the function
1331 * fails the return value is zero.
1332 *
1333 * Status
1334 * @unimplemented
1335 */
1336
1337BOOL
1340 HANDLE hObject,
1341 DWORD nIndex,
1342 PVOID pvInformation,
1343 DWORD nLength)
1344{
1345 /* FIXME: ZwQueryObject */
1346 /* FIXME: ZwSetInformationObject */
1348 return FALSE;
1349}
1350
1351
1352HWINSTA FASTCALL
1354{
1356
1357 return ppi->hwinsta;
1358}
1359
1360
1361/*
1362 * NtUserGetProcessWindowStation
1363 *
1364 * Returns a handle to the current process window station.
1365 *
1366 * Return Value
1367 * If the function succeeds, the return value is handle to the window
1368 * station assigned to the current process. If the function fails, the
1369 * return value is NULL.
1370 *
1371 * Status
1372 * @implemented
1373 */
1374
1375HWINSTA APIENTRY
1377{
1379}
1380
1382UserSetProcessWindowStation(HWINSTA hWindowStation)
1383{
1385 PPROCESSINFO ppi;
1386 OBJECT_HANDLE_INFORMATION ObjectHandleInfo;
1387 PWINSTATION_OBJECT NewWinSta = NULL, OldWinSta;
1388 HWINSTA hCacheWinSta;
1389
1391
1392 /* Reference the new window station */
1393 if (hWindowStation != NULL)
1394 {
1395 Status = IntValidateWindowStationHandle(hWindowStation,
1396 UserMode,
1397 0,
1398 &NewWinSta,
1399 &ObjectHandleInfo);
1400 if (!NT_SUCCESS(Status))
1401 {
1402 TRACE("Validation of window station handle 0x%p failed\n", hWindowStation);
1404 return FALSE;
1405 }
1406 }
1407
1408 OldWinSta = ppi->prpwinsta;
1409 hCacheWinSta = PsGetProcessWin32WindowStation(ppi->peProcess);
1410
1411 /* Dereference the previous window station */
1412 if (OldWinSta != NULL)
1413 {
1414 ObDereferenceObject(OldWinSta);
1415 }
1416
1417 /*
1418 * FIXME: Don't allow changing the window station if there are threads that are attached to desktops and own GUI objects?
1419 */
1420
1421 /* Close the cached EPROCESS window station handle if needed */
1422 if (hCacheWinSta != NULL)
1423 {
1424 /* Reference the window station */
1425 Status = ObReferenceObjectByHandle(hCacheWinSta,
1426 0,
1428 UserMode,
1429 (PVOID*)&OldWinSta,
1430 NULL);
1431 if (!NT_SUCCESS(Status))
1432 {
1433 ERR("Failed to reference the inherited window station, Status 0x%08lx\n", Status);
1434 /* We failed, reset the cache */
1435 hCacheWinSta = NULL;
1436 PsSetProcessWindowStation(ppi->peProcess, hCacheWinSta);
1437 }
1438 else
1439 {
1440 /*
1441 * Close the old handle and reset the cache only
1442 * if we are setting a different window station.
1443 */
1444 if (NewWinSta != OldWinSta)
1445 {
1446 ObCloseHandle(hCacheWinSta, UserMode);
1447 hCacheWinSta = NULL;
1448 PsSetProcessWindowStation(ppi->peProcess, hCacheWinSta);
1449 }
1450
1451 /* Dereference the window station */
1452 ObDereferenceObject(OldWinSta);
1453 }
1454 }
1455
1456 /* Duplicate and save a new cached EPROCESS window station handle */
1457 if ((hCacheWinSta == NULL) && (hWindowStation != NULL))
1458 {
1459 Status = ZwDuplicateObject(ZwCurrentProcess(),
1460 hWindowStation,
1462 (PHANDLE)&hCacheWinSta,
1463 0,
1464 0,
1466 if (!NT_SUCCESS(Status))
1467 {
1468 ERR("UserSetProcessWindowStation: Failed to duplicate the window station handle, Status 0x%08lx\n", Status);
1469 }
1470 else
1471 {
1472 PsSetProcessWindowStation(ppi->peProcess, hCacheWinSta);
1473 }
1474 }
1475
1476 ppi->prpwinsta = NewWinSta;
1477 ppi->hwinsta = hWindowStation;
1478 ppi->amwinsta = hWindowStation != NULL ? ObjectHandleInfo.GrantedAccess : 0;
1479 TRACE("WS : Granted Access 0x%08lx\n",ppi->amwinsta);
1480
1482 {
1483 ppi->W32PF_flags |= W32PF_READSCREENACCESSGRANTED;
1484 }
1485 else
1486 {
1487 ppi->W32PF_flags &= ~W32PF_READSCREENACCESSGRANTED;
1488 }
1489
1490 if (NewWinSta && !(NewWinSta->Flags & WSS_NOIO))
1491 {
1492 ppi->W32PF_flags |= W32PF_IOWINSTA;
1493 }
1494 else /* Might be closed if the handle is NULL */
1495 {
1496 ppi->W32PF_flags &= ~W32PF_IOWINSTA;
1497 }
1498 return TRUE;
1499}
1500
1501/*
1502 * NtUserSetProcessWindowStation
1503 *
1504 * Assigns a window station to the current process.
1505 *
1506 * Parameters
1507 * hWinSta
1508 * Handle to the window station.
1509 *
1510 * Return Value
1511 * Status
1512 *
1513 * Status
1514 * @implemented
1515 */
1516
1518NtUserSetProcessWindowStation(HWINSTA hWindowStation)
1519{
1520 BOOL ret;
1521
1523
1524 ret = UserSetProcessWindowStation(hWindowStation);
1525
1526 UserLeave();
1527
1528 return ret;
1529}
1530
1531/*
1532 * NtUserLockWindowStation
1533 *
1534 * Locks switching desktops. Only the logon application is allowed to call this function.
1535 *
1536 * Status
1537 * @implemented
1538 */
1539
1541NtUserLockWindowStation(HWINSTA hWindowStation)
1542{
1545
1546 TRACE("About to set process window station with handle (%p)\n",
1547 hWindowStation);
1548
1550 {
1551 ERR("Unauthorized process attempted to lock the window station!\n");
1553 return FALSE;
1554 }
1555
1556 Status = IntValidateWindowStationHandle(hWindowStation,
1557 UserMode,
1558 0,
1559 &Object,
1560 NULL);
1561 if (!NT_SUCCESS(Status))
1562 {
1563 TRACE("Validation of window station handle (%p) failed\n",
1564 hWindowStation);
1566 return FALSE;
1567 }
1568
1569 Object->Flags |= WSS_LOCKED;
1570
1572 return TRUE;
1573}
1574
1575/*
1576 * NtUserUnlockWindowStation
1577 *
1578 * Unlocks switching desktops. Only the logon application is allowed to call this function.
1579 *
1580 * Status
1581 * @implemented
1582 */
1583
1585NtUserUnlockWindowStation(HWINSTA hWindowStation)
1586{
1589 BOOL Ret;
1590
1591 TRACE("About to set process window station with handle (%p)\n",
1592 hWindowStation);
1593
1595 {
1596 ERR("Unauthorized process attempted to unlock the window station!\n");
1598 return FALSE;
1599 }
1600
1601 Status = IntValidateWindowStationHandle(hWindowStation,
1602 UserMode,
1603 0,
1604 &Object,
1605 NULL);
1606 if (!NT_SUCCESS(Status))
1607 {
1608 TRACE("Validation of window station handle (%p) failed\n",
1609 hWindowStation);
1611 return FALSE;
1612 }
1613
1614 Ret = (Object->Flags & WSS_LOCKED) == WSS_LOCKED;
1615 Object->Flags &= ~WSS_LOCKED;
1616
1618 return Ret;
1619}
1620
1621static NTSTATUS FASTCALL
1623 ULONG dwSize,
1625 PULONG pRequiredSize)
1626{
1630 char InitialBuffer[256], *Buffer;
1632 DWORD EntryCount;
1634 WCHAR NullWchar;
1635
1636 //
1637 // FIXME: Fully wrong! Since, by calling NtUserCreateWindowStation
1638 // with judicious parameters one can create window stations elsewhere
1639 // than in Windows\WindowStations directory, Win32k definitely MUST
1640 // maintain a list of window stations it has created, and not rely
1641 // on the enumeration of Windows\WindowStations !!!
1642 //
1643
1644 /*
1645 * Try to open the directory.
1646 */
1650 NULL,
1651 NULL);
1652
1656
1657 if (!NT_SUCCESS(Status))
1658 {
1659 return Status;
1660 }
1661
1662 /* First try to query the directory using a fixed-size buffer */
1663 Context = 0;
1664 Buffer = NULL;
1665 Status = ZwQueryDirectoryObject(DirectoryHandle,
1666 InitialBuffer,
1667 sizeof(InitialBuffer),
1668 FALSE,
1669 TRUE,
1670 &Context,
1671 &ReturnLength);
1672 if (NT_SUCCESS(Status))
1673 {
1674 if (STATUS_NO_MORE_ENTRIES == ZwQueryDirectoryObject(DirectoryHandle, NULL, 0, FALSE,
1675 FALSE, &Context, NULL))
1676 {
1677 /* Our fixed-size buffer is large enough */
1678 Buffer = InitialBuffer;
1679 }
1680 }
1681
1682 if (NULL == Buffer)
1683 {
1684 /* Need a larger buffer, check how large exactly */
1685 Status = ZwQueryDirectoryObject(DirectoryHandle, NULL, 0, FALSE, TRUE, &Context,
1686 &ReturnLength);
1687 if (!NT_SUCCESS(Status))
1688 {
1689 ERR("ZwQueryDirectoryObject failed\n");
1691 return Status;
1692 }
1693
1696 if (NULL == Buffer)
1697 {
1699 return STATUS_NO_MEMORY;
1700 }
1701
1702 /* We should have a sufficiently large buffer now */
1703 Context = 0;
1704 Status = ZwQueryDirectoryObject(DirectoryHandle, Buffer, BufferSize,
1706 if (! NT_SUCCESS(Status) ||
1707 STATUS_NO_MORE_ENTRIES != ZwQueryDirectoryObject(DirectoryHandle, NULL, 0, FALSE,
1708 FALSE, &Context, NULL))
1709 {
1710 /* Something went wrong, maybe someone added a directory entry? Just give up. */
1714 }
1715 }
1716
1718
1719 /*
1720 * Count the required size of buffer.
1721 */
1722 ReturnLength = sizeof(DWORD);
1723 EntryCount = 0;
1725 0 != DirEntry->Name.Length;
1726 DirEntry++)
1727 {
1728 ReturnLength += DirEntry->Name.Length + sizeof(WCHAR);
1729 EntryCount++;
1730 }
1731 TRACE("Required size: %lu Entry count: %lu\n", ReturnLength, EntryCount);
1732 if (NULL != pRequiredSize)
1733 {
1734 Status = MmCopyToCaller(pRequiredSize, &ReturnLength, sizeof(ULONG));
1735 if (! NT_SUCCESS(Status))
1736 {
1737 if (Buffer != InitialBuffer)
1738 {
1740 }
1742 }
1743 }
1744
1745 /*
1746 * Check if the supplied buffer is large enough.
1747 */
1748 if (dwSize < ReturnLength)
1749 {
1750 if (Buffer != InitialBuffer)
1751 {
1753 }
1755 }
1756
1757 /*
1758 * Generate the resulting buffer contents.
1759 */
1760 Status = MmCopyToCaller(lpBuffer, &EntryCount, sizeof(DWORD));
1761 if (! NT_SUCCESS(Status))
1762 {
1763 if (Buffer != InitialBuffer)
1764 {
1766 }
1767 return Status;
1768 }
1769 lpBuffer = (PVOID) ((PCHAR) lpBuffer + sizeof(DWORD));
1770
1771 NullWchar = L'\0';
1773 0 != DirEntry->Name.Length;
1774 DirEntry++)
1775 {
1776 Status = MmCopyToCaller(lpBuffer, DirEntry->Name.Buffer, DirEntry->Name.Length);
1777 if (! NT_SUCCESS(Status))
1778 {
1779 if (Buffer != InitialBuffer)
1780 {
1782 }
1783 return Status;
1784 }
1785 lpBuffer = (PVOID) ((PCHAR) lpBuffer + DirEntry->Name.Length);
1786 Status = MmCopyToCaller(lpBuffer, &NullWchar, sizeof(WCHAR));
1787 if (! NT_SUCCESS(Status))
1788 {
1789 if (Buffer != InitialBuffer)
1790 {
1792 }
1793 return Status;
1794 }
1795 lpBuffer = (PVOID) ((PCHAR) lpBuffer + sizeof(WCHAR));
1796 }
1797
1798 /*
1799 * Clean up
1800 */
1801 if (Buffer != InitialBuffer)
1802 {
1804 }
1805
1806 return STATUS_SUCCESS;
1807}
1808
1809static NTSTATUS FASTCALL
1811 HWINSTA hWindowStation,
1812 ULONG dwSize,
1814 PULONG pRequiredSize)
1815{
1817 PWINSTATION_OBJECT WindowStation;
1818 PLIST_ENTRY DesktopEntry;
1819 PDESKTOP DesktopObject;
1820 DWORD EntryCount;
1822 WCHAR NullWchar;
1823 UNICODE_STRING DesktopName;
1824
1825 Status = IntValidateWindowStationHandle(hWindowStation,
1826 UserMode,
1827 0,
1828 &WindowStation,
1829 NULL);
1830 if (! NT_SUCCESS(Status))
1831 {
1832 return Status;
1833 }
1834
1835 /*
1836 * Count the required size of buffer.
1837 */
1838 ReturnLength = sizeof(DWORD);
1839 EntryCount = 0;
1840 for (DesktopEntry = WindowStation->DesktopListHead.Flink;
1841 DesktopEntry != &WindowStation->DesktopListHead;
1842 DesktopEntry = DesktopEntry->Flink)
1843 {
1844 DesktopObject = CONTAINING_RECORD(DesktopEntry, DESKTOP, ListEntry);
1845 RtlInitUnicodeString(&DesktopName, DesktopObject->pDeskInfo->szDesktopName);
1846 ReturnLength += DesktopName.Length + sizeof(WCHAR);
1847 EntryCount++;
1848 }
1849 TRACE("Required size: %lu Entry count: %lu\n", ReturnLength, EntryCount);
1850 if (NULL != pRequiredSize)
1851 {
1852 Status = MmCopyToCaller(pRequiredSize, &ReturnLength, sizeof(ULONG));
1853 if (! NT_SUCCESS(Status))
1854 {
1855 ObDereferenceObject(WindowStation);
1857 }
1858 }
1859
1860 /*
1861 * Check if the supplied buffer is large enough.
1862 */
1863 if (dwSize < ReturnLength)
1864 {
1865 ObDereferenceObject(WindowStation);
1867 }
1868
1869 /*
1870 * Generate the resulting buffer contents.
1871 */
1872 Status = MmCopyToCaller(lpBuffer, &EntryCount, sizeof(DWORD));
1873 if (! NT_SUCCESS(Status))
1874 {
1875 ObDereferenceObject(WindowStation);
1876 return Status;
1877 }
1878 lpBuffer = (PVOID) ((PCHAR) lpBuffer + sizeof(DWORD));
1879
1880 NullWchar = L'\0';
1881 for (DesktopEntry = WindowStation->DesktopListHead.Flink;
1882 DesktopEntry != &WindowStation->DesktopListHead;
1883 DesktopEntry = DesktopEntry->Flink)
1884 {
1885 DesktopObject = CONTAINING_RECORD(DesktopEntry, DESKTOP, ListEntry);
1886 RtlInitUnicodeString(&DesktopName, DesktopObject->pDeskInfo->szDesktopName);
1887 Status = MmCopyToCaller(lpBuffer, DesktopName.Buffer, DesktopName.Length);
1888 if (! NT_SUCCESS(Status))
1889 {
1890 ObDereferenceObject(WindowStation);
1891 return Status;
1892 }
1893 lpBuffer = (PVOID) ((PCHAR)lpBuffer + DesktopName.Length);
1894 Status = MmCopyToCaller(lpBuffer, &NullWchar, sizeof(WCHAR));
1895 if (! NT_SUCCESS(Status))
1896 {
1897 ObDereferenceObject(WindowStation);
1898 return Status;
1899 }
1900 lpBuffer = (PVOID) ((PCHAR) lpBuffer + sizeof(WCHAR));
1901 }
1902
1903 /*
1904 * Clean up and return
1905 */
1906 ObDereferenceObject(WindowStation);
1907 return STATUS_SUCCESS;
1908}
1909
1910/*
1911 * NtUserBuildNameList
1912 *
1913 * Function used for enumeration of desktops or window stations.
1914 *
1915 * Parameters
1916 * hWinSta
1917 * For enumeration of window stations this parameter must be set to
1918 * zero. Otherwise it's handle for window station.
1919 *
1920 * dwSize
1921 * Size of buffer passed by caller.
1922 *
1923 * lpBuffer
1924 * Buffer passed by caller. If the function succeeds, the buffer is
1925 * filled with window station/desktop count (in first DWORD) and
1926 * NULL-terminated window station/desktop names.
1927 *
1928 * pRequiredSize
1929 * If the function succeeds, this is the number of bytes copied.
1930 * Otherwise it's size of buffer needed for function to succeed.
1931 *
1932 * Status
1933 * @implemented
1934 */
1935
1938 HWINSTA hWindowStation,
1939 ULONG dwSize,
1941 PULONG pRequiredSize)
1942{
1943 /* The WindowStation name list and desktop name list are build in completely
1944 different ways. Call the appropriate function */
1945 return NULL == hWindowStation ? BuildWindowStationNameList(dwSize, lpBuffer, pRequiredSize) :
1946 BuildDesktopNameList(hWindowStation, dwSize, lpBuffer, pRequiredSize);
1947}
1948
1949/*
1950 * @implemented
1951 */
1954{
1956 {
1957 return FALSE;
1958 }
1959
1960 if (!IntIsWindow(hWnd))
1961 {
1962 return FALSE;
1963 }
1964
1965 hwndSAS = hWnd;
1966
1967 return TRUE;
1968}
1969
1970BOOL
1973{
1974 BOOL ret;
1976
1978
1979 if (pti->rpdesk == IntGetActiveDesktop())
1980 {
1982 }
1983 else
1984 {
1985 ret = FALSE;
1986 }
1987
1988 UserLeave();
1989
1990 return ret;
1991}
1992
1993BOOL
1994NTAPI
1996 IN HWINSTA hWindowStation,
1997 IN PLUID pluid,
1998 IN PSID psid OPTIONAL,
1999 IN DWORD size)
2000{
2001 BOOL Ret = FALSE;
2003 PWINSTATION_OBJECT WindowStation = NULL;
2004 LUID luidUser;
2005
2007
2009 {
2011 goto Leave;
2012 }
2013
2014 /* Validate the window station */
2015 Status = IntValidateWindowStationHandle(hWindowStation,
2016 UserMode,
2017 0,
2018 &WindowStation,
2019 NULL);
2020 if (!NT_SUCCESS(Status))
2021 {
2022 goto Leave;
2023 }
2024
2025 /* Capture the user LUID */
2026 _SEH2_TRY
2027 {
2028 ProbeForRead(pluid, sizeof(LUID), 1);
2029 luidUser = *pluid;
2030 }
2032 {
2034 _SEH2_YIELD(goto Leave);
2035 }
2036 _SEH2_END;
2037
2038 /* Reset the window station user LUID */
2039 RtlZeroMemory(&WindowStation->luidUser, sizeof(LUID));
2040
2041 /* Reset the window station user SID */
2042 if (WindowStation->psidUser)
2043 {
2045 WindowStation->psidUser = NULL;
2046 }
2047
2048 /* Copy the new user SID if one has been provided */
2049 if (psid)
2050 {
2052 if (WindowStation->psidUser == NULL)
2053 {
2055 goto Leave;
2056 }
2057
2059 _SEH2_TRY
2060 {
2061 ProbeForRead(psid, size, 1);
2062 RtlCopyMemory(WindowStation->psidUser, psid, size);
2063 }
2065 {
2067 }
2068 _SEH2_END;
2069
2070 if (!NT_SUCCESS(Status))
2071 {
2073 WindowStation->psidUser = NULL;
2074 goto Leave;
2075 }
2076 }
2077
2078 /* Copy the new user LUID */
2079 WindowStation->luidUser = luidUser;
2080
2081 Ret = TRUE;
2082
2083Leave:
2084 if (WindowStation)
2085 ObDereferenceObject(WindowStation);
2086
2087 UserLeave();
2088 return Ret;
2089}
2090
2091/* EOF */
#define NtCurrentPeb()
Definition: FLS.c:22
static HANDLE DirectoryHandle
Definition: ObType.c:48
PRTL_UNICODE_STRING_BUFFER PULONG PULONG Unknown4
#define OBJ_NAME_PATH_SEPARATOR
Definition: arcname_tests.c:25
HWND hWnd
Definition: settings.c:17
LONG NTSTATUS
Definition: precomp.h:26
#define FIXME(fmt,...)
Definition: debug.h:111
#define ERR(fmt,...)
Definition: debug.h:110
#define DBG_DEFAULT_CHANNEL(ch)
Definition: debug.h:103
_Inout_ PFCB _Inout_ PUNICODE_STRING RemainingName
Definition: cdprocs.h:802
Definition: bufpool.h:45
NTSYSAPI BOOLEAN NTAPI RtlCreateUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES IN DWORD IN DWORD IN DWORD IN DWORD Unknown6
Definition: conport.c:40
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES IN DWORD IN DWORD IN DWORD Unknown5
Definition: conport.c:39
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES IN DWORD Unknown3
Definition: conport.c:37
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES ObjectAttributes
Definition: conport.c:36
BOOL UserCreateSystemThread(DWORD Type)
Definition: csr.c:247
static TAGREF LPCWSTR LPDWORD LPVOID lpBuffer
Definition: db.cpp:175
BOOL NTAPI GreSetDCOwner(HDC hdc, ULONG ulOwner)
Definition: dclife.c:455
HDC FASTCALL IntGdiCreateDC(PUNICODE_STRING Driver, PUNICODE_STRING pustrDevice, PVOID pUMdhpdev, CONST PDEVMODEW pdmInit, BOOL CreateAsIC)
Definition: dclife.c:1040
#define BufferSize
Definition: mmc.h:75
#define ERROR_OUTOFMEMORY
Definition: deptool.c:13
#define ERROR_SUCCESS
Definition: deptool.c:10
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define APIENTRY
Definition: api.h:79
#define wcschr
Definition: compat.h:17
#define MAX_PATH
Definition: compat.h:34
#define ERROR_INVALID_HANDLE
Definition: compat.h:98
#define ERROR_ACCESS_DENIED
Definition: compat.h:97
PSERVERINFO gpsi
Definition: imm.c:18
PPEB Peb
Definition: dllmain.c:27
#define SESSION_DIR
Definition: dllmain.c:38
IN CINT OUT PVOID IN ULONG OUT PULONG ReturnLength
Definition: dumpinfo.c:43
#define ExAllocatePoolWithTag(hernya, size, tag)
Definition: env_spec_w32.h:350
#define KeWaitForSingleObject(pEvt, foo, a, b, c)
Definition: env_spec_w32.h:478
#define InitializeListHead(ListHead)
Definition: env_spec_w32.h:944
#define PagedPool
Definition: env_spec_w32.h:308
VOID NTAPI ProbeForRead(IN CONST VOID *Address, IN SIZE_T Length, IN ULONG Alignment)
Definition: exintrin.c:102
VOID NTAPI ProbeForWrite(IN PVOID Address, IN SIZE_T Length, IN ULONG Alignment)
Definition: exintrin.c:143
#define _SEH2_END
Definition: filesup.c:22
#define _SEH2_TRY
Definition: filesup.c:19
#define _SEH2_LEAVE
Definition: filesup.c:20
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
Status
Definition: gdiplustypes.h:25
GLsizeiptr size
Definition: glext.h:5919
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:85
_Check_return_ _CRTIMP int __cdecl _scwprintf(_In_z_ _Printf_format_string_ const wchar_t *_Format,...)
_CRTIMP size_t __cdecl wcslen(_In_z_ const wchar_t *_Str)
struct _PROCESSINFO * GetW32ProcessInfo(VOID)
Definition: misc.c:799
#define PUSIF_PALETTEDISPLAY
Definition: ntuser.h:993
#define OBJ_KERNEL_HANDLE
Definition: winternl.h:231
#define OBJ_CASE_INSENSITIVE
Definition: winternl.h:228
#define OBJ_INHERIT
Definition: winternl.h:225
#define NOTHING
Definition: input_list.c:10
HDC hSystemBM
Definition: stockobj.c:52
#define NtCurrentTeb
static CODE_SEG("PAGE")
Definition: isapnp.c:1482
PMDEVOBJ gpmdev
Definition: mdevobj.c:14
#define MmCopyToCaller(x, y, z)
Definition: mmcopy.h:19
#define ASSERT(a)
Definition: mode.c:44
#define ExFreePoolWithTag(_P, _T)
Definition: module.h:1109
PSDBQUERYRESULT_VISTA PVOID DWORD * dwSize
Definition: env.c:56
HDC hdc
Definition: main.c:9
static HDC
Definition: imagelist.c:92
#define InitializeObjectAttributes(p, n, a, r, s)
Definition: reg.c:106
#define _In_
Definition: ms_sal.h:308
#define KernelMode
Definition: asm.h:34
#define UserMode
Definition: asm.h:35
NTSYSAPI NTSTATUS NTAPI ZwOpenDirectoryObject(_Out_ PHANDLE FileHandle, _In_ ACCESS_MASK DesiredAccess, _In_ POBJECT_ATTRIBUTES ObjectAttributes)
NTSYSAPI NTSTATUS NTAPI ZwClose(_In_ HANDLE Handle)
NTSYSAPI NTSTATUS NTAPI ZwCreateDirectoryObject(_Out_ PHANDLE DirectoryHandle, _In_ ACCESS_MASK DesiredAccess, _In_ POBJECT_ATTRIBUTES ObjectAttributes)
#define OBJECT_HEADER_TO_NAME_INFO(h)
Definition: obtypes.h:114
#define OBJECT_TO_OBJECT_HEADER(o)
Definition: obtypes.h:111
NTSYSAPI NTSTATUS NTAPI RtlDestroyAtomTable(IN PRTL_ATOM_TABLE AtomTable)
Definition: atom.c:203
NTSYSAPI NTSTATUS NTAPI RtlCreateAtomTable(_In_ ULONG TableSize, _Inout_ PRTL_ATOM_TABLE *AtomTable)
NTSYSAPI BOOLEAN NTAPI RtlAreAllAccessesGranted(ACCESS_MASK GrantedAccess, ACCESS_MASK DesiredAccess)
#define DIRECTORY_CREATE_OBJECT
Definition: nt_native.h:1256
ULONG ACCESS_MASK
Definition: nt_native.h:40
#define PAGE_READWRITE
Definition: nt_native.h:1304
#define DIRECTORY_QUERY
Definition: nt_native.h:1254
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
#define FASTCALL
Definition: nt_native.h:50
#define MEM_RELEASE
Definition: nt_native.h:1316
#define DWORD
Definition: nt_native.h:44
#define MEM_COMMIT
Definition: nt_native.h:1313
#define UNICODE_NULL
__kernel_entry W32KAPI HDC APIENTRY NtGdiCreateCompatibleDC(_In_opt_ HDC hdc)
__kernel_entry W32KAPI INT APIENTRY NtGdiGetDeviceCaps(_In_ HDC hdc, _In_ INT i)
__kernel_entry W32KAPI HANDLE APIENTRY NtGdiGetStockObject(_In_ INT iObject)
__kernel_entry W32KAPI HFONT APIENTRY NtGdiSelectFont(_In_ HDC hdc, _In_ HFONT hf)
Definition: dcobjs.c:597
#define GDI_OBJ_HMGR_POWNED
Definition: ntgdihdl.h:117
#define GDI_OBJ_HMGR_PUBLIC
Definition: ntgdihdl.h:116
VOID NTAPI PsSetProcessWindowStation(PEPROCESS Process, PVOID WindowStation)
Definition: process.c:1314
PVOID NTAPI PsGetCurrentProcessWin32Process(VOID)
Definition: process.c:1183
HANDLE NTAPI PsGetCurrentProcessId(VOID)
Definition: process.c:1123
PVOID NTAPI PsGetProcessWin32WindowStation(PEPROCESS Process)
Definition: process.c:1203
PVOID NTAPI PsGetCurrentThreadWin32Thread(VOID)
Definition: thread.c:805
PVOID *typedef PHANDLE
Definition: ntsecpkg.h:455
#define STATUS_INTERNAL_ERROR
Definition: ntstatus.h:465
#define STATUS_INVALID_HANDLE
Definition: ntstatus.h:245
#define STATUS_NO_MORE_ENTRIES
Definition: ntstatus.h:205
#define STATUS_NO_MEMORY
Definition: ntstatus.h:260
#define STATUS_NOT_IMPLEMENTED
Definition: ntstatus.h:239
#define STATUS_OBJECT_PATH_INVALID
Definition: ntstatus.h:293
#define STATUS_NAME_TOO_LONG
Definition: ntstatus.h:498
#define STATUS_OBJECT_TYPE_MISMATCH
Definition: ntstatus.h:273
NTSTRSAFEVAPI RtlStringCbPrintfW(_Out_writes_bytes_(cbDest) _Always_(_Post_z_) NTSTRSAFE_PWSTR pszDest, _In_ size_t cbDest, _In_ _Printf_format_string_ NTSTRSAFE_PCWSTR pszFormat,...)
Definition: ntstrsafe.h:1173
NTSTATUS NTAPI IntWinStaObjectDelete(_In_ PVOID Parameters)
Definition: winsta.c:106
BOOL APIENTRY NtUserLockWorkStation(VOID)
Definition: winsta.c:1972
PWINSTATION_OBJECT InputWindowStation
Definition: winsta.c:21
VOID FASTCALL IntEndDesktopGraphics(VOID)
Definition: winsta.c:358
static VOID FreeUserModeWindowStationName(IN OUT PUNICODE_STRING WindowStationName, IN PUNICODE_STRING TebStaticUnicodeString, IN OUT POBJECT_ATTRIBUTES UserModeObjectAttributes OPTIONAL, IN POBJECT_ATTRIBUTES LocalObjectAttributes OPTIONAL)
Definition: winsta.c:574
NTSTATUS NTAPI IntWinStaOkToClose(_In_ PVOID Parameters)
Definition: winsta.c:203
UNICODE_STRING gustrWindowStationsDir
Definition: winsta.c:27
BOOL APIENTRY NtUserSetProcessWindowStation(HWINSTA hWindowStation)
Definition: winsta.c:1518
NTSTATUS APIENTRY NtUserBuildNameList(HWINSTA hWindowStation, ULONG dwSize, PVOID lpBuffer, PULONG pRequiredSize)
Definition: winsta.c:1937
NTSTATUS NTAPI InitWindowStationImpl(VOID)
Definition: winsta.c:34
HWND hwndSAS
Definition: winsta.c:24
BOOL FASTCALL CheckWinstaAttributeAccess(ACCESS_MASK DesiredAccess)
Definition: winsta.c:377
PWINSTATION_OBJECT FASTCALL IntGetProcessWindowStation(HWINSTA *phWinSta OPTIONAL)
Definition: winsta.c:400
BOOL APIENTRY NtUserSetLogonNotifyWindow(HWND hWnd)
Definition: winsta.c:1953
static NTSTATUS FASTCALL BuildWindowStationNameList(ULONG dwSize, PVOID lpBuffer, PULONG pRequiredSize)
Definition: winsta.c:1622
BOOL APIENTRY NtUserCloseWindowStation(HWINSTA hWinSta)
Definition: winsta.c:1019
HWINSTA APIENTRY NtUserCreateWindowStation(IN POBJECT_ATTRIBUTES ObjectAttributes, IN ACCESS_MASK dwDesiredAccess, DWORD Unknown2, DWORD Unknown3, DWORD Unknown4, DWORD Unknown5, DWORD Unknown6)
Definition: winsta.c:731
BOOL APIENTRY NtUserSetObjectInformation(HANDLE hObject, DWORD nIndex, PVOID pvInformation, DWORD nLength)
Definition: winsta.c:1339
BOOL NTAPI NtUserSetWindowStationUser(IN HWINSTA hWindowStation, IN PLUID pluid, IN PSID psid OPTIONAL, IN DWORD size)
Definition: winsta.c:1995
BOOL APIENTRY NtUserLockWindowStation(HWINSTA hWindowStation)
Definition: winsta.c:1541
static NTSTATUS FASTCALL BuildDesktopNameList(HWINSTA hWindowStation, ULONG dwSize, PVOID lpBuffer, PULONG pRequiredSize)
Definition: winsta.c:1810
static NTSTATUS BuildUserModeWindowStationName(IN OUT POBJECT_ATTRIBUTES UserModeObjectAttributes, IN OUT POBJECT_ATTRIBUTES LocalObjectAttributes, OUT PUNICODE_STRING *WindowStationName, OUT PUNICODE_STRING *TebStaticUnicodeString)
Definition: winsta.c:608
BOOL APIENTRY NtUserUnlockWindowStation(HWINSTA hWindowStation)
Definition: winsta.c:1585
HWINSTA APIENTRY NtUserOpenWindowStation(IN POBJECT_ATTRIBUTES ObjectAttributes, IN ACCESS_MASK dwDesiredAccess)
Definition: winsta.c:872
HWINSTA FASTCALL UserGetProcessWindowStation(VOID)
Definition: winsta.c:1353
HWINSTA APIENTRY NtUserGetProcessWindowStation(VOID)
Definition: winsta.c:1376
NTSTATUS FASTCALL IntCreateWindowStation(OUT HWINSTA *phWinSta, IN POBJECT_ATTRIBUTES ObjectAttributes, IN KPROCESSOR_MODE AccessMode, IN KPROCESSOR_MODE OwnerMode, IN ACCESS_MASK dwDesiredAccess, DWORD Unknown2, DWORD Unknown3, DWORD Unknown4, DWORD Unknown5, DWORD Unknown6)
Definition: winsta.c:447
BOOL FASTCALL co_IntInitializeDesktopGraphics(VOID)
Definition: winsta.c:262
NTSTATUS FASTCALL IntValidateWindowStationHandle(HWINSTA WindowStation, KPROCESSOR_MODE AccessMode, ACCESS_MASK DesiredAccess, PWINSTATION_OBJECT *Object, POBJECT_HANDLE_INFORMATION pObjectHandleInfo)
Definition: winsta.c:232
HDC FASTCALL IntGetScreenDC(VOID)
Definition: winsta.c:371
BOOL APIENTRY NtUserGetObjectInformation(HANDLE hObject, DWORD nIndex, PVOID pvInformation, DWORD nLength, PDWORD nLengthNeeded)
Definition: winsta.c:1099
NTSTATUS NTAPI UserCreateWinstaDirectory(VOID)
Definition: winsta.c:51
NTSTATUS NTAPI IntWinStaObjectParse(_In_ PVOID Parameters)
Definition: winsta.c:138
BOOL FASTCALL UserSetProcessWindowStation(HWINSTA hWindowStation)
Definition: winsta.c:1382
VOID FASTCALL UserLeave(VOID)
Definition: ntuser.c:251
VOID FASTCALL UserEnterExclusive(VOID)
Definition: ntuser.c:242
#define L(x)
Definition: ntvdm.h:50
NTSTATUS NTAPI ObCloseHandle(IN HANDLE Handle, IN KPROCESSOR_MODE AccessMode)
Definition: obhandle.c:3379
NTSTATUS NTAPI ObInsertObject(IN PVOID Object, IN PACCESS_STATE AccessState OPTIONAL, IN ACCESS_MASK DesiredAccess, IN ULONG ObjectPointerBias, OUT PVOID *NewObject OPTIONAL, OUT PHANDLE Handle)
Definition: obhandle.c:2935
NTSTATUS NTAPI ObOpenObjectByName(IN POBJECT_ATTRIBUTES ObjectAttributes, IN POBJECT_TYPE ObjectType, IN KPROCESSOR_MODE AccessMode, IN PACCESS_STATE PassedAccessState, IN ACCESS_MASK DesiredAccess, IN OUT PVOID ParseContext, OUT PHANDLE Handle)
Definition: obhandle.c:2532
NTSTATUS NTAPI ObCreateObject(IN KPROCESSOR_MODE ProbeMode OPTIONAL, IN POBJECT_TYPE Type, IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, IN KPROCESSOR_MODE AccessMode, IN OUT PVOID ParseContext OPTIONAL, IN ULONG ObjectSize, IN ULONG PagedPoolCharge OPTIONAL, IN ULONG NonPagedPoolCharge OPTIONAL, OUT PVOID *Object)
Definition: oblife.c:1039
NTSTATUS NTAPI ObReferenceObjectByHandle(IN HANDLE Handle, IN ACCESS_MASK DesiredAccess, IN POBJECT_TYPE ObjectType, IN KPROCESSOR_MODE AccessMode, OUT PVOID *Object, OUT POBJECT_HANDLE_INFORMATION HandleInformation OPTIONAL)
Definition: obref.c:494
LONG PDEVOBJ_lChangeDisplaySettings(_In_opt_ PUNICODE_STRING pustrDeviceName, _In_opt_ PDEVMODEW RequestedMode, _In_opt_ PMDEVOBJ pmdevOld, _Out_ PMDEVOBJ *ppmdevNew, _In_ BOOL bSearchClosestMode)
Definition: pdevobj.c:849
DWORD * PDWORD
Definition: pedump.c:68
unsigned short USHORT
Definition: pedump.c:61
#define _SEH2_GetExceptionCode()
Definition: pseh2_64.h:159
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:34
#define _SEH2_YIELD(__stmt)
Definition: pseh2_64.h:162
_Check_return_ _CRTIMP int __cdecl _wcsnicmp(_In_reads_or_z_(_MaxCount) const wchar_t *_Str1, _In_reads_or_z_(_MaxCount) const wchar_t *_Str2, _In_ size_t _MaxCount)
#define STATUS_SUCCESS
Definition: shellext.h:65
#define STATUS_BUFFER_TOO_SMALL
Definition: shellext.h:69
HANDLE gpidLogon
Definition: simplecall.c:15
static void Exit(void)
Definition: sock.c:1330
#define TRACE(s)
Definition: solgame.cpp:4
PULONG MinorVersion OPTIONAL
Definition: CrossNt.h:68
WCHAR szDesktopName[1]
Definition: ntuser.h:158
PDESKTOPINFO pDeskInfo
Definition: desktop.h:8
ULONG ulVertRes
Definition: winddi.h:883
ULONG ulHorzRes
Definition: winddi.h:882
WCHAR szWinDeviceName[CCHDEVICENAME/2]
Definition: pdevobj.h:60
Definition: typedefs.h:120
struct _LIST_ENTRY * Flink
Definition: typedefs.h:121
LONG HighPart
DWORD LowPart
PPDEVOBJ ppdevGlobal
Definition: mdevobj.h:16
PUNICODE_STRING ObjectName
Definition: umtypes.h:185
ACCESS_MASK GrantedAccess
Definition: iotypes.h:181
UNICODE_STRING Name
Definition: obtypes.h:433
POBJECT_TYPE Type
Definition: obtypes.h:493
GENERIC_MAPPING GenericMapping
Definition: obtypes.h:358
ULONG DefaultNonPagedPoolCharge
Definition: obtypes.h:365
OBJECT_TYPE_INITIALIZER TypeInfo
Definition: obtypes.h:390
UNICODE_STRING Name
Definition: obtypes.h:383
GDIINFO gdiinfo
Definition: pdevobj.h:123
ULONG SessionId
Definition: btrfs_drv.h:1919
HWINSTA hwinsta
Definition: win32.h:267
ACCESS_MASK amwinsta
Definition: win32.h:268
struct _WINSTATION_OBJECT * prpwinsta
Definition: win32.h:266
Definition: compat.h:836
WCHAR StaticUnicodeBuffer[261]
Definition: compat.h:877
UNICODE_STRING StaticUnicodeString
Definition: compat.h:876
struct _DESKTOP * rpdesk
Definition: win32.h:92
USHORT MaximumLength
Definition: env_spec_w32.h:370
PUNICODE_STRING RemainingName
Definition: pstypes.h:1675
_Out_ PUNICODE_STRING CompleteName
Definition: pstypes.h:1674
PSECURITY_QUALITY_OF_SERVICE SecurityQos
Definition: pstypes.h:1677
KPROCESSOR_MODE AccessMode
Definition: pstypes.h:1672
DWORD dwSessionId
Definition: winsta.h:17
struct tagKL * spklList
Definition: winsta.h:23
PRTL_ATOM_TABLE AtomTable
Definition: winsta.h:20
PVOID psidUser
Definition: winsta.h:39
LIST_ENTRY DesktopListHead
Definition: winsta.h:19
#define RTL_CONSTANT_STRING(s)
Definition: tunneltest.c:14
uint32_t * PULONG
Definition: typedefs.h:59
#define NTAPI
Definition: typedefs.h:36
void * PVOID
Definition: typedefs.h:50
ULONG_PTR SIZE_T
Definition: typedefs.h:80
#define RtlCopyMemory(Destination, Source, Length)
Definition: typedefs.h:263
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
#define MAXUSHORT
Definition: typedefs.h:83
uint32_t ULONG_PTR
Definition: typedefs.h:65
#define IN
Definition: typedefs.h:39
uint16_t * PWCHAR
Definition: typedefs.h:56
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260
uint32_t ULONG
Definition: typedefs.h:59
#define OUT
Definition: typedefs.h:40
char * PCHAR
Definition: typedefs.h:51
#define STATUS_ACCESS_DENIED
Definition: udferr_usr.h:145
#define STATUS_INVALID_PARAMETER
Definition: udferr_usr.h:135
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158
#define ALIGN_UP(size, type)
Definition: umtypes.h:91
#define LN_LOCK_WORKSTATION
Definition: undocuser.h:118
#define WM_LOGONNOTIFY
Definition: undocuser.h:37
#define UserEnterCo
Definition: ntuser.h:3
#define UserLeaveCo
Definition: ntuser.h:4
int ret
_Must_inspect_result_ _In_ WDFCOLLECTION _In_ WDFOBJECT Object
_Must_inspect_result_ _In_ WDFDEVICE _In_ ULONG _In_ ACCESS_MASK DesiredAccess
Definition: wdfdevice.h:2658
_Must_inspect_result_ _In_ WDFQUEUE _In_opt_ WDFREQUEST _In_opt_ WDFFILEOBJECT _Inout_opt_ PWDF_REQUEST_PARAMETERS Parameters
Definition: wdfio.h:869
_In_ WDFMEMORY _Out_opt_ size_t * BufferSize
Definition: wdfmemory.h:254
#define W32PF_IOWINSTA
Definition: win32.h:23
#define W32PF_READSCREENACCESSGRANTED
Definition: win32.h:8
POBJECT_TYPE ExDesktopObjectType
Definition: win32k.c:22
POBJECT_TYPE ExWindowStationObjectType
Definition: win32k.c:21
PGRAPHICS_DEVICE NTAPI EngpFindGraphicsDevice(_In_opt_ PUNICODE_STRING pustrDevice, _In_ ULONG iDevNum)
Definition: device.c:641
VOID FASTCALL SetLastNtError(_In_ NTSTATUS Status)
Definition: error.c:31
BOOL FASTCALL IntCreatePrimarySurface(VOID)
Definition: device.c:17
VOID FASTCALL IntDestroyPrimarySurface(VOID)
Definition: device.c:32
DWORD FASTCALL IntGetCharDimensions(HDC hdc, PTEXTMETRICW ptm, PDWORD height)
Definition: font.c:329
BOOL NTAPI GreDeleteObject(HGDIOBJ hobj)
Definition: gdiobj.c:1158
BOOL APIENTRY co_IntLoadDefaultCursors(VOID)
Definition: callback.c:471
BOOL FASTCALL co_IntSetWndIcons(VOID)
Definition: callback.c:1101
VOID NTAPI UserEmptyClipboardData(PWINSTATION_OBJECT pWinSta)
Definition: clipboard.c:354
#define ST_DESKTOP_THREAD
Definition: csr.h:36
#define ST_RIT
Definition: csr.h:35
BOOL InitCursorImpl(VOID)
Definition: cursoricon.c:64
PDESKTOP FASTCALL IntGetActiveDesktop(VOID)
Definition: desktop.c:1262
PKEVENT gpDesktopThreadStartedEvent
Definition: desktop.c:39
HDC ScreenDeviceContext
Definition: desktop.c:36
NTSTATUS FASTCALL IntHideDesktop(PDESKTOP Desktop)
Definition: desktop.c:1635
NTSTATUS FASTCALL co_IntShowDesktop(PDESKTOP Desktop, ULONG Width, ULONG Height, BOOL bRedraw)
Definition: desktop.c:1617
NTSTATUS FASTCALL IntValidateDesktopHandle(HDESK Desktop, KPROCESSOR_MODE AccessMode, ACCESS_MASK DesiredAccess, PDESKTOP *Object)
Definition: desktop.c:1237
NTSTATUS APIENTRY IntDesktopObjectParse(IN PVOID ParseObject, IN PVOID ObjectType, IN OUT PACCESS_STATE AccessState, IN KPROCESSOR_MODE AccessMode, IN ULONG Attributes, IN OUT PUNICODE_STRING CompleteName, IN OUT PUNICODE_STRING RemainingName, IN OUT PVOID Context OPTIONAL, IN PSECURITY_QUALITY_OF_SERVICE SecurityQos OPTIONAL, OUT PVOID *Object)
Definition: desktop.c:45
BOOL FASTCALL IntPaintDesktop(HDC hDC)
Definition: desktop.c:1835
BOOL MenuInit(VOID)
Definition: menu.c:359
BOOL FASTCALL UserPostMessage(HWND Wnd, UINT Msg, WPARAM wParam, LPARAM lParam)
Definition: message.c:1345
BOOL NTAPI InitMetrics(VOID)
Definition: metric.c:44
NTSTATUS GetProcessLuid(IN PETHREAD Thread OPTIONAL, IN PEPROCESS Process OPTIONAL, OUT PLUID Luid)
Definition: misc.c:813
NTSTATUS NTAPI UserAttachMonitor(IN HDEV hDev)
Definition: monitor.c:129
NTSTATUS NTAPI UserUpdateMonitorSize(IN HDEV hDev)
Definition: monitor.c:225
PVOID FASTCALL UserAssignmentUnlock(PVOID *ppvObj)
Definition: object.c:860
#define WINSTA_WRITE
Definition: security.h:48
#define WINSTA_READ
Definition: security.h:42
#define WINSTA_ACCESS_ALL
Definition: security.h:57
#define WINSTA_EXECUTE
Definition: security.h:53
#define USERTAG_SECURITY
Definition: tags.h:275
#define TAG_WINSTA
Definition: tags.h:11
BOOL FASTCALL IntIsWindow(HWND hWnd)
Definition: window.c:176
struct _WINSTATION_OBJECT WINSTATION_OBJECT
#define WSS_LOCKED
Definition: winsta.h:7
#define WINSTA_OBJ_DIR
Definition: winsta.h:3
struct _WINSTATION_OBJECT * PWINSTATION_OBJECT
#define WSS_DYING
Definition: winsta.h:11
#define WSS_NOIO
Definition: winsta.h:9
_In_ DWORD nLength
Definition: wincon.h:473
ENGAPI VOID APIENTRY EngSetLastError(_In_ ULONG iError)
Definition: error.c:22
_In_ ULONG _In_opt_ PVOID pvData
Definition: winddi.h:3749
#define ERROR_REQUIRES_INTERACTIVE_WINDOWSTATION
Definition: winerror.h:940
#define RASTERCAPS
Definition: wingdi.h:745
#define LOGPIXELSY
Definition: wingdi.h:719
#define PLANES
Definition: wingdi.h:721
#define SYSTEM_FONT
Definition: wingdi.h:911
#define BITSPIXEL
Definition: wingdi.h:720
#define RC_PALETTE
Definition: wingdi.h:790
#define SM_CYSCREEN
Definition: winuser.h:960
#define UOI_NAME
Definition: winuser.h:1084
#define DISP_CHANGE_SUCCESSFUL
Definition: winuser.h:190
#define UOI_TYPE
Definition: winuser.h:1085
#define UOI_USER_SID
Definition: winuser.h:1086
#define WINSTA_READSCREEN
Definition: winuser.h:415
#define WSF_VISIBLE
Definition: winuser.h:2452
#define UOI_FLAGS
Definition: winuser.h:1083
#define SM_CXSCREEN
Definition: winuser.h:959
@ UserRequest
Definition: ketypes.h:421
CCHAR KPROCESSOR_MODE
Definition: ketypes.h:7
_In_ PEPROCESS _In_ KPROCESSOR_MODE AccessMode
Definition: mmfuncs.h:396
#define ObDereferenceObject
Definition: obfuncs.h:203
#define ObReferenceObject
Definition: obfuncs.h:204
#define DUPLICATE_SAME_ACCESS
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define ZwCurrentProcess()