ReactOS 0.4.16-dev-1946-g52006dd
sas.c
Go to the documentation of this file.
1/*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS Winlogon
4 * FILE: base/system/winlogon/sas.c
5 * PURPOSE: Secure Attention Sequence
6 * PROGRAMMERS: Thomas Weidenmueller (w3seek@users.sourceforge.net)
7 * Hervé Poussineau (hpoussin@reactos.org)
8 * Arnav Bhatt (arnavbhatt288@gmail.com)
9 * UPDATE HISTORY:
10 * Created 28/03/2004
11 */
12
13/* INCLUDES *****************************************************************/
14
15#include "winlogon.h"
16
17#define WIN32_LEAN_AND_MEAN
18#include <aclapi.h>
19#include <mmsystem.h>
20#include <userenv.h>
21#include <ndk/setypes.h>
22#include <ndk/sefuncs.h>
23
24/* GLOBALS ******************************************************************/
25
26#define WINLOGON_SAS_CLASS L"SAS Window class"
27#define WINLOGON_SAS_TITLE L"SAS window"
28
29#define IDHK_CTRL_ALT_DEL 0
30#define IDHK_CTRL_SHIFT_ESC 1
31#define IDHK_WIN_L 2
32#define IDHK_WIN_U 3
33
34// #define EWX_FLAGS_MASK 0x00000014
35// #define EWX_ACTION_MASK ~EWX_FLAGS_MASK
36
37// FIXME: At the moment we use this value (select the lowbyte flags and some highbytes ones).
38// It should be set such that it makes winlogon accepting only valid flags.
39#define EWX_ACTION_MASK 0x5C0F
40
42{
46
48
49LUID LuidNone = {0, 0};
50
51typedef struct tagLOGON_SOUND_DATA
52{
56
57/* FUNCTIONS ****************************************************************/
58
59static BOOL
61 IN OUT PWLSESSION Session)
62{
63 LPVOID lpEnvironment;
64 BOOL ret;
65
66 if (!Session->Gina.Functions.WlxStartApplication)
67 return FALSE;
68
70 &lpEnvironment,
71 Session->UserToken,
72 TRUE))
73 {
74 return FALSE;
75 }
76
77 ret = Session->Gina.Functions.WlxStartApplication(
78 Session->Gina.Context,
79 L"Default",
80 lpEnvironment,
81 L"taskmgr.exe");
82
83 DestroyEnvironmentBlock(lpEnvironment);
84 return ret;
85}
86
87static BOOL
89 IN OUT PWLSESSION Session)
90{
91 LPVOID lpEnvironment = NULL;
92 BOOLEAN Old;
93 BOOL ret;
94
95 /* Create environment block for the user */
96 if (!CreateEnvironmentBlock(&lpEnvironment, Session->UserToken, TRUE))
97 {
98 WARN("WL: CreateEnvironmentBlock() failed\n");
99 return FALSE;
100 }
101
102 /* Get privilege */
103 /* FIXME: who should do it? winlogon or gina? */
104 /* FIXME: reverting to lower privileges after creating user shell? */
106
107 ret = Session->Gina.Functions.WlxActivateUserShell(
108 Session->Gina.Context,
109 L"Default",
110 NULL, /* FIXME */
111 lpEnvironment);
112
113 DestroyEnvironmentBlock(lpEnvironment);
114 return ret;
115}
116
117
118BOOL
120 IN PWLSESSION Session)
121{
122 BOOL ret = FALSE;
123 BOOL UserProfile;
124 LONG rc;
125 HKEY UserKey, hKey = NULL;
126 LPCWSTR SubKey, ValueName;
127 DWORD dwType, dwSize;
128 LPWSTR Value = NULL;
129 UNICODE_STRING ValueString;
131 LCID Lcid;
132
133 UserProfile = (Session && Session->UserToken);
134
135 if (UserProfile && !ImpersonateLoggedOnUser(Session->UserToken))
136 {
137 ERR("WL: ImpersonateLoggedOnUser() failed with error %lu\n", GetLastError());
138 return FALSE;
139 // FIXME: ... or use the default language of the system??
140 // UserProfile = FALSE;
141 }
142
143 if (UserProfile)
144 {
145 rc = RegOpenCurrentUser(MAXIMUM_ALLOWED, &UserKey);
146 if (rc != ERROR_SUCCESS)
147 {
148 TRACE("RegOpenCurrentUser() failed with error %lu\n", rc);
149 goto cleanup;
150 }
151
152 SubKey = L"Control Panel\\International";
153 ValueName = L"Locale";
154 }
155 else
156 {
157 UserKey = NULL;
158 SubKey = L"System\\CurrentControlSet\\Control\\Nls\\Language";
159 ValueName = L"Default";
160 }
161
162 rc = RegOpenKeyExW(UserKey ? UserKey : HKEY_LOCAL_MACHINE,
163 SubKey,
164 0,
165 KEY_READ,
166 &hKey);
167
168 if (UserKey)
169 RegCloseKey(UserKey);
170
171 if (rc != ERROR_SUCCESS)
172 {
173 TRACE("RegOpenKeyEx() failed with error %lu\n", rc);
174 goto cleanup;
175 }
176
178 ValueName,
179 NULL,
180 &dwType,
181 NULL,
182 &dwSize);
183 if (rc != ERROR_SUCCESS)
184 {
185 TRACE("RegQueryValueEx() failed with error %lu\n", rc);
186 goto cleanup;
187 }
188 else if (dwType != REG_SZ)
189 {
190 TRACE("Wrong type for %S\\%S registry entry (got 0x%lx, expected 0x%x)\n",
191 SubKey, ValueName, dwType, REG_SZ);
192 goto cleanup;
193 }
194
196 if (!Value)
197 {
198 TRACE("HeapAlloc() failed\n");
199 goto cleanup;
200 }
202 ValueName,
203 NULL,
204 NULL,
205 (LPBYTE)Value,
206 &dwSize);
207 if (rc != ERROR_SUCCESS)
208 {
209 TRACE("RegQueryValueEx() failed with error %lu\n", rc);
210 goto cleanup;
211 }
212
213 /* Convert Value to a Lcid */
214 ValueString.Length = ValueString.MaximumLength = (USHORT)dwSize;
215 ValueString.Buffer = Value;
216 Status = RtlUnicodeStringToInteger(&ValueString, 16, (PULONG)&Lcid);
217 if (!NT_SUCCESS(Status))
218 {
219 TRACE("RtlUnicodeStringToInteger() failed with status 0x%08lx\n", Status);
220 goto cleanup;
221 }
222
223 TRACE("%s language is 0x%08lx\n",
224 UserProfile ? "User" : "System", Lcid);
225 Status = NtSetDefaultLocale(UserProfile, Lcid);
226 if (!NT_SUCCESS(Status))
227 {
228 TRACE("NtSetDefaultLocale() failed with status 0x%08lx\n", Status);
229 goto cleanup;
230 }
231
232 ret = TRUE;
233
234cleanup:
235 if (Value)
237
238 if (hKey)
240
241 if (UserProfile)
242 RevertToSelf();
243
244 return ret;
245}
246
247BOOL
250 IN UINT bLogon,
251 IN UINT Flags)
252{
253 typedef BOOL (WINAPI *PLAYSOUNDW)(LPCWSTR,HMODULE,DWORD);
254 typedef UINT (WINAPI *WAVEOUTGETNUMDEVS)(VOID);
255 PLAYSOUNDW Play;
256 WAVEOUTGETNUMDEVS waveOutGetNumDevs;
257 UINT NumDevs;
259 BOOL Ret = FALSE;
260
261 hLibrary = LoadLibraryW(L"winmm.dll");
262 if (!hLibrary)
263 return FALSE;
264
265 waveOutGetNumDevs = (WAVEOUTGETNUMDEVS)GetProcAddress(hLibrary, "waveOutGetNumDevs");
266 Play = (PLAYSOUNDW)GetProcAddress(hLibrary, "PlaySoundW");
267
269 {
271 {
272 NumDevs = waveOutGetNumDevs();
273 if (!NumDevs)
274 {
275 if (!bLogon)
276 Beep(440, 125);
278 }
279 }
280
281 if (Play)
282 Ret = Play(FileName, NULL, Flags);
283 }
285 {
286 ERR("WL: Exception while playing sound '%S', Status 0x%08lx\n",
288 }
289 _SEH2_END;
290
292
293 return Ret;
294}
295
296static
297DWORD
298WINAPI
300 _In_ LPVOID lpParameter)
301{
302 PLOGON_SOUND_DATA SoundData = (PLOGON_SOUND_DATA)lpParameter;
305 ULONG Index = 0;
306 SC_HANDLE hSCManager, hService;
307
308 /* Open the service manager */
310 if (!hSCManager)
311 {
312 ERR("OpenSCManager failed (%x)\n", GetLastError());
313 goto Cleanup;
314 }
315
316 /* Open the wdmaud service */
317 hService = OpenServiceW(hSCManager, L"wdmaud", GENERIC_READ);
318 if (!hService)
319 {
320 /* The service is not installed */
321 TRACE("Failed to open wdmaud service (%x)\n", GetLastError());
323 goto Cleanup;
324 }
325
326 /* Wait for wdmaud to start */
327 do
328 {
330 {
331 TRACE("QueryServiceStatusEx failed (%x)\n", GetLastError());
332 break;
333 }
334
335 if (Info.dwCurrentState == SERVICE_RUNNING)
336 break;
337
338 Sleep(1000);
339
340 } while (Index++ < 20);
341
342 CloseServiceHandle(hService);
344
345 /* If wdmaud is not running exit */
346 if (Info.dwCurrentState != SERVICE_RUNNING)
347 {
348 WARN("wdmaud has not started!\n");
349 goto Cleanup;
350 }
351
352 /* Sound subsystem is running. Play logon sound. */
353 TRACE("Playing %s sound\n", SoundData->IsStartup ? "startup" : "logon");
354 if (!ImpersonateLoggedOnUser(SoundData->UserToken))
355 {
356 ERR("ImpersonateLoggedOnUser failed (%x)\n", GetLastError());
357 }
358 else
359 {
360 PlaySoundRoutine(SoundData->IsStartup ? L"SystemStart" : L"WindowsLogon",
361 TRUE,
363 RevertToSelf();
364 }
365
366Cleanup:
367 HeapFree(GetProcessHeap(), 0, SoundData);
368 return 0;
369}
370
371static
372VOID
374 _In_ PWLSESSION Session)
375{
376 PLOGON_SOUND_DATA SoundData;
378
379 SoundData = HeapAlloc(GetProcessHeap(), 0, sizeof(LOGON_SOUND_DATA));
380 if (!SoundData)
381 return;
382
383 SoundData->UserToken = Session->UserToken;
384 SoundData->IsStartup = IsFirstLogon(Session);
385
386 hThread = CreateThread(NULL, 0, PlayLogonSoundThread, SoundData, 0, NULL);
387 if (!hThread)
388 {
389 HeapFree(GetProcessHeap(), 0, SoundData);
390 return;
391 }
393}
394
395static
396VOID
398 _In_ PWLSESSION Session,
400{
401 if (!ImpersonateLoggedOnUser(Session->UserToken))
402 return;
403
404 /* NOTE: Logoff and shutdown sounds play synchronously */
405 PlaySoundRoutine(bShutdown ? L"SystemExit" : L"WindowsLogoff",
406 FALSE,
408
409 RevertToSelf();
410}
411
412static
413BOOL
415 _In_ PWLSESSION Session,
416 _In_ LPCWSTR EventName)
417{
418 BOOL bRet;
419
420 if (!ImpersonateLoggedOnUser(Session->UserToken))
421 return FALSE;
422
424
425 RevertToSelf();
426
427 return bRet;
428}
429
430static
431VOID
433 _In_ PWLSESSION Session)
434{
435 DWORD dRet;
436 HANDLE hEnum;
437 LPNETRESOURCE lpRes;
438 DWORD dSize = 0x1000;
439 DWORD dCount = -1;
440 LPNETRESOURCE lpCur;
441 BOOL UserProfile;
442
443 UserProfile = (Session && Session->UserToken);
444 if (!UserProfile)
445 return;
446
447 if (!ImpersonateLoggedOnUser(Session->UserToken))
448 {
449 ERR("WL: ImpersonateLoggedOnUser() failed with error %lu\n", GetLastError());
450 return;
451 }
452
454 if (dRet != WN_SUCCESS)
455 {
456 ERR("Failed to open enumeration: %lu\n", dRet);
457 goto quit;
458 }
459
460 lpRes = HeapAlloc(GetProcessHeap(), 0, dSize);
461 if (!lpRes)
462 {
463 ERR("Failed to allocate memory\n");
464 WNetCloseEnum(hEnum);
465 goto quit;
466 }
467
468 do
469 {
470 dSize = 0x1000;
471 dCount = -1;
472
473 ZeroMemory(lpRes, dSize);
474 dRet = WNetEnumResource(hEnum, &dCount, lpRes, &dSize);
475 if (dRet == WN_SUCCESS || dRet == WN_MORE_DATA)
476 {
477 lpCur = lpRes;
478 for (; dCount; dCount--)
479 {
481 lpCur++;
482 }
483 }
484 } while (dRet != WN_NO_MORE_ENTRIES);
485
486 HeapFree(GetProcessHeap(), 0, lpRes);
487 WNetCloseEnum(hEnum);
488
489quit:
490 RevertToSelf();
491}
492
493static
494VOID
496 _In_ PWLSESSION Session)
497{
498 if (!Session->UserToken || !ImpersonateLoggedOnUser(Session->UserToken))
499 return;
501 RevertToSelf();
502}
503
509static VOID
511 _Inout_ PVOID Profile)
512{
513 PWLX_PROFILE_V2_0 pProfile = (PWLX_PROFILE_V2_0)Profile;
514
515 if (pProfile->dwType != WLX_PROFILE_TYPE_V1_0
516 && pProfile->dwType != WLX_PROFILE_TYPE_V2_0)
517 {
518 ERR("WL: Wrong profile info\n");
519 return;
520 }
521
522 if (pProfile->pszProfile)
523 LocalFree(pProfile->pszProfile);
524 if (pProfile->dwType >= WLX_PROFILE_TYPE_V2_0)
525 {
526 if (pProfile->pszPolicy)
527 LocalFree(pProfile->pszPolicy);
528 if (pProfile->pszNetworkDefaultUserProfile)
530 if (pProfile->pszServerName)
531 LocalFree(pProfile->pszServerName);
532 if (pProfile->pszEnvironment)
533 LocalFree(pProfile->pszEnvironment);
534 }
535}
536
545static VOID
547 _Inout_ PWLX_MPR_NOTIFY_INFO MprNotifyInfo)
548{
549 if (MprNotifyInfo->pszUserName)
550 LocalFree(MprNotifyInfo->pszUserName);
551 if (MprNotifyInfo->pszDomain)
552 LocalFree(MprNotifyInfo->pszDomain);
553 if (MprNotifyInfo->pszPassword)
554 {
555 /* Zero out the password buffer before freeing it */
556 SIZE_T pwdLen = (wcslen(MprNotifyInfo->pszPassword) + 1) * sizeof(WCHAR);
557 SecureZeroMemory(MprNotifyInfo->pszPassword, pwdLen);
558 LocalFree(MprNotifyInfo->pszPassword);
559 }
560 if (MprNotifyInfo->pszOldPassword)
561 {
562 /* Zero out the password buffer before freeing it */
563 SIZE_T pwdLen = (wcslen(MprNotifyInfo->pszOldPassword) + 1) * sizeof(WCHAR);
564 SecureZeroMemory(MprNotifyInfo->pszOldPassword, pwdLen);
565 LocalFree(MprNotifyInfo->pszOldPassword);
566 }
567}
568
569static
570BOOL
572 IN OUT PWLSESSION Session)
573{
574 BOOL ret = FALSE;
575
576 /* Loading personal settings */
577 DisplayStatusMessage(Session, Session->WinlogonDesktop, IDS_LOADINGYOURPERSONALSETTINGS);
578
579 Session->hProfileInfo = NULL;
580 if (!(Session->Options & WLX_LOGON_OPT_NO_PROFILE))
581 {
582 HKEY hKey;
583 LONG lError;
584 BOOL bNoPopups = FALSE;
585 PROFILEINFOW ProfileInfo;
586
587 if (Session->Profile == NULL
588 || (Session->Profile->dwType != WLX_PROFILE_TYPE_V1_0
589 && Session->Profile->dwType != WLX_PROFILE_TYPE_V2_0))
590 {
591 ERR("WL: Wrong profile\n");
592 goto cleanup;
593 }
594
595 /* Check whether error messages may be displayed when loading the user profile */
597 L"System\\CurrentControlSet\\Control\\Windows",
598 0,
600 &hKey);
601 if (lError == ERROR_SUCCESS)
602 {
603 DWORD dwValue, dwType, cbData = sizeof(dwValue);
604 lError = RegQueryValueExW(hKey, L"NoPopupsOnBoot", NULL,
605 &dwType, (PBYTE)&dwValue, &cbData);
606 if ((lError == ERROR_SUCCESS) && (dwType == REG_DWORD) && (cbData == sizeof(dwValue)))
607 bNoPopups = !!dwValue;
608
610 }
611
612 /* Load the user profile */
613 ZeroMemory(&ProfileInfo, sizeof(ProfileInfo));
614 ProfileInfo.dwSize = sizeof(ProfileInfo);
615 if (bNoPopups)
616 ProfileInfo.dwFlags |= PI_NOUI;
617 ProfileInfo.lpUserName = Session->MprNotifyInfo.pszUserName;
618 ProfileInfo.lpProfilePath = Session->Profile->pszProfile;
619 if (Session->Profile->dwType >= WLX_PROFILE_TYPE_V2_0)
620 {
621 ProfileInfo.lpDefaultPath = Session->Profile->pszNetworkDefaultUserProfile;
622 ProfileInfo.lpServerName = Session->Profile->pszServerName;
623 ProfileInfo.lpPolicyPath = Session->Profile->pszPolicy;
624 }
625
626 if (!LoadUserProfileW(Session->UserToken, &ProfileInfo))
627 {
628 ERR("WL: LoadUserProfileW() failed\n");
629 goto cleanup;
630 }
631 Session->hProfileInfo = ProfileInfo.hProfile;
632 }
633
634 /* Cache the username and domain */
635 Session->UserName = WlStrDup(Session->MprNotifyInfo.pszUserName);
636 Session->Domain = WlStrDup(Session->MprNotifyInfo.pszDomain);
637
638 /* Create environment block for the user */
639 if (!CreateUserEnvironment(Session))
640 {
641 WARN("WL: CreateUserEnvironment() failed\n");
642 goto cleanup;
643 }
644
645 /* Enable per-user settings */
646 DisplayStatusMessage(Session, Session->WinlogonDesktop, IDS_APPLYINGYOURPERSONALSETTINGS);
648
649 /* Set default user language */
650 if (!SetDefaultLanguage(Session))
651 {
652 WARN("WL: SetDefaultLanguage() failed\n");
653 goto cleanup;
654 }
655
656 /* Allow winsta and desktop access for this session */
657 if (!AllowAccessOnSession(Session))
658 {
659 WARN("WL: AllowAccessOnSession() failed to give winsta & desktop access for this session\n");
660 goto cleanup;
661 }
662
664
665 /* Connect remote resources */
666 RestoreAllConnections(Session);
667
668 /* Start the user shell */
670 if (!StartUserShell(Session))
671 {
672 //WCHAR StatusMsg[256];
673 WARN("WL: WlxActivateUserShell() failed\n");
674 //LoadStringW(hAppInstance, IDS_FAILEDACTIVATEUSERSHELL, StatusMsg, ARRAYSIZE(StatusMsg));
675 //MessageBoxW(0, StatusMsg, NULL, MB_ICONERROR);
676 goto cleanup;
677 }
679
680 if (!InitializeScreenSaver(Session))
681 WARN("WL: Failed to initialize screen saver\n");
682
683 /* Logon has succeeded. Play sound. */
684 PlayLogonSound(Session);
685
686 /* NOTE: The logon timestamp has to be set after calling PlayLogonSound
687 * to correctly detect the startup event (first logon) */
688 SetLogonTimestamp(Session);
689 ret = TRUE;
690
691cleanup:
692 if (Session->Profile)
693 {
694 FreeWlxProfileInfo(Session->Profile);
695 LocalFree(Session->Profile);
696 Session->Profile = NULL;
697 }
698 FreeWlxMprInfo(&Session->MprNotifyInfo);
699 ZeroMemory(&Session->MprNotifyInfo, sizeof(Session->MprNotifyInfo));
700
701 RemoveStatusMessage(Session);
702
703 if (!ret)
704 {
705 RtlFreeHeap(RtlGetProcessHeap(), 0, Session->UserName);
706 RtlFreeHeap(RtlGetProcessHeap(), 0, Session->Domain);
707 Session->UserName = Session->Domain = NULL;
708
709 if (Session->hProfileInfo)
710 UnloadUserProfile(Session->UserToken, Session->hProfileInfo);
711 Session->hProfileInfo = NULL;
712
713 /* Restore default system parameters */
715
716 // TODO: Remove session access to window station
717 // (revert what security.c!AllowAccessOnSession() does).
718 SetWindowStationUser(Session->InteractiveWindowStation,
719 &LuidNone, NULL, 0);
720
721 /* Switch back to default SYSTEM user */
722 CloseHandle(Session->UserToken);
723 Session->UserToken = NULL;
724 Session->LogonId = LuidNone;
725 }
726 else // if (ret)
727 {
728 SwitchDesktop(Session->ApplicationDesktop);
729 Session->LogonState = STATE_LOGGED_ON;
730 }
731 return ret;
732}
733
734
735static
736DWORD
737WINAPI
740{
742 HANDLE UserToken = LSData->Session->UserToken;
743 DWORD ret = TRUE;
744 UINT uFlags;
745
746 if (UserToken && !ImpersonateLoggedOnUser(UserToken))
747 {
748 ERR("ImpersonateLoggedOnUser() failed with error %lu\n", GetLastError());
749 return FALSE;
750 }
751
752 // FIXME: To be really fixed: need to check what needs to be kept and what needs to be removed there.
753 //
754 // uFlags = EWX_INTERNAL_KILL_USER_APPS | (LSData->Flags & EWX_FLAGS_MASK) |
755 // ((LSData->Flags & EWX_ACTION_MASK) == EWX_LOGOFF ? EWX_CALLER_WINLOGON_LOGOFF : 0);
756
757 uFlags = EWX_CALLER_WINLOGON | (LSData->Flags & 0x0F);
758
759 TRACE("In LogoffShutdownThread with uFlags == 0x%x; exit_in_progress == %s\n",
760 uFlags, ExitReactOSInProgress ? "TRUE" : "FALSE");
761
763
764 /* Close processes of the interactive user */
765 if (!ExitWindowsEx(uFlags, 0))
766 {
767 ERR("Unable to kill user apps, error %lu\n", GetLastError());
768 ret = FALSE;
769 }
770
771 if (UserToken)
772 RevertToSelf();
773
774 return ret;
775}
776
777static
780 _In_ PWLSESSION Session,
782 _In_ DWORD wlxAction)
783{
784 PCSTR pDescName;
787 DWORD dwExitCode;
788
789 /* Validate the action */
790 if (WLX_LOGGINGOFF(wlxAction))
791 {
792 pDescName = "Logoff";
793 }
794 else if (WLX_SHUTTINGDOWN(wlxAction))
795 {
796 pDescName = "Shutdown";
797 }
798 else
799 {
800 ASSERT(FALSE);
802 }
803
804 /* Prepare data for the logoff/shutdown thread */
805 LSData = HeapAlloc(GetProcessHeap(), 0, sizeof(*LSData));
806 if (!LSData)
807 {
808 ERR("Failed to allocate %s thread data\n", pDescName);
809 return STATUS_NO_MEMORY;
810 }
811
812 /* Set the flags accordingly */
813 if (WLX_LOGGINGOFF(wlxAction))
814 {
815 LSData->Flags = EWX_LOGOFF;
816 if (wlxAction == WLX_SAS_ACTION_FORCE_LOGOFF)
817 LSData->Flags |= EWX_FORCE;
818 }
819 else // if (WLX_SHUTTINGDOWN(wlxAction))
820 {
821 /* Because we are shutting down the OS, force processes termination too */
822 LSData->Flags = EWX_SHUTDOWN | EWX_FORCE;
823 if (wlxAction == WLX_SAS_ACTION_SHUTDOWN_POWER_OFF)
824 LSData->Flags |= EWX_POWEROFF;
825 else if (wlxAction == WLX_SAS_ACTION_SHUTDOWN_REBOOT)
826 LSData->Flags |= EWX_REBOOT;
827 }
828
829 LSData->Session = Session;
830
831 /* Run the logoff/shutdown thread */
833 if (!hThread)
834 {
835 ERR("Unable to create %s thread, error %lu\n", pDescName, GetLastError());
836 HeapFree(GetProcessHeap(), 0, LSData);
837 return STATUS_UNSUCCESSFUL;
838 }
840 HeapFree(GetProcessHeap(), 0, LSData);
841 if (!GetExitCodeThread(hThread, &dwExitCode))
842 {
843 ERR("Unable to get %s thread exit code (error %lu)\n", pDescName, GetLastError());
845 return STATUS_UNSUCCESSFUL;
846 }
848 if (dwExitCode == 0)
849 {
850 ERR("%s thread returned failure\n", pDescName);
851 return STATUS_UNSUCCESSFUL;
852 }
853 return STATUS_SUCCESS;
854}
855
856static
857DWORD
858WINAPI
861{
862 HANDLE UserToken = (HANDLE)Parameter;
863 DWORD ret = TRUE;
864
865 TRACE("In KillComProcesses\n");
866
867 if (UserToken && !ImpersonateLoggedOnUser(UserToken))
868 {
869 ERR("ImpersonateLoggedOnUser() failed with error %lu\n", GetLastError());
870 return FALSE;
871 }
872
873 /* Attempt to kill remaining processes. No notifications needed. */
875 {
876 ERR("Unable to kill COM apps, error %lu\n", GetLastError());
877 ret = FALSE;
878 }
879
880 if (UserToken)
881 RevertToSelf();
882
883 return ret;
884}
885
886
887static
891{
892 /* The following code is not working yet and messy */
893 /* Still, it gives some ideas about data types and functions involved and */
894 /* required to set up a SECURITY_DESCRIPTOR for a SECURITY_ATTRIBUTES */
895 /* instance for a thread, to allow that thread to ImpersonateLoggedOnUser(). */
896 /* Specifically THREAD_SET_THREAD_TOKEN is required. */
899 BYTE* pMem;
900 PACL pACL;
901 EXPLICIT_ACCESS Access;
902 PSID pEveryoneSID = NULL;
904
905 *ppsa = NULL;
906
907 // Let's first try to enumerate what kind of data we need for this to ever work:
908 // 1. The Winlogon SID, to be able to give it THREAD_SET_THREAD_TOKEN.
909 // 2. The users SID (the user trying to logoff, or rather shut down the system).
910 // 3. At least two EXPLICIT_ACCESS instances:
911 // 3.1 One for Winlogon itself, giving it the rights
912 // required to THREAD_SET_THREAD_TOKEN (as it's needed to successfully call
913 // ImpersonateLoggedOnUser).
914 // 3.2 One for the user, to allow *that* thread to perform its work.
915 // 4. An ACL to hold the these EXPLICIT_ACCESS ACE's.
916 // 5. A SECURITY_DESCRIPTOR to hold the ACL, and finally.
917 // 6. A SECURITY_ATTRIBUTES instance to pull all of this required stuff
918 // together, to hand it to CreateThread.
919 //
920 // However, it seems struct LOGOFF_SHUTDOWN_DATA doesn't contain
921 // these required SID's, why they'd have to be added.
922 // The Winlogon's own SID should probably only be created once,
923 // while the user's SID obviously must be created for each new user.
924 // Might as well store it when the user logs on?
925
927 1,
929 0, 0, 0, 0, 0, 0, 0,
930 &pEveryoneSID))
931 {
932 ERR("Failed to initialize security descriptor for logoff thread!\n");
933 return STATUS_UNSUCCESSFUL;
934 }
935
936 /* set up the required security attributes to be able to shut down */
937 /* To save space and time, allocate a single block of memory holding */
938 /* both SECURITY_ATTRIBUTES and SECURITY_DESCRIPTOR */
939 pMem = HeapAlloc(GetProcessHeap(),
940 0,
941 sizeof(SECURITY_ATTRIBUTES) +
943 sizeof(ACL));
944 if (!pMem)
945 {
946 ERR("Failed to allocate memory for logoff security descriptor!\n");
947 return STATUS_NO_MEMORY;
948 }
949
950 /* Note that the security descriptor needs to be in _absolute_ format, */
951 /* meaning its members must be pointers to other structures, rather */
952 /* than the relative format using offsets */
956
957 // Initialize an EXPLICIT_ACCESS structure for an ACE.
958 // The ACE will allow this thread to log off (and shut down the system, currently).
959 ZeroMemory(&Access, sizeof(Access));
961 Access.grfAccessMode = SET_ACCESS; // GRANT_ACCESS?
965 Access.Trustee.ptstrName = pEveryoneSID;
966
967 if (SetEntriesInAcl(1, &Access, NULL, &pACL) != ERROR_SUCCESS)
968 {
969 ERR("Failed to set Access Rights for logoff thread. Logging out will most likely fail.\n");
970
971 HeapFree(GetProcessHeap(), 0, pMem);
972 return STATUS_UNSUCCESSFUL;
973 }
974
976 {
977 ERR("Failed to initialize security descriptor for logoff thread!\n");
978 HeapFree(GetProcessHeap(), 0, pMem);
979 return STATUS_UNSUCCESSFUL;
980 }
981
983 TRUE, // bDaclPresent flag
984 pACL,
985 FALSE)) // not a default DACL
986 {
987 ERR("SetSecurityDescriptorDacl Error %lu\n", GetLastError());
988 HeapFree(GetProcessHeap(), 0, pMem);
989 return STATUS_UNSUCCESSFUL;
990 }
991
992 psa->nLength = sizeof(SECURITY_ATTRIBUTES);
993 psa->lpSecurityDescriptor = SecurityDescriptor;
994 psa->bInheritHandle = FALSE;
995
996 *ppsa = psa;
997
998 return STATUS_SUCCESS;
999}
1000
1001static
1002VOID
1005{
1006 if (psa)
1007 {
1009 }
1010}
1011
1012
1013static
1016 _Inout_ PWLSESSION Session,
1017 _In_ DWORD wlxAction)
1018{
1022
1024 if (!NT_SUCCESS(Status))
1025 {
1026 ERR("Failed to create Logoff security descriptor. Status 0x%08lx\n", Status);
1027 return Status;
1028 }
1029
1030 /* Run the Logoff thread. Log off as well if we are
1031 * invoked as part of a shutdown operation. */
1033 WLX_LOGGINGOFF(wlxAction)
1034 ? wlxAction
1036 if (!NT_SUCCESS(Status))
1037 {
1038 ERR("Failed to start the Logoff thread, Status 0x%08lx\n", Status);
1040 return Status;
1041 }
1042
1043 /* Invoke Logoff notifications on the application desktop */
1044 SwitchDesktop(Session->ApplicationDesktop);
1045 DisplayStatusMessage(Session, Session->ApplicationDesktop, IDS_LOGGINGOFF);
1047 RemoveStatusMessage(Session);
1048
1049 /* The remaining Logoff steps run on the Winlogon desktop */
1050 SwitchDesktop(Session->WinlogonDesktop);
1051
1052 PlayLogoffShutdownSound(Session, WLX_SHUTTINGDOWN(wlxAction));
1053
1054 /* Close all user network connections */
1055 DisplayStatusMessage(Session, Session->WinlogonDesktop, IDS_CLOSINGNETWORKCONNECTIONS);
1056 CloseAllConnections(Session);
1057 // TODO: Do any other user-specific network-related cleaning:
1058 // user-added NetAPI message aliases; user cached credentials (remote login)...
1059
1060 SetWindowStationUser(Session->InteractiveWindowStation,
1061 &LuidNone, NULL, 0);
1062
1063 /* Kill remaining COM processes that may have been started by logoff scripts */
1064 hThread = CreateThread(psa, 0, KillComProcesses, (PVOID)Session->UserToken, 0, NULL);
1065 if (hThread)
1066 {
1069 }
1070
1071 /* We're done with the SECURITY_DESCRIPTOR */
1073
1074 DisplayStatusMessage(Session, Session->WinlogonDesktop, IDS_SAVEYOURSETTINGS);
1075
1076 RtlFreeHeap(RtlGetProcessHeap(), 0, Session->UserName);
1077 RtlFreeHeap(RtlGetProcessHeap(), 0, Session->Domain);
1078 Session->UserName = Session->Domain = NULL;
1079
1080 if (Session->hProfileInfo)
1081 UnloadUserProfile(Session->UserToken, Session->hProfileInfo);
1082 Session->hProfileInfo = NULL;
1083
1084 /* Restore default system parameters */
1086
1087 // TODO: Remove session access to window station
1088 // (revert what security.c!AllowAccessOnSession() does).
1089
1090 /* Switch back to default SYSTEM user */
1091 CloseHandle(Session->UserToken);
1092 Session->UserToken = NULL;
1093 Session->LogonId = LuidNone;
1094
1095 Session->LogonState = STATE_LOGGED_OFF;
1096
1097 return STATUS_SUCCESS;
1098}
1099
1100static
1101INT_PTR
1104 IN HWND hwndDlg,
1105 IN UINT uMsg,
1108{
1110
1111 switch (uMsg)
1112 {
1113 case WM_COMMAND:
1114 {
1115 switch (LOWORD(wParam))
1116 {
1119 return TRUE;
1120 }
1121 break;
1122 }
1123 case WM_INITDIALOG:
1124 {
1125 /* Remove the Close menu item */
1127 return TRUE;
1128 }
1129 }
1130 return FALSE;
1131}
1132
1133static
1134VOID
1136 IN OUT PWLSESSION Session)
1137{
1138 if (Session->SASWindow)
1139 {
1140 DestroyWindow(Session->SASWindow);
1141 Session->SASWindow = NULL;
1142 }
1143 if (Session->hEndOfScreenSaverThread)
1144 SetEvent(Session->hEndOfScreenSaverThread);
1146}
1147
1150 IN OUT PWLSESSION Session,
1151 IN DWORD wlxAction)
1152{
1154 UINT uMsgId;
1155 BOOLEAN Old;
1156
1157 /* Display the appropriate shutdown or reboot message */
1158 if (wlxAction == WLX_SAS_ACTION_SHUTDOWN_REBOOT)
1159 uMsgId = IDS_REACTOSISRESTARTING;
1160 else
1162
1163 // SwitchDesktop(Session->WinlogonDesktop);
1164 DisplayStatusMessage(Session, Session->WinlogonDesktop, uMsgId);
1165
1166 /* Invoke Shutdown notifications and notify GINA */
1168 Session->Gina.Functions.WlxShutdown(Session->Gina.Context, wlxAction);
1169
1170 /* Run the shutdown thread. *IGNORE* all failures as we want to force shutting down! */
1171 Status = RunLogoffShutdownThread(Session, NULL, wlxAction);
1172 if (!NT_SUCCESS(Status))
1173 ERR("Failed to start the Shutdown thread, Status 0x%08lx\n", Status);
1174
1175 /* Show again the shutdown message */
1176 // SwitchDesktop(Session->WinlogonDesktop); // Re-enable if you notice the desktop may have switched to something else.
1177 DisplayStatusMessage(Session, Session->WinlogonDesktop, uMsgId);
1178
1179 /* Destroy SAS window */
1180 UninitializeSAS(Session);
1181
1182 /* Now we can shut down NT */
1183 ERR("Shutting down NT...\n");
1185 if (wlxAction == WLX_SAS_ACTION_SHUTDOWN_REBOOT)
1186 {
1188 }
1189 else
1190 {
1191 if (FALSE)
1192 {
1193 /* FIXME - only show this dialog if it's a shutdown and the computer doesn't support APM */
1196 }
1197 if (wlxAction == WLX_SAS_ACTION_SHUTDOWN_POWER_OFF)
1199 else // if (wlxAction == WLX_SAS_ACTION_SHUTDOWN)
1201 }
1203 return STATUS_SUCCESS;
1204}
1205
1206static
1207VOID
1209 IN OUT PWLSESSION Session,
1210 IN DWORD wlxAction)
1211{
1212 switch (wlxAction)
1213 {
1214 case WLX_SAS_ACTION_LOGON: /* 0x01 */
1215 if (Session->LogonState == STATE_LOGGED_OFF_SAS)
1216 {
1217 if (!HandleLogon(Session))
1218 {
1219 Session->LogonState = STATE_LOGGED_OFF;
1220 Session->Gina.Functions.WlxDisplaySASNotice(Session->Gina.Context);
1221 }
1222 }
1223 break;
1224 case WLX_SAS_ACTION_NONE: /* 0x02 */
1225 if (Session->LogonState == STATE_LOGGED_OFF_SAS)
1226 {
1227 Session->LogonState = STATE_LOGGED_OFF;
1228 Session->Gina.Functions.WlxDisplaySASNotice(Session->Gina.Context);
1229 }
1230 else if (Session->LogonState == STATE_LOGGED_ON_SAS)
1231 {
1232 Session->LogonState = STATE_LOGGED_ON;
1233 }
1234 else if (Session->LogonState == STATE_LOCKED_SAS)
1235 {
1236 Session->LogonState = STATE_LOCKED;
1237 Session->Gina.Functions.WlxDisplayLockedNotice(Session->Gina.Context);
1238 }
1239 break;
1240 case WLX_SAS_ACTION_LOCK_WKSTA: /* 0x03 */
1241 if ((Session->LogonState == STATE_LOGGED_ON) ||
1242 (Session->LogonState == STATE_LOGGED_ON_SAS))
1243 {
1244 if (Session->Gina.Functions.WlxIsLockOk(Session->Gina.Context))
1245 {
1246 Session->LogonState = STATE_LOCKED;
1247 SwitchDesktop(Session->WinlogonDesktop);
1248 /* We may be on the Logged-On SAS dialog, in which case
1249 * we need to close it if the lock action came via Win-L */
1252 Session->Gina.Functions.WlxDisplayLockedNotice(Session->Gina.Context);
1253 }
1254 }
1255 break;
1256 case WLX_SAS_ACTION_LOGOFF: /* 0x04 */
1257 case WLX_SAS_ACTION_SHUTDOWN: /* 0x05 */
1258 case WLX_SAS_ACTION_FORCE_LOGOFF: /* 0x09 */
1259 case WLX_SAS_ACTION_SHUTDOWN_POWER_OFF: /* 0x0a */
1260 case WLX_SAS_ACTION_SHUTDOWN_REBOOT: /* 0x0b */
1261 if ((Session->LogonState != STATE_INIT) &&
1262 (Session->LogonState != STATE_LOGGED_OFF) &&
1263 (Session->LogonState != STATE_LOGGED_OFF_SAS) &&
1264 (Session->LogonState != STATE_SHUT_DOWN))
1265 {
1266 ASSERT((Session->LogonState == STATE_LOGGED_ON) ||
1267 (Session->LogonState == STATE_LOGGED_ON_SAS) ||
1268 (Session->LogonState == STATE_LOCKED) ||
1269 (Session->LogonState == STATE_LOCKED_SAS));
1270
1271 if (!Session->Gina.Functions.WlxIsLogoffOk(Session->Gina.Context))
1272 break;
1273 if (!NT_SUCCESS(HandleLogoff(Session, wlxAction)))
1274 {
1275 RemoveStatusMessage(Session);
1276 break;
1277 }
1278 Session->Gina.Functions.WlxLogoff(Session->Gina.Context);
1279 }
1280 if (WLX_SHUTTINGDOWN(wlxAction))
1281 {
1282 if (!NT_SUCCESS(HandleShutdown(Session, wlxAction)))
1283 {
1284 RemoveStatusMessage(Session);
1285 Session->LogonState = STATE_LOGGED_OFF;
1286 Session->Gina.Functions.WlxDisplaySASNotice(Session->Gina.Context);
1287 }
1288 }
1289 else
1290 {
1291 RemoveStatusMessage(Session);
1292 Session->LogonState = STATE_LOGGED_OFF;
1293 Session->Gina.Functions.WlxDisplaySASNotice(Session->Gina.Context);
1294 }
1295 break;
1296 case WLX_SAS_ACTION_TASKLIST: /* 0x07 */
1297 if ((Session->LogonState == STATE_LOGGED_ON) ||
1298 (Session->LogonState == STATE_LOGGED_ON_SAS))
1299 {
1300 /* Start a Task-Manager instance on the application desktop.
1301 * If the user pressed Ctrl-Shift-Esc while being on the
1302 * Logged-On SAS dialog (on the Winlogon desktop), stay there. */
1303 StartTaskManager(Session);
1304 }
1305 break;
1306 case WLX_SAS_ACTION_UNLOCK_WKSTA: /* 0x08 */
1307 if ((Session->LogonState == STATE_LOCKED) ||
1308 (Session->LogonState == STATE_LOCKED_SAS))
1309 {
1311 SwitchDesktop(Session->ApplicationDesktop);
1312 Session->LogonState = STATE_LOGGED_ON;
1313 }
1314 break;
1315 default:
1316 WARN("Unknown SAS action 0x%lx\n", wlxAction);
1317 }
1318}
1319
1320static
1321VOID
1323 IN OUT PWLSESSION Session,
1324 IN DWORD dwSasType)
1325{
1326 DWORD wlxAction = WLX_SAS_ACTION_NONE;
1327 PSID LogonSid = NULL; /* FIXME */
1328 BOOL bSecure = TRUE;
1329
1330 switch (dwSasType)
1331 {
1333 switch (Session->LogonState)
1334 {
1335 case STATE_INIT:
1336 Session->LogonState = STATE_LOGGED_OFF;
1337 Session->Gina.Functions.WlxDisplaySASNotice(Session->Gina.Context);
1338 return;
1339
1340 case STATE_LOGGED_OFF:
1341 Session->LogonState = STATE_LOGGED_OFF_SAS;
1342
1344
1345 Session->Options = 0;
1346
1347 wlxAction = (DWORD)Session->Gina.Functions.WlxLoggedOutSAS(
1348 Session->Gina.Context,
1349 Session->SASAction,
1350 &Session->LogonId,
1351 LogonSid,
1352 &Session->Options,
1353 &Session->UserToken,
1354 &Session->MprNotifyInfo,
1355 (PVOID*)&Session->Profile);
1356 break;
1357
1359 /* Ignore SAS if we are already in an SAS state */
1360 return;
1361
1362 case STATE_LOGGED_ON:
1363 Session->LogonState = STATE_LOGGED_ON_SAS;
1364 SwitchDesktop(Session->WinlogonDesktop);
1365 wlxAction = (DWORD)Session->Gina.Functions.WlxLoggedOnSAS(Session->Gina.Context, dwSasType, NULL);
1366 if ((wlxAction == WLX_SAS_ACTION_NONE) ||
1367 (wlxAction == WLX_SAS_ACTION_TASKLIST))
1368 {
1369 /*
1370 * If the user canceled (WLX_SAS_ACTION_NONE) the
1371 * Logged-On SAS dialog, or clicked on the Task-Manager
1372 * button (WLX_SAS_ACTION_TASKLIST), switch back to
1373 * the application desktop and return to log-on state.
1374 * In the latter case, the Task-Manager is launched
1375 * by DoGenericAction(WLX_SAS_ACTION_TASKLIST), which
1376 * doesn't automatically do the switch back, because
1377 * the user may have also pressed on Ctrl-Shift-Esc
1378 * to start it while being on the Logged-On SAS dialog
1379 * and wanting to stay there.
1380 */
1381 SwitchDesktop(Session->ApplicationDesktop);
1382 Session->LogonState = STATE_LOGGED_ON;
1383 }
1384 break;
1385
1387 /* Ignore SAS if we are already in an SAS state */
1388 return;
1389
1390 case STATE_LOCKED:
1391 Session->LogonState = STATE_LOCKED_SAS;
1392
1394
1395 wlxAction = (DWORD)Session->Gina.Functions.WlxWkstaLockedSAS(Session->Gina.Context, dwSasType);
1396 break;
1397
1398 case STATE_LOCKED_SAS:
1399 /* Ignore SAS if we are already in an SAS state */
1400 return;
1401
1402 default:
1403 return;
1404 }
1405 break;
1406
1408 return;
1409
1411 if (!Session->Gina.Functions.WlxScreenSaverNotify(Session->Gina.Context, &bSecure))
1412 {
1413 /* Skip start of screen saver */
1414 SetEvent(Session->hEndOfScreenSaver);
1415 }
1416 else
1417 {
1418 StartScreenSaver(Session);
1419 if (bSecure)
1420 {
1421 wlxAction = WLX_SAS_ACTION_LOCK_WKSTA;
1422// DoGenericAction(Session, WLX_SAS_ACTION_LOCK_WKSTA);
1423 }
1424 }
1425 break;
1426
1428 SetEvent(Session->hUserActivity);
1429 break;
1430 }
1431
1432 DoGenericAction(Session, wlxAction);
1433}
1434
1435static
1436BOOL
1438 IN PWLSESSION Session,
1439 IN HWND hwndSAS)
1440{
1441 /* Register Ctrl+Alt+Del hotkey */
1443 {
1444 ERR("WL: Unable to register Ctrl+Alt+Del hotkey\n");
1445 return FALSE;
1446 }
1447
1448 /* Register Ctrl+Shift+Esc "Task Manager" hotkey (optional) */
1450 if (!Session->TaskManHotkey)
1451 WARN("WL: Unable to register Ctrl+Shift+Esc hotkey\n");
1452
1453 /* Register Win+L "Lock Workstation" hotkey (optional) */
1454 Session->LockWkStaHotkey = RegisterHotKey(hwndSAS, IDHK_WIN_L, MOD_WIN, 'L');
1455 if (!Session->LockWkStaHotkey)
1456 WARN("WL: Unable to register Win+L hotkey\n");
1457
1458 /* Register Win+U "Accessibility Utility" hotkey (optional) */
1459 Session->UtilManHotkey = RegisterHotKey(hwndSAS, IDHK_WIN_U, MOD_WIN, 'U');
1460 if (!Session->UtilManHotkey)
1461 WARN("WL: Unable to register Win+U hotkey\n");
1462
1463 return TRUE;
1464}
1465
1466static
1467BOOL
1469 IN PWLSESSION Session,
1470 IN HWND hwndSAS)
1471{
1472 /* Unregister the hotkeys */
1474
1475 if (Session->TaskManHotkey)
1477
1478 if (Session->LockWkStaHotkey)
1480
1481 if (Session->UtilManHotkey)
1483
1484 return TRUE;
1485}
1486
1487static
1488BOOL
1490 _In_ PWLSESSION Session,
1491 _In_ UINT uType)
1492{
1493 LPWSTR EventName;
1494
1495 switch (uType)
1496 {
1497 case 0xFFFFFFFF:
1498 EventName = NULL;
1499 break;
1500 case MB_OK:
1501 EventName = L"SystemDefault";
1502 break;
1503 case MB_ICONASTERISK:
1504 EventName = L"SystemAsterisk";
1505 break;
1506 case MB_ICONEXCLAMATION:
1507 EventName = L"SystemExclamation";
1508 break;
1509 case MB_ICONHAND:
1510 EventName = L"SystemHand";
1511 break;
1512 case MB_ICONQUESTION:
1513 EventName = L"SystemQuestion";
1514 break;
1515 default:
1516 WARN("Unhandled type %d\n", uType);
1517 EventName = L"SystemDefault";
1518 }
1519
1520 return PlayEventSound(Session, EventName);
1521}
1522
1523static
1524LRESULT
1527 IN HWND hwndDlg,
1528 IN UINT uMsg,
1531{
1533
1534 switch (uMsg)
1535 {
1536 case WM_HOTKEY:
1537 {
1538 switch (wParam)
1539 {
1540 case IDHK_CTRL_ALT_DEL:
1541 {
1542 TRACE("SAS: CONTROL+ALT+DELETE\n");
1543 if (!Session->Gina.UseCtrlAltDelete)
1544 break;
1546 return TRUE;
1547 }
1549 {
1550 TRACE("SAS: CONTROL+SHIFT+ESCAPE\n");
1552 return TRUE;
1553 }
1554 case IDHK_WIN_L:
1555 {
1556 TRACE("SAS: WIN+L\n");
1558 return TRUE;
1559 }
1560 case IDHK_WIN_U:
1561 {
1562 TRACE("SAS: WIN+U\n");
1563 // PostMessageW(Session->SASWindow, WM_LOGONNOTIFY, LN_ACCESSIBILITY, 0);
1564 return TRUE;
1565 }
1566 }
1567 break;
1568 }
1569 case WM_CREATE:
1570 {
1571 /* Get the session pointer from the create data */
1572 Session = (PWLSESSION)((LPCREATESTRUCT)lParam)->lpCreateParams;
1573
1574 /* Save the Session pointer */
1575 SetWindowLongPtrW(hwndDlg, GWLP_USERDATA, (LONG_PTR)Session);
1576 if (GetSetupType())
1577 return TRUE;
1578 return RegisterHotKeys(Session, hwndDlg);
1579 }
1580 case WM_DESTROY:
1581 {
1582 if (!GetSetupType())
1583 UnregisterHotKeys(Session, hwndDlg);
1584 PostQuitMessage(0);
1585 return TRUE;
1586 }
1587 case WM_SETTINGCHANGE:
1588 {
1589 UINT uiAction = (UINT)wParam;
1590 if (uiAction == SPI_SETSCREENSAVETIMEOUT
1591 || uiAction == SPI_SETSCREENSAVEACTIVE)
1592 {
1594 }
1595 return TRUE;
1596 }
1597 case WM_LOGONNOTIFY:
1598 {
1599 switch(wParam)
1600 {
1601 case LN_MESSAGE_BEEP:
1602 {
1603 return HandleMessageBeep(Session, lParam);
1604 }
1605 case LN_SHELL_EXITED:
1606 {
1607 /* lParam is the exit code */
1608 if (lParam != 1 &&
1609 Session->LogonState != STATE_LOGGED_OFF &&
1610 Session->LogonState != STATE_LOGGED_OFF_SAS)
1611 {
1612 SetTimer(hwndDlg, 1, 1000, NULL);
1613 }
1614 break;
1615 }
1617 {
1619 break;
1620 }
1621#if 0
1622 case LN_ACCESSIBILITY:
1623 {
1624 ERR("LN_ACCESSIBILITY(lParam = %lu)\n", lParam);
1625 break;
1626 }
1627#endif
1629 {
1631 break;
1632 }
1633 case LN_LOGOFF:
1634 {
1635 UINT Flags = (UINT)lParam;
1637 DWORD wlxAction;
1638
1639 TRACE("\tFlags : 0x%lx\n", lParam);
1640
1641 /*
1642 * Our caller (USERSRV) should have added the shutdown flag
1643 * when setting also poweroff or reboot.
1644 */
1645 if ((Action & (EWX_POWEROFF | EWX_REBOOT)) && !(Action & EWX_SHUTDOWN))
1646 {
1647 ERR("Missing EWX_SHUTDOWN flag for poweroff or reboot; action 0x%x\n", Action);
1649 }
1650
1651 // INVESTIGATE: Our HandleLogoff/HandleShutdown may instead
1652 // take an EWX_* flags combination to determine what to do
1653 // more precisely.
1654 /* Map EWX_* flags to WLX_* actions and check for any unhandled flag */
1655 if (Action & EWX_POWEROFF)
1656 {
1659 }
1660 else if (Action & EWX_REBOOT)
1661 {
1664 }
1665 else if (Action & EWX_SHUTDOWN)
1666 {
1667 wlxAction = WLX_SAS_ACTION_SHUTDOWN;
1668 Action &= ~EWX_SHUTDOWN;
1669 }
1670 else // EWX_LOGOFF
1671 {
1672 if (Action & EWX_FORCE)
1673 wlxAction = WLX_SAS_ACTION_FORCE_LOGOFF;
1674 else
1675 wlxAction = WLX_SAS_ACTION_LOGOFF;
1676 Action &= ~(EWX_LOGOFF | EWX_FORCE);
1677 }
1678 if (Action)
1679 ERR("Unhandled EWX_* action flags: 0x%x\n", Action);
1680
1681 TRACE("In LN_LOGOFF, exit_in_progress == %s\n",
1682 ExitReactOSInProgress ? "TRUE" : "FALSE");
1683
1684 /*
1685 * In case a parallel shutdown request is done (while we are
1686 * being to shut down) and it was not done by Winlogon itself,
1687 * then just stop here.
1688 */
1689#if 0
1690// This code is commented at the moment (even if it's correct) because
1691// our log-offs do not really work: the shell is restarted, no app is killed
1692// etc... and as a result you just get explorer opening "My Documents". And
1693// if you try now a shut down, it won't work because winlogon thinks it is
1694// still in the middle of a shutdown.
1695// Maybe we also need to reset ExitReactOSInProgress somewhere else??
1697 {
1698 break;
1699 }
1700#endif
1701 /* Now do the shutdown action proper */
1702 DoGenericAction(Session, wlxAction);
1703 return 1;
1704 }
1705 case LN_LOGOFF_CANCELED:
1706 {
1707 ERR("Logoff canceled! Before: exit_in_progress == %s; After: FALSE\n",
1708 ExitReactOSInProgress ? "TRUE" : "FALSE");
1709
1711 return 1;
1712 }
1713 default:
1714 {
1715 ERR("WM_LOGONNOTIFY case %d is unimplemented\n", wParam);
1716 }
1717 }
1718 return 0;
1719 }
1720 case WM_TIMER:
1721 {
1722 if (wParam == 1)
1723 {
1724 KillTimer(hwndDlg, 1);
1725 StartUserShell(Session);
1726 }
1727 break;
1728 }
1729 case WLX_WM_SAS:
1730 {
1731 DispatchSAS(Session, (DWORD)wParam);
1732 return TRUE;
1733 }
1734 }
1735
1736 return DefWindowProc(hwndDlg, uMsg, wParam, lParam);
1737}
1738
1739BOOL
1741 IN OUT PWLSESSION Session)
1742{
1743 WNDCLASSEXW swc;
1744 BOOL ret = FALSE;
1745
1746 if (!SwitchDesktop(Session->WinlogonDesktop))
1747 {
1748 ERR("WL: Failed to switch to winlogon desktop\n");
1749 goto cleanup;
1750 }
1751
1752 /* Register SAS window class */
1753 swc.cbSize = sizeof(WNDCLASSEXW);
1754 swc.style = CS_SAVEBITS;
1756 swc.cbClsExtra = 0;
1757 swc.cbWndExtra = 0;
1758 swc.hInstance = hAppInstance;
1759 swc.hIcon = NULL;
1760 swc.hCursor = NULL;
1761 swc.hbrBackground = NULL;
1762 swc.lpszMenuName = NULL;
1764 swc.hIconSm = NULL;
1765 if (RegisterClassExW(&swc) == 0)
1766 {
1767 ERR("WL: Failed to register SAS window class\n");
1768 goto cleanup;
1769 }
1770
1771 /* Create invisible SAS window */
1772 Session->SASWindow = CreateWindowExW(
1773 0,
1776 WS_POPUP,
1777 0, 0, 0, 0, 0, 0,
1778 hAppInstance, Session);
1779 if (!Session->SASWindow)
1780 {
1781 ERR("WL: Failed to create SAS window\n");
1782 goto cleanup;
1783 }
1784
1785 /* Register SAS window to receive SAS notifications */
1786 if (!SetLogonNotifyWindow(Session->SASWindow))
1787 {
1788 ERR("WL: Failed to register SAS window\n");
1789 goto cleanup;
1790 }
1791
1793 return FALSE;
1794
1795 ret = TRUE;
1796
1797cleanup:
1798 if (!ret)
1799 UninitializeSAS(Session);
1800 return ret;
1801}
DWORD WINAPI UpdatePerUserSystemParameters(DWORD dw1, DWORD dw2)
unsigned char BOOLEAN
@ TRUSTEE_IS_SID
Definition: accctrl.h:190
@ TRUSTEE_IS_WELL_KNOWN_GROUP
Definition: accctrl.h:182
#define NO_INHERITANCE
Definition: accctrl.h:103
@ SET_ACCESS
Definition: accctrl.h:150
#define VOID
Definition: acefi.h:82
#define SetEntriesInAcl
Definition: aclapi.h:240
LONG NTSTATUS
Definition: precomp.h:26
HINSTANCE hAppInstance
Definition: mmc.c:23
void quit(int argc, const char *argv[])
Definition: cmds.c:1606
#define WARN(fmt,...)
Definition: precomp.h:61
#define ERR(fmt,...)
Definition: precomp.h:57
BOOL CreateUserEnvironment(IN PWLSESSION Session)
Definition: environment.c:128
VOID CallNotificationDlls(PWLSESSION pSession, NOTIFICATION_TYPE Type)
Definition: notify.c:530
#define IDS_CLOSINGNETWORKCONNECTIONS
Definition: resource.h:32
#define IDS_APPLYINGYOURPERSONALSETTINGS
Definition: resource.h:28
#define IDC_BTNSHTDOWNCOMPUTER
Definition: resource.h:12
#define IDS_REACTOSISSHUTTINGDOWN
Definition: resource.h:33
#define IDD_SHUTDOWNCOMPUTER
Definition: resource.h:9
#define IDS_REACTOSISRESTARTING
Definition: resource.h:41
#define IDS_SAVEYOURSETTINGS
Definition: resource.h:36
#define IDS_LOGGINGOFF
Definition: resource.h:38
#define IDS_LOADINGYOURPERSONALSETTINGS
Definition: resource.h:31
BOOL InitializeScreenSaver(IN OUT PWLSESSION Session)
Definition: screensaver.c:205
VOID StartScreenSaver(IN PWLSESSION Session)
Definition: screensaver.c:258
BOOL AllowAccessOnSession(_In_ PWLSESSION Session)
Assigns both window station and desktop access to the specific session currently active on the system...
Definition: security.c:1392
DWORD GetSetupType(VOID)
Definition: setup.c:16
BOOLEAN NTAPI RtlFreeHeap(IN PVOID HeapHandle, IN ULONG Flags, IN PVOID HeapBase)
Definition: heap.c:634
#define RegCloseKey(hKey)
Definition: registry.h:49
WPARAM wParam
Definition: combotst.c:138
LPARAM lParam
Definition: combotst.c:139
HMODULE hLibrary
Definition: odbccp32.c:12
#define STATUS_NO_MEMORY
Definition: d3dkmdt.h:51
#define ERROR_SUCCESS
Definition: deptool.c:10
BOOL WINAPI Beep(IN DWORD dwFreq, IN DWORD dwDuration)
Definition: deviceio.c:48
#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:33
LONG WINAPI RegOpenKeyExW(HKEY hKey, LPCWSTR lpSubKey, DWORD ulOptions, REGSAM samDesired, PHKEY phkResult)
Definition: reg.c:3333
LONG WINAPI RegOpenCurrentUser(IN REGSAM samDesired, OUT PHKEY phkResult)
Definition: reg.c:3209
LONG WINAPI RegQueryValueExW(_In_ HKEY hkeyorg, _In_ LPCWSTR name, _In_ LPDWORD reserved, _In_ LPDWORD type, _In_ LPBYTE data, _In_ LPDWORD count)
Definition: reg.c:4103
BOOL WINAPI ImpersonateLoggedOnUser(HANDLE hToken)
Definition: misc.c:152
BOOL WINAPI AllocateAndInitializeSid(PSID_IDENTIFIER_AUTHORITY pIdentifierAuthority, BYTE nSubAuthorityCount, DWORD nSubAuthority0, DWORD nSubAuthority1, DWORD nSubAuthority2, DWORD nSubAuthority3, DWORD nSubAuthority4, DWORD nSubAuthority5, DWORD nSubAuthority6, DWORD nSubAuthority7, PSID *pSid)
Definition: security.c:674
BOOL WINAPI InitializeSecurityDescriptor(PSECURITY_DESCRIPTOR pSecurityDescriptor, DWORD dwRevision)
Definition: security.c:929
UINT uFlags
Definition: api.c:59
#define CloseHandle
Definition: compat.h:739
#define GetProcessHeap()
Definition: compat.h:736
struct _SECURITY_ATTRIBUTES SECURITY_ATTRIBUTES
#define GetProcAddress(x, y)
Definition: compat.h:753
#define HeapAlloc
Definition: compat.h:733
#define FreeLibrary(x)
Definition: compat.h:748
#define GENERIC_READ
Definition: compat.h:135
struct _SECURITY_ATTRIBUTES * PSECURITY_ATTRIBUTES
#define HeapFree(x, y, z)
Definition: compat.h:735
#define CALLBACK
Definition: compat.h:35
#define LoadLibraryW(x)
Definition: compat.h:747
static void cleanup(void)
Definition: main.c:1335
HANDLE WINAPI DECLSPEC_HOTPATCH CreateThread(IN LPSECURITY_ATTRIBUTES lpThreadAttributes, IN DWORD dwStackSize, IN LPTHREAD_START_ROUTINE lpStartAddress, IN LPVOID lpParameter, IN DWORD dwCreationFlags, OUT LPDWORD lpThreadId)
Definition: thread.c:137
BOOL WINAPI GetExitCodeThread(IN HANDLE hThread, OUT LPDWORD lpExitCode)
Definition: thread.c:541
BOOL WINAPI RevertToSelf(void)
Definition: security.c:855
static SID_IDENTIFIER_AUTHORITY WorldAuthority
Definition: security.c:14
BOOL WINAPI DestroyEnvironmentBlock(IN LPVOID lpEnvironment)
Definition: environment.c:725
BOOL WINAPI CreateEnvironmentBlock(OUT LPVOID *lpEnvironment, IN HANDLE hToken, IN BOOL bInherit)
Definition: environment.c:503
BOOL WINAPI LoadUserProfileW(_In_ HANDLE hToken, _Inout_ LPPROFILEINFOW lpProfileInfo)
Definition: profile.c:2005
BOOL WINAPI UnloadUserProfile(_In_ HANDLE hToken, _In_ HANDLE hProfile)
Definition: profile.c:2206
static const WCHAR Cleanup[]
Definition: register.c:80
return ret
Definition: mutex.c:146
#define L(x)
Definition: resources.c:13
#define INFINITE
Definition: serial.h:102
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
FxAutoRegKey hKey
Status
Definition: gdiplustypes.h:25
HLOCAL NTAPI LocalFree(HLOCAL hMem)
Definition: heapmem.c:1594
#define MOD_ALT
Definition: imm.h:184
#define MOD_SHIFT
Definition: imm.h:186
#define MOD_CONTROL
Definition: imm.h:185
_CRTIMP size_t __cdecl wcslen(_In_z_ const wchar_t *_Str)
#define THREAD_SET_THREAD_TOKEN
Definition: pstypes.h:151
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:90
#define REG_SZ
Definition: layer.c:22
#define ZeroMemory
Definition: minwinbase.h:31
LONG_PTR LPARAM
Definition: minwindef.h:175
LONG_PTR LRESULT
Definition: minwindef.h:176
UINT_PTR WPARAM
Definition: minwindef.h:174
#define SND_ALIAS
Definition: mmsystem.h:160
#define SND_ASYNC
Definition: mmsystem.h:154
#define SND_NODEFAULT
Definition: mmsystem.h:155
#define ASSERT(a)
Definition: mode.c:44
PSDBQUERYRESULT_VISTA PVOID DWORD * dwSize
Definition: env.c:56
#define SE_ASSIGNPRIMARYTOKEN_PRIVILEGE
Definition: security.c:657
#define SE_SHUTDOWN_PRIVILEGE
Definition: security.c:673
static SCRIPT_CACHE SCRIPT_ANALYSIS * psa
Definition: usp10.c:64
struct _SECURITY_DESCRIPTOR * PSECURITY_DESCRIPTOR
Definition: security.c:98
struct _ACL * PACL
Definition: security.c:105
__int3264 LONG_PTR
Definition: mstsclib_h.h:276
unsigned int UINT
Definition: ndis.h:50
@ ShutdownReboot
Definition: extypes.h:177
@ ShutdownPowerOff
Definition: extypes.h:178
@ ShutdownNoReboot
Definition: extypes.h:176
NTSYSAPI NTSTATUS NTAPI RtlAdjustPrivilege(_In_ ULONG Privilege, _In_ BOOLEAN NewValue, _In_ BOOLEAN ForThread, _Out_ PBOOLEAN OldValue)
HANDLE hThread
Definition: wizard.c:28
#define _Inout_
Definition: no_sal2.h:162
#define _In_
Definition: no_sal2.h:158
#define _In_opt_
Definition: no_sal2.h:212
#define KEY_READ
Definition: nt_native.h:1026
NTSYSAPI NTSTATUS NTAPI RtlUnicodeStringToInteger(PUNICODE_STRING String, ULONG Base, PULONG Value)
#define KEY_QUERY_VALUE
Definition: nt_native.h:1019
#define BOOL
Definition: nt_native.h:43
#define DWORD
Definition: nt_native.h:44
#define MAXIMUM_ALLOWED
Definition: nt_native.h:83
#define UNREFERENCED_PARAMETER(P)
Definition: ntbasedef.h:329
NTSTATUS NTAPI NtSetDefaultLocale(IN BOOLEAN UserProfile, IN LCID DefaultLocaleId)
Definition: locale.c:437
NTSTATUS NTAPI NtShutdownSystem(IN SHUTDOWN_ACTION Action)
Definition: shutdown.c:43
HWND hwndSAS
Definition: winsta.c:24
#define MAKEINTRESOURCE(i)
Definition: ntverrsrc.c:25
#define LOWORD(l)
Definition: pedump.c:82
BYTE * PBYTE
Definition: pedump.c:66
#define WS_POPUP
Definition: pedump.c:616
long LONG
Definition: pedump.c:60
unsigned short USHORT
Definition: pedump.c:61
_In_opt_ _In_opt_ _In_ _In_ DWORD cbData
Definition: shlwapi.h:761
#define _SEH2_GetExceptionCode()
Definition: pseh2_64.h:181
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:82
#define _SEH2_END
Definition: pseh2_64.h:171
#define _SEH2_TRY
Definition: pseh2_64.h:71
#define _SEH2_LEAVE
Definition: pseh2_64.h:183
#define DefWindowProc
Definition: ros2win.h:31
static NTSTATUS CreateLogoffSecurityAttributes(OUT PSECURITY_ATTRIBUTES *ppsa)
Definition: sas.c:889
#define WINLOGON_SAS_TITLE
Definition: sas.c:27
static BOOL StartUserShell(IN OUT PWLSESSION Session)
Definition: sas.c:88
static BOOL RegisterHotKeys(IN PWLSESSION Session, IN HWND hwndSAS)
Definition: sas.c:1437
struct tagLOGOFF_SHUTDOWN_DATA LOGOFF_SHUTDOWN_DATA
static DWORD WINAPI PlayLogonSoundThread(_In_ LPVOID lpParameter)
Definition: sas.c:299
static DWORD WINAPI KillComProcesses(LPVOID Parameter)
Definition: sas.c:859
static VOID FreeWlxMprInfo(_Inout_ PWLX_MPR_NOTIFY_INFO MprNotifyInfo)
Frees the MPR information structure allocated by the GINA.
Definition: sas.c:546
#define WINLOGON_SAS_CLASS
Definition: sas.c:26
#define IDHK_CTRL_ALT_DEL
Definition: sas.c:29
struct tagLOGON_SOUND_DATA LOGON_SOUND_DATA
static LRESULT CALLBACK SASWindowProc(IN HWND hwndDlg, IN UINT uMsg, IN WPARAM wParam, IN LPARAM lParam)
Definition: sas.c:1526
static VOID FreeWlxProfileInfo(_Inout_ PVOID Profile)
Frees the Profile information structure (WLX_PROFILE_V1_0 or WLX_PROFILE_V2_0) allocated by the GINA.
Definition: sas.c:510
#define IDHK_WIN_L
Definition: sas.c:31
static INT_PTR CALLBACK ShutdownComputerWindowProc(IN HWND hwndDlg, IN UINT uMsg, IN WPARAM wParam, IN LPARAM lParam)
Definition: sas.c:1103
BOOL SetDefaultLanguage(IN PWLSESSION Session)
Definition: sas.c:119
static VOID DispatchSAS(IN OUT PWLSESSION Session, IN DWORD dwSasType)
Definition: sas.c:1322
LUID LuidNone
Definition: sas.c:49
NTSTATUS HandleShutdown(IN OUT PWLSESSION Session, IN DWORD wlxAction)
Definition: sas.c:1149
static NTSTATUS RunLogoffShutdownThread(_In_ PWLSESSION Session, _In_opt_ PSECURITY_ATTRIBUTES psa, _In_ DWORD wlxAction)
Definition: sas.c:779
static VOID UninitializeSAS(IN OUT PWLSESSION Session)
Definition: sas.c:1135
static VOID PlayLogoffShutdownSound(_In_ PWLSESSION Session, _In_ BOOL bShutdown)
Definition: sas.c:397
static VOID DoGenericAction(IN OUT PWLSESSION Session, IN DWORD wlxAction)
Definition: sas.c:1208
static VOID PlayLogonSound(_In_ PWLSESSION Session)
Definition: sas.c:373
static VOID RestoreAllConnections(_In_ PWLSESSION Session)
Definition: sas.c:432
static BOOL StartTaskManager(IN OUT PWLSESSION Session)
Definition: sas.c:60
static BOOL HandleMessageBeep(_In_ PWLSESSION Session, _In_ UINT uType)
Definition: sas.c:1489
#define EWX_ACTION_MASK
Definition: sas.c:39
static BOOL PlayEventSound(_In_ PWLSESSION Session, _In_ LPCWSTR EventName)
Definition: sas.c:414
static BOOL HandleLogon(IN OUT PWLSESSION Session)
Definition: sas.c:571
struct tagLOGOFF_SHUTDOWN_DATA * PLOGOFF_SHUTDOWN_DATA
struct tagLOGON_SOUND_DATA * PLOGON_SOUND_DATA
static VOID DestroyLogoffSecurityAttributes(IN PSECURITY_ATTRIBUTES psa)
Definition: sas.c:1003
BOOL InitializeSAS(IN OUT PWLSESSION Session)
Definition: sas.c:1740
static DWORD WINAPI LogoffShutdownThread(LPVOID Parameter)
Definition: sas.c:738
BOOL PlaySoundRoutine(IN LPCWSTR FileName, IN UINT bLogon, IN UINT Flags)
Definition: sas.c:248
#define IDHK_CTRL_SHIFT_ESC
Definition: sas.c:30
static BOOL UnregisterHotKeys(IN PWLSESSION Session, IN HWND hwndSAS)
Definition: sas.c:1468
#define IDHK_WIN_U
Definition: sas.c:32
static VOID CloseAllConnections(_In_ PWLSESSION Session)
Definition: sas.c:495
static BOOL ExitReactOSInProgress
Definition: sas.c:47
static NTSTATUS HandleLogoff(_Inout_ PWLSESSION Session, _In_ DWORD wlxAction)
Definition: sas.c:1015
SC_HANDLE hSCManager
Definition: sc.c:12
BOOL WINAPI QueryServiceStatusEx(SC_HANDLE hService, SC_STATUS_TYPE InfoLevel, LPBYTE lpBuffer, DWORD cbBufSize, LPDWORD pcbBytesNeeded)
Definition: scm.c:2926
SC_HANDLE WINAPI OpenServiceW(SC_HANDLE hSCManager, LPCWSTR lpServiceName, DWORD dwDesiredAccess)
Definition: scm.c:2199
BOOL WINAPI CloseServiceHandle(SC_HANDLE hSCObject)
Definition: scm.c:580
#define REG_DWORD
Definition: sdbapi.c:615
DWORD LCID
Definition: nls.h:13
BOOL WINAPI SetSecurityDescriptorDacl(PSECURITY_DESCRIPTOR pSecurityDescriptor, BOOL bDaclPresent, PACL pDacl, BOOL bDaclDefaulted)
Definition: sec.c:262
#define STATUS_SUCCESS
Definition: shellext.h:65
#define TRACE(s)
Definition: solgame.cpp:4
DWORD grfAccessPermissions
Definition: accctrl.h:333
TRUSTEE_A Trustee
Definition: accctrl.h:336
DWORD grfInheritance
Definition: accctrl.h:335
ACCESS_MODE grfAccessMode
Definition: accctrl.h:334
BOOL UseCtrlAltDelete
Definition: winlogon.h:132
LPSTR lpLocalName
Definition: winnetwk.h:171
LPSTR lpRemoteName
Definition: winnetwk.h:172
LPWSTR lpPolicyPath
Definition: userenv.h:42
LPWSTR lpServerName
Definition: userenv.h:41
LPWSTR lpProfilePath
Definition: userenv.h:39
DWORD dwFlags
Definition: userenv.h:37
DWORD dwSize
Definition: userenv.h:36
HANDLE hProfile
Definition: userenv.h:43
LPWSTR lpUserName
Definition: userenv.h:38
LPWSTR lpDefaultPath
Definition: userenv.h:40
TRUSTEE_TYPE TrusteeType
Definition: accctrl.h:208
TRUSTEE_FORM TrusteeForm
Definition: accctrl.h:207
LPSTR ptstrName
Definition: accctrl.h:209
USHORT MaximumLength
Definition: env_spec_w32.h:370
HANDLE hScreenSaverParametersChanged
Definition: winlogon.h:249
HANDLE UserToken
Definition: winlogon.h:237
LOGON_STATE LogonState
Definition: winlogon.h:239
HWND SASWindow
Definition: winlogon.h:228
GINAINSTANCE Gina
Definition: winlogon.h:222
PWSTR pszPolicy
Definition: winwlx.h:150
PWSTR pszEnvironment
Definition: winwlx.h:153
PWSTR pszServerName
Definition: winwlx.h:152
PWSTR pszProfile
Definition: winwlx.h:149
PWSTR pszNetworkDefaultUserProfile
Definition: winwlx.h:151
LPCWSTR lpszClassName
Definition: winuser.h:3328
LPCWSTR lpszMenuName
Definition: winuser.h:3327
HBRUSH hbrBackground
Definition: winuser.h:3326
WNDPROC lpfnWndProc
Definition: winuser.h:3320
UINT cbSize
Definition: winuser.h:3318
int cbWndExtra
Definition: winuser.h:3322
HCURSOR hCursor
Definition: winuser.h:3325
HICON hIconSm
Definition: winuser.h:3329
HINSTANCE hInstance
Definition: winuser.h:3323
UINT style
Definition: winuser.h:3319
int cbClsExtra
Definition: winuser.h:3321
HICON hIcon
Definition: winuser.h:3324
PWLSESSION Session
Definition: sas.c:44
BOOL IsStartup
Definition: sas.c:54
HANDLE UserToken
Definition: sas.c:53
DWORD WINAPI WaitForSingleObject(IN HANDLE hHandle, IN DWORD dwMilliseconds)
Definition: synch.c:82
VOID WINAPI DECLSPEC_HOTPATCH Sleep(IN DWORD dwMilliseconds)
Definition: synch.c:790
BOOL WINAPI DECLSPEC_HOTPATCH SetEvent(IN HANDLE hEvent)
Definition: synch.c:733
volatile BOOL bShutdown
Definition: tcpsvcs.c:16
#define GetWindowLongPtr
Definition: treelist.c:73
#define GWLP_USERDATA
Definition: treelist.c:63
int32_t INT_PTR
Definition: typedefs.h:64
uint32_t * PULONG
Definition: typedefs.h:59
unsigned char * LPBYTE
Definition: typedefs.h:53
PVOID HANDLE
Definition: typedefs.h:73
ULONG_PTR SIZE_T
Definition: typedefs.h:80
const char * PCSTR
Definition: typedefs.h:52
#define IN
Definition: typedefs.h:39
HANDLE HMODULE
Definition: typedefs.h:77
uint32_t ULONG
Definition: typedefs.h:59
#define OUT
Definition: typedefs.h:40
#define STATUS_INVALID_PARAMETER
Definition: udferr_usr.h:135
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
#define LN_SHELL_EXITED
Definition: undocuser.h:117
#define EWX_NONOTIFY
Definition: undocuser.h:136
#define LN_LOCK_WORKSTATION
Definition: undocuser.h:119
BOOL WINAPI SetLogonNotifyWindow(HWND Wnd)
Definition: logon.c:91
#define WM_LOGONNOTIFY
Definition: undocuser.h:39
#define EWX_CALLER_WINLOGON
Definition: undocuser.h:130
#define LN_START_SCREENSAVE
Definition: undocuser.h:122
#define LN_MESSAGE_BEEP
Definition: undocuser.h:121
#define LN_LOGOFF
Definition: undocuser.h:116
#define LN_LOGOFF_CANCELED
Definition: undocuser.h:123
#define PI_NOUI
Definition: userenv.h:8
_Must_inspect_result_ _In_ WDFCHILDLIST _In_ PWDF_CHILD_LIST_ITERATOR _Out_ WDFDEVICE _Inout_opt_ PWDF_CHILD_RETRIEVE_INFO Info
Definition: wdfchildlist.h:690
_In_ WDFCOLLECTION _In_ ULONG Index
_In_ WDFIOTARGET _In_ _Strict_type_match_ WDF_IO_TARGET_SENT_IO_ACTION Action
Definition: wdfiotarget.h:510
_Must_inspect_result_ _In_ WDFKEY _In_ PCUNICODE_STRING ValueName
Definition: wdfregistry.h:243
_Must_inspect_result_ _In_ WDFKEY _In_ PCUNICODE_STRING _Out_opt_ PUSHORT _Inout_opt_ PUNICODE_STRING Value
Definition: wdfregistry.h:413
#define SecureZeroMemory
Definition: winbase.h:1465
DWORD WINAPI GetLastError(void)
Definition: except.c:1042
#define WINAPI
Definition: msvc.h:6
BOOL DisplayStatusMessage(IN PWLSESSION Session, IN HDESK hDesktop, IN UINT ResourceId)
Definition: winlogon.c:370
PWSTR WlStrDup(_In_opt_ PCWSTR String)
Duplicates the given string, allocating a buffer on the heap.
Definition: winlogon.c:29
BOOL RemoveStatusMessage(IN PWLSESSION Session)
Definition: winlogon.c:391
FORCEINLINE BOOL IsFirstLogon(_In_ PWLSESSION Session)
Definition: winlogon.h:306
BOOL WINAPI SetWindowStationUser(IN HWINSTA hWindowStation, IN PLUID pluid, IN PSID psid OPTIONAL, IN DWORD size)
Definition: winsta.c:419
struct _WLSESSION * PWLSESSION
FORCEINLINE VOID SetLogonTimestamp(_Inout_ PWLSESSION Session)
Definition: winlogon.h:298
@ STATE_LOGGED_ON
Definition: winlogon.h:207
@ STATE_LOGGED_OFF_SAS
Definition: winlogon.h:206
@ STATE_LOCKED_SAS
Definition: winlogon.h:210
@ STATE_INIT
Definition: winlogon.h:204
@ STATE_LOGGED_OFF
Definition: winlogon.h:205
@ STATE_SHUT_DOWN
Definition: winlogon.h:213
@ STATE_LOGGED_ON_SAS
Definition: winlogon.h:208
@ STATE_LOCKED
Definition: winlogon.h:209
#define WLX_LOGGINGOFF(wlxAction)
Definition: winlogon.h:282
VOID CloseAllDialogWindows(VOID)
Definition: wlx.c:95
#define WLX_SHUTTINGDOWN(wlxAction)
Definition: winlogon.h:286
@ PostShellHandler
Definition: winlogon.h:275
@ LogonHandler
Definition: winlogon.h:264
@ LogoffHandler
Definition: winlogon.h:265
@ StartShellHandler
Definition: winlogon.h:274
@ UnlockHandler
Definition: winlogon.h:267
@ LockHandler
Definition: winlogon.h:266
@ ShutdownHandler
Definition: winlogon.h:269
UINT WINAPI waveOutGetNumDevs(void)
Definition: winmm.c:2137
#define RESOURCETYPE_DISK
Definition: winnetwk.h:64
#define WN_MORE_DATA
Definition: winnetwk.h:117
#define WN_SUCCESS
Definition: winnetwk.h:111
#define RESOURCE_REMEMBERED
Definition: winnetwk.h:60
#define WNetEnumResource
Definition: winnetwk.h:599
#define WNetOpenEnum
Definition: winnetwk.h:598
#define WNetAddConnection
Definition: winnetwk.h:611
#define WN_NO_MORE_ENTRIES
Definition: winnetwk.h:146
#define HKEY_LOCAL_MACHINE
Definition: winreg.h:12
#define OpenSCManager
Definition: winsvc.h:581
@ SC_STATUS_PROCESS_INFO
Definition: winsvc.h:125
#define SC_MANAGER_CONNECT
Definition: winsvc.h:14
#define SERVICE_RUNNING
Definition: winsvc.h:24
#define EWX_POWEROFF
Definition: winuser.h:645
#define EWX_SHUTDOWN
Definition: winuser.h:647
#define MF_BYCOMMAND
Definition: winuser.h:202
BOOL WINAPI SwitchDesktop(_In_ HDESK)
BOOL WINAPI PostMessageW(_In_opt_ HWND, _In_ UINT, _In_ WPARAM, _In_ LPARAM)
#define MOD_WIN
Definition: winuser.h:2686
#define MB_ICONHAND
Definition: winuser.h:799
#define WM_CREATE
Definition: winuser.h:1636
BOOL WINAPI UnregisterHotKey(_In_opt_ HWND, _In_ int)
__analysis_noreturn void WINAPI PostQuitMessage(_In_ int)
#define WM_COMMAND
Definition: winuser.h:1768
#define SPI_SETSCREENSAVEACTIVE
Definition: winuser.h:1377
#define EWX_LOGOFF
Definition: winuser.h:644
BOOL WINAPI DeleteMenu(_In_ HMENU, _In_ UINT, _In_ UINT)
#define WM_INITDIALOG
Definition: winuser.h:1767
HMENU WINAPI GetSystemMenu(_In_ HWND, _In_ BOOL)
UINT_PTR WINAPI SetTimer(_In_opt_ HWND, _In_ UINT_PTR, _In_ UINT, _In_opt_ TIMERPROC)
HWND WINAPI GetDesktopWindow(void)
Definition: window.c:628
#define WM_SETTINGCHANGE
Definition: winuser.h:1657
#define EWX_REBOOT
Definition: winuser.h:646
BOOL WINAPI RegisterHotKey(_In_opt_ HWND, _In_ int, _In_ UINT, _In_ UINT)
#define WM_TIMER
Definition: winuser.h:1770
HWND WINAPI CreateWindowExW(_In_ DWORD dwExStyle, _In_opt_ LPCWSTR lpClassName, _In_opt_ LPCWSTR lpWindowName, _In_ DWORD dwStyle, _In_ int X, _In_ int Y, _In_ int nWidth, _In_ int nHeight, _In_opt_ HWND hWndParent, _In_opt_ HMENU hMenu, _In_opt_ HINSTANCE hInstance, _In_opt_ LPVOID lpParam)
ATOM WINAPI RegisterClassExW(_In_ CONST WNDCLASSEXW *)
#define EWX_FORCE
Definition: winuser.h:643
#define SC_CLOSE
Definition: winuser.h:2628
#define MB_ICONEXCLAMATION
Definition: winuser.h:796
#define MB_OK
Definition: winuser.h:801
#define MB_ICONQUESTION
Definition: winuser.h:800
#define CS_SAVEBITS
Definition: winuser.h:665
BOOL WINAPI ExitWindowsEx(_In_ UINT, _In_ DWORD)
#define WM_HOTKEY
Definition: winuser.h:1907
struct _WNDCLASSEXW WNDCLASSEXW
#define VK_DELETE
Definition: winuser.h:2269
#define WM_DESTROY
Definition: winuser.h:1637
BOOL WINAPI UnregisterClassW(_In_ LPCWSTR, HINSTANCE)
#define MB_ICONASTERISK
Definition: winuser.h:795
BOOL WINAPI KillTimer(_In_opt_ HWND, _In_ UINT_PTR)
#define SetWindowLongPtrW
Definition: winuser.h:5457
#define VK_ESCAPE
Definition: winuser.h:2250
BOOL WINAPI DestroyWindow(_In_ HWND)
#define SPI_SETSCREENSAVETIMEOUT
Definition: winuser.h:1375
#define DialogBox
Definition: winuser.h:5872
BOOL WINAPI EndDialog(_In_ HWND, _In_ INT_PTR)
struct _WLX_PROFILE_V2_0 * PWLX_PROFILE_V2_0
#define WLX_SAS_TYPE_TIMEOUT
Definition: winwlx.h:35
#define WLX_SAS_ACTION_NONE
Definition: winwlx.h:54
#define WLX_PROFILE_TYPE_V1_0
Definition: winwlx.h:50
#define WLX_SAS_ACTION_FORCE_LOGOFF
Definition: winwlx.h:61
#define WLX_SAS_ACTION_UNLOCK_WKSTA
Definition: winwlx.h:60
#define WLX_SAS_TYPE_CTRL_ALT_DEL
Definition: winwlx.h:36
#define WLX_PROFILE_TYPE_V2_0
Definition: winwlx.h:51
#define WLX_WM_SAS
Definition: winwlx.h:71
#define WLX_SAS_ACTION_LOGON
Definition: winwlx.h:53
#define WLX_SAS_ACTION_TASKLIST
Definition: winwlx.h:59
#define WLX_SAS_ACTION_SHUTDOWN_POWER_OFF
Definition: winwlx.h:62
#define WLX_SAS_TYPE_SCRNSVR_TIMEOUT
Definition: winwlx.h:37
#define WLX_SAS_ACTION_SHUTDOWN
Definition: winwlx.h:57
#define WLX_SAS_TYPE_SCRNSVR_ACTIVITY
Definition: winwlx.h:38
#define WLX_LOGON_OPT_NO_PROFILE
Definition: winwlx.h:48
#define WLX_SAS_ACTION_SHUTDOWN_REBOOT
Definition: winwlx.h:63
#define WLX_SAS_ACTION_LOCK_WKSTA
Definition: winwlx.h:55
#define WLX_SAS_ACTION_LOGOFF
Definition: winwlx.h:56
DWORD WINAPI WNetClearConnections(HWND owner)
Definition: wnet.c:2827
DWORD WINAPI WNetCloseEnum(HANDLE hEnum)
Definition: wnet.c:1762
_In_ USHORT _In_ ULONG _In_ PSOCKADDR _In_ PSOCKADDR _Reserved_ ULONG _In_opt_ PVOID _In_opt_ const WSK_CLIENT_CONNECTION_DISPATCH _In_opt_ PEPROCESS _In_opt_ PETHREAD _In_opt_ PSECURITY_DESCRIPTOR SecurityDescriptor
Definition: wsk.h:191
_Must_inspect_result_ _In_ ULONG Flags
Definition: wsk.h:170
_In_ CONST DEVPROPKEY _In_ LCID Lcid
Definition: iofuncs.h:2415
_Inout_opt_ PVOID Parameter
Definition: rtltypes.h:336
#define SECURITY_WORLD_SID_AUTHORITY
Definition: setypes.h:527
#define SECURITY_WORLD_RID
Definition: setypes.h:541
#define SECURITY_DESCRIPTOR_REVISION
Definition: setypes.h:58
#define SECURITY_DESCRIPTOR_MIN_LENGTH
Definition: setypes.h:827
const WCHAR * LPCWSTR
Definition: xmlstorage.h:185
__wchar_t WCHAR
Definition: xmlstorage.h:180
WCHAR * LPWSTR
Definition: xmlstorage.h:184
unsigned char BYTE
Definition: xxhash.c:193