987 lines
25 KiB
C
987 lines
25 KiB
C
//+---------------------------------------------------------------------------
|
|
//
|
|
// Microsoft Windows
|
|
// Copyright (C) Microsoft Corporation, 1992 - 1993.
|
|
//
|
|
// File: shell.c
|
|
//
|
|
// Contents: Microsoft Logon GUI DLL
|
|
//
|
|
// History: 7-14-94 RichardW Created
|
|
//
|
|
//----------------------------------------------------------------------------
|
|
|
|
#include "msgina.h"
|
|
#include <stdio.h>
|
|
#include <wchar.h>
|
|
|
|
HICON hNoDCIcon;
|
|
|
|
#if DBG
|
|
DWORD DebugAllowNoShell = 1;
|
|
#else
|
|
DWORD DebugAllowNoShell = 0;
|
|
#endif
|
|
|
|
//
|
|
// Parsing information for autoexec.bat
|
|
//
|
|
#define PARSE_AUTOEXEC_KEY TEXT("Software\\Microsoft\\Windows NT\\CurrentVersion\\Winlogon")
|
|
#define PARSE_AUTOEXEC_ENTRY TEXT("ParseAutoexec")
|
|
#define PARSE_AUTOEXEC_DEFAULT TEXT("1")
|
|
#define MAX_PARSE_AUTOEXEC_BUFFER 2
|
|
|
|
BOOL
|
|
SetLogonScriptVariables(
|
|
PGLOBALS pGlobals,
|
|
PVOID * pEnvironment
|
|
);
|
|
|
|
VOID
|
|
DeleteLogonScriptVariables(
|
|
PGLOBALS pGlobals,
|
|
PVOID * pEnvironment
|
|
);
|
|
|
|
BOOL
|
|
DoAutoexecStuff(
|
|
PGLOBALS pGlobals,
|
|
PVOID * ppEnvironment,
|
|
LPTSTR pszPathVar)
|
|
{
|
|
NTSTATUS Status;
|
|
HKEY hKey;
|
|
DWORD dwDisp, dwType, dwMaxBufferSize;
|
|
TCHAR szParseAutoexec[MAX_PARSE_AUTOEXEC_BUFFER];
|
|
|
|
|
|
//
|
|
// Set the default case
|
|
//
|
|
|
|
lstrcpy (szParseAutoexec, PARSE_AUTOEXEC_DEFAULT);
|
|
|
|
|
|
//
|
|
// Impersonate the user, and check the registry
|
|
//
|
|
|
|
if (OpenHKeyCurrentUser(pGlobals)) {
|
|
|
|
|
|
if (RegCreateKeyEx (HKEY_CURRENT_USER, PARSE_AUTOEXEC_KEY, 0, 0,
|
|
REG_OPTION_NON_VOLATILE, KEY_READ | KEY_WRITE,
|
|
NULL, &hKey, &dwDisp) == ERROR_SUCCESS) {
|
|
|
|
|
|
//
|
|
// Query the current value. If it doesn't exist, then add
|
|
// the entry for next time.
|
|
//
|
|
|
|
dwMaxBufferSize = sizeof (TCHAR) * MAX_PARSE_AUTOEXEC_BUFFER;
|
|
if (RegQueryValueEx (hKey, PARSE_AUTOEXEC_ENTRY, NULL, &dwType,
|
|
(LPBYTE) szParseAutoexec, &dwMaxBufferSize)
|
|
!= ERROR_SUCCESS) {
|
|
|
|
//
|
|
// Set the default value
|
|
//
|
|
|
|
RegSetValueEx (hKey, PARSE_AUTOEXEC_ENTRY, 0, REG_SZ,
|
|
(LPBYTE) szParseAutoexec,
|
|
sizeof (TCHAR) * (lstrlen (szParseAutoexec) + 1));
|
|
}
|
|
|
|
//
|
|
// Close key
|
|
//
|
|
|
|
RegCloseKey (hKey);
|
|
}
|
|
|
|
//
|
|
// Close HKCU
|
|
//
|
|
|
|
CloseHKeyCurrentUser(pGlobals);
|
|
|
|
}
|
|
|
|
|
|
//
|
|
// Process the autoexec if appropriate
|
|
//
|
|
|
|
if (szParseAutoexec[0] == TEXT('1')) {
|
|
ProcessAutoexec(ppEnvironment, PATH_VARIABLE);
|
|
}
|
|
|
|
return(TRUE);
|
|
}
|
|
|
|
//+---------------------------------------------------------------------------
|
|
//
|
|
// Function: UpdateUserEnvironment
|
|
//
|
|
// Synopsis:
|
|
//
|
|
// Arguments: [pGlobals] --
|
|
// [ppEnvironment] --
|
|
//
|
|
// History: 11-01-94 RichardW Created
|
|
//
|
|
// Notes:
|
|
//
|
|
//----------------------------------------------------------------------------
|
|
VOID
|
|
UpdateUserEnvironment(
|
|
PGLOBALS pGlobals,
|
|
PVOID * ppEnvironment,
|
|
PWSTR pszOldDir
|
|
)
|
|
{
|
|
BOOL DeepShare;
|
|
TCHAR lpHomeShare[MAX_PATH] = TEXT("");
|
|
TCHAR lpHomePath[MAX_PATH] = TEXT("");
|
|
TCHAR lpHomeDrive[4] = TEXT("");
|
|
TCHAR lpHomeDirectory[MAX_PATH] = TEXT("");
|
|
|
|
/*
|
|
* Initialize user's environment.
|
|
*/
|
|
|
|
SetUserEnvironmentVariable(ppEnvironment, USERNAME_VARIABLE, (LPTSTR)pGlobals->UserName, TRUE);
|
|
SetUserEnvironmentVariable(ppEnvironment, USERDOMAIN_VARIABLE, (LPTSTR)pGlobals->Domain, TRUE);
|
|
|
|
if (pGlobals->Profile->HomeDirectoryDrive.Length &&
|
|
(pGlobals->Profile->HomeDirectoryDrive.Length + 1) < MAX_PATH) {
|
|
lstrcpy(lpHomeDrive, pGlobals->Profile->HomeDirectoryDrive.Buffer);
|
|
}
|
|
|
|
if (pGlobals->Profile->HomeDirectory.Length &&
|
|
(pGlobals->Profile->HomeDirectory.Length + 1) < MAX_PATH) {
|
|
lstrcpy(lpHomeDirectory, pGlobals->Profile->HomeDirectory.Buffer);
|
|
}
|
|
|
|
SetHomeDirectoryEnvVars(ppEnvironment,
|
|
lpHomeDirectory,
|
|
lpHomeDrive,
|
|
lpHomeShare,
|
|
lpHomePath,
|
|
&DeepShare);
|
|
|
|
ChangeToHomeDirectory( pGlobals,
|
|
ppEnvironment,
|
|
lpHomeDirectory,
|
|
lpHomeDrive,
|
|
lpHomeShare,
|
|
lpHomePath,
|
|
pszOldDir,
|
|
DeepShare
|
|
);
|
|
|
|
|
|
DoAutoexecStuff(pGlobals, ppEnvironment, PATH_VARIABLE);
|
|
|
|
SetEnvironmentVariables(pGlobals, ppEnvironment);
|
|
|
|
AppendNTPathWithAutoexecPath( ppEnvironment,
|
|
PATH_VARIABLE,
|
|
AUTOEXECPATH_VARIABLE);
|
|
|
|
}
|
|
|
|
|
|
BOOL
|
|
ExecApplication(
|
|
IN LPTSTR pch,
|
|
IN LPTSTR Desktop,
|
|
IN PGLOBALS pGlobals,
|
|
IN PVOID pEnvironment,
|
|
IN DWORD Flags,
|
|
IN DWORD StartupFlags,
|
|
OUT PPROCESS_INFORMATION ProcessInformation
|
|
)
|
|
{
|
|
STARTUPINFO si;
|
|
BOOL Result, IgnoreResult;
|
|
HANDLE ImpersonationHandle;
|
|
|
|
|
|
//
|
|
// Initialize process startup info
|
|
//
|
|
si.cb = sizeof(STARTUPINFO);
|
|
si.lpReserved = pch;
|
|
si.lpTitle = pch;
|
|
si.dwX = si.dwY = si.dwXSize = si.dwYSize = 0L;
|
|
si.dwFlags = StartupFlags;
|
|
si.wShowWindow = SW_SHOW; // at least let the guy see it
|
|
si.lpReserved2 = NULL;
|
|
si.cbReserved2 = 0;
|
|
si.lpDesktop = Desktop;
|
|
|
|
//
|
|
// Impersonate the user so we get access checked correctly on
|
|
// the file we're trying to execute
|
|
//
|
|
|
|
ImpersonationHandle = ImpersonateUser(&pGlobals->UserProcessData, NULL);
|
|
if (ImpersonationHandle == NULL) {
|
|
WLPrint(("ExecApplication failed to impersonate user"));
|
|
return(FALSE);
|
|
}
|
|
|
|
|
|
//
|
|
// Create the app suspended
|
|
//
|
|
DebugLog((DEB_TRACE, "About to create process of %ws, on desktop %ws\n", pch, Desktop));
|
|
Result = CreateProcessAsUser(
|
|
pGlobals->UserProcessData.UserToken,
|
|
NULL,
|
|
pch,
|
|
NULL,
|
|
NULL,
|
|
FALSE,
|
|
Flags | CREATE_SUSPENDED | CREATE_UNICODE_ENVIRONMENT,
|
|
pEnvironment,
|
|
NULL,
|
|
&si,
|
|
ProcessInformation);
|
|
|
|
|
|
IgnoreResult = StopImpersonating(ImpersonationHandle);
|
|
ASSERT(IgnoreResult);
|
|
|
|
return(Result);
|
|
|
|
}
|
|
|
|
BOOL
|
|
SetProcessQuotas(
|
|
PPROCESS_INFORMATION ProcessInformation,
|
|
PUSER_PROCESS_DATA UserProcessData
|
|
)
|
|
{
|
|
NTSTATUS Status = STATUS_SUCCESS;
|
|
BOOL Result;
|
|
QUOTA_LIMITS RequestedLimits;
|
|
|
|
RequestedLimits = UserProcessData->Quotas;
|
|
RequestedLimits.MinimumWorkingSetSize = 0;
|
|
RequestedLimits.MaximumWorkingSetSize = 0;
|
|
|
|
if (UserProcessData->Quotas.PagedPoolLimit != 0) {
|
|
|
|
Result = EnablePrivilege(SE_INCREASE_QUOTA_PRIVILEGE, TRUE);
|
|
if (!Result) {
|
|
WLPrint(("failed to enable increase_quota privilege"));
|
|
return(FALSE);
|
|
}
|
|
|
|
Status = NtSetInformationProcess(
|
|
ProcessInformation->hProcess,
|
|
ProcessQuotaLimits,
|
|
(PVOID)&RequestedLimits,
|
|
(ULONG)sizeof(QUOTA_LIMITS)
|
|
);
|
|
|
|
Result = EnablePrivilege(SE_INCREASE_QUOTA_PRIVILEGE, FALSE);
|
|
if (!Result) {
|
|
WLPrint(("failed to disable increase_quota privilege"));
|
|
}
|
|
}
|
|
|
|
|
|
#if DBG
|
|
if (!NT_SUCCESS(Status)) {
|
|
WLPrint(("SetProcessQuotas failed. Status: 0x%lx", Status));
|
|
}
|
|
#endif //DBG
|
|
|
|
return (NT_SUCCESS(Status));
|
|
}
|
|
|
|
|
|
DWORD
|
|
ExecProcesses(
|
|
PVOID pWlxContext,
|
|
IN LPTSTR Desktop,
|
|
IN PWSTR Processes,
|
|
PVOID pEnvironment,
|
|
DWORD Flags,
|
|
DWORD StartupFlags
|
|
)
|
|
{
|
|
PWCH pchData;
|
|
PROCESS_INFORMATION ProcessInformation;
|
|
DWORD dwExecuted = 0 ;
|
|
PWSTR pszTok;
|
|
PGLOBALS pGlobals = (PGLOBALS) pWlxContext;
|
|
WCHAR szCurrentDir[MAX_PATH];
|
|
int err;
|
|
|
|
pchData = Processes;
|
|
|
|
UpdateUserEnvironment(pGlobals, &pEnvironment, szCurrentDir);
|
|
|
|
SetLogonScriptVariables(pGlobals, &pEnvironment);
|
|
|
|
pszTok = wcstok(pchData, TEXT(","));
|
|
while (pszTok)
|
|
{
|
|
if (*pszTok == TEXT(' '))
|
|
{
|
|
while (*pszTok++ == TEXT(' '))
|
|
;
|
|
}
|
|
if (ExecApplication((LPTSTR)pszTok,
|
|
Desktop,
|
|
pGlobals,
|
|
pEnvironment,
|
|
Flags,
|
|
StartupFlags,
|
|
&ProcessInformation)) {
|
|
dwExecuted++;
|
|
|
|
if (SetProcessQuotas(&ProcessInformation,
|
|
&pGlobals->UserProcessData))
|
|
{
|
|
ResumeThread(ProcessInformation.hThread);
|
|
}
|
|
else
|
|
{
|
|
TerminateProcess(ProcessInformation.hProcess,
|
|
ERROR_ACCESS_DENIED);
|
|
}
|
|
|
|
CloseHandle(ProcessInformation.hThread);
|
|
CloseHandle(ProcessInformation.hProcess);
|
|
|
|
} else {
|
|
|
|
DebugLog((DEB_WARN, "Cannot start %ws on %ws, error %d.", pszTok, Desktop, GetLastError()));
|
|
}
|
|
|
|
pszTok = wcstok(NULL, TEXT(","));
|
|
|
|
}
|
|
|
|
DeleteLogonScriptVariables(pGlobals, &pEnvironment);
|
|
|
|
SetCurrentDirectory(szCurrentDir);
|
|
|
|
return dwExecuted ;
|
|
}
|
|
|
|
|
|
LRESULT
|
|
NoDCDlgProc(
|
|
HWND hDlg,
|
|
UINT Message,
|
|
WPARAM wParam,
|
|
LPARAM lParam )
|
|
{
|
|
DWORD * pFlag;
|
|
DWORD Button;
|
|
HWND hwnd;
|
|
|
|
switch (Message)
|
|
{
|
|
case WM_INITDIALOG:
|
|
CentreWindow( hDlg );
|
|
if ( !hNoDCIcon )
|
|
{
|
|
hNoDCIcon = LoadImage( hDllInstance,
|
|
MAKEINTRESOURCE( IDI_NODC_ICON ),
|
|
IMAGE_ICON,
|
|
64, 64,
|
|
LR_DEFAULTCOLOR );
|
|
}
|
|
SendMessage( GetDlgItem( hDlg, IDD_NODC_FRAME ),
|
|
STM_SETICON,
|
|
(WPARAM) hNoDCIcon,
|
|
0 );
|
|
|
|
if ( GetProfileInt( WINLOGON, TEXT("AllowDisableDCNotify"), 0 ) )
|
|
{
|
|
hwnd = GetDlgItem( hDlg, IDD_NODC_TEXT2 );
|
|
ShowWindow( hwnd, SW_HIDE );
|
|
EnableWindow( hwnd, FALSE );
|
|
}
|
|
else
|
|
{
|
|
hwnd = GetDlgItem( hDlg, IDD_NODC_CHECK );
|
|
CheckDlgButton( hDlg, IDD_NODC_CHECK, BST_UNCHECKED );
|
|
ShowWindow( hwnd, SW_HIDE );
|
|
EnableWindow( hwnd, FALSE );
|
|
|
|
}
|
|
|
|
return( TRUE );
|
|
|
|
case WM_COMMAND:
|
|
if (LOWORD(wParam) == IDOK)
|
|
{
|
|
Button = IsDlgButtonChecked( hDlg, IDD_NODC_CHECK );
|
|
EndDialog( hDlg, Button );
|
|
return( TRUE );
|
|
}
|
|
|
|
|
|
}
|
|
|
|
return( FALSE );
|
|
}
|
|
|
|
VOID
|
|
DoNoDCDialog(
|
|
PGLOBALS pGlobals )
|
|
{
|
|
HKEY hKey;
|
|
int err;
|
|
DWORD disp;
|
|
DWORD Flag;
|
|
DWORD dwType;
|
|
DWORD cbData;
|
|
BOOL MappedHKey;
|
|
PWSTR ReportControllerMissing;
|
|
|
|
Flag = 1;
|
|
|
|
if (OpenHKeyCurrentUser(pGlobals))
|
|
{
|
|
MappedHKey = TRUE;
|
|
|
|
err = RegCreateKeyEx( HKEY_CURRENT_USER,
|
|
WINLOGON_USER_KEY,
|
|
0, NULL,
|
|
REG_OPTION_NON_VOLATILE,
|
|
KEY_READ | KEY_WRITE,
|
|
NULL,
|
|
&hKey,
|
|
&disp );
|
|
if (err == 0)
|
|
{
|
|
cbData = sizeof(DWORD);
|
|
|
|
RegQueryValueEx( hKey,
|
|
NODCMESSAGE,
|
|
NULL,
|
|
&dwType,
|
|
(LPBYTE) &Flag,
|
|
&cbData );
|
|
|
|
if (dwType != REG_DWORD)
|
|
{
|
|
Flag = 1;
|
|
}
|
|
|
|
}
|
|
else
|
|
{
|
|
hKey = NULL;
|
|
}
|
|
|
|
|
|
}
|
|
else
|
|
{
|
|
MappedHKey = FALSE;
|
|
}
|
|
|
|
if ( Flag )
|
|
{
|
|
ReportControllerMissing = AllocAndGetProfileString( APPLICATION_NAME,
|
|
REPORT_CONTROLLER_MISSING,
|
|
TEXT("TRUE")
|
|
);
|
|
|
|
if ( ReportControllerMissing )
|
|
{
|
|
if ( lstrcmp( ReportControllerMissing, TEXT("TRUE")) == 0 )
|
|
{
|
|
Flag = 1;
|
|
}
|
|
else
|
|
{
|
|
Flag = 0;
|
|
}
|
|
|
|
Free( ReportControllerMissing );
|
|
}
|
|
else
|
|
{
|
|
Flag = 1;
|
|
}
|
|
|
|
}
|
|
|
|
|
|
if (Flag)
|
|
{
|
|
pWlxFuncs->WlxSetTimeout( hGlobalWlx,
|
|
120 );
|
|
|
|
Flag = pWlxFuncs->WlxDialogBoxParam( hGlobalWlx,
|
|
hDllInstance,
|
|
(LPTSTR) IDD_NODC_DIALOG,
|
|
NULL,
|
|
NoDCDlgProc,
|
|
0 );
|
|
}
|
|
else
|
|
{
|
|
Flag = BST_CHECKED;
|
|
}
|
|
|
|
if (hKey)
|
|
{
|
|
if (Flag == BST_CHECKED)
|
|
{
|
|
Flag = 0;
|
|
}
|
|
else
|
|
{
|
|
Flag = 1;
|
|
}
|
|
|
|
RegSetValueEx( hKey,
|
|
NODCMESSAGE,
|
|
0,
|
|
REG_DWORD,
|
|
(LPBYTE) &Flag,
|
|
sizeof(DWORD) );
|
|
|
|
RegCloseKey( hKey );
|
|
|
|
}
|
|
|
|
if (MappedHKey)
|
|
{
|
|
CloseHKeyCurrentUser(pGlobals);
|
|
}
|
|
}
|
|
|
|
/****************************************************************************\
|
|
*
|
|
* FUNCTION: DisplayPostShellLogonMessages
|
|
*
|
|
* PURPOSE: Displays any security warnings to the user after a successful logon
|
|
* The messages are displayed while the shell is starting up.
|
|
*
|
|
* RETURNS: DLG_SUCCESS - the dialogs were displayed successfully.
|
|
* DLG_INTERRUPTED() - a set defined in winlogon.h
|
|
*
|
|
* NOTE: Screen-saver timeouts are handled by our parent dialog so this
|
|
* routine should never return DLG_SCREEN_SAVER_TIMEOUT
|
|
*
|
|
* HISTORY:
|
|
*
|
|
* 12-09-91 Davidc Created.
|
|
*
|
|
\****************************************************************************/
|
|
|
|
int
|
|
DisplayPostShellLogonMessages(
|
|
PGLOBALS pGlobals
|
|
)
|
|
{
|
|
int Result = IDOK;
|
|
BOOLEAN Success;
|
|
TCHAR Buffer1[MAX_STRING_BYTES];
|
|
TCHAR Buffer2[MAX_STRING_BYTES];
|
|
ULONG ElapsedSecondsNow;
|
|
ULONG ElapsedSecondsPasswordExpires;
|
|
ULONG DaysToExpiry;
|
|
DWORD DaysToCheck;
|
|
HKEY hKey;
|
|
DWORD dwSize;
|
|
DWORD dwType;
|
|
PSECURITY_SEED_AND_LENGTH SeedAndLength;
|
|
UCHAR Seed;
|
|
|
|
|
|
//
|
|
// Check to see if the system time is properly set
|
|
//
|
|
|
|
{
|
|
SYSTEMTIME Systime;
|
|
|
|
GetSystemTime(&Systime);
|
|
|
|
if ( Systime.wYear < 1996 ) {
|
|
|
|
Result = TimeoutMessageBox(
|
|
NULL,
|
|
IDS_INVALID_TIME_MSG,
|
|
IDS_INVALID_TIME,
|
|
MB_OK | MB_ICONSTOP,
|
|
TIMEOUT_NONE
|
|
);
|
|
|
|
if (DLG_INTERRUPTED(Result)) {
|
|
return(Result);
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
DaysToCheck = PASSWORD_EXPIRY_WARNING_DAYS;
|
|
|
|
if (RegOpenKey( HKEY_LOCAL_MACHINE, WINLOGON_USER_KEY, &hKey ) == 0)
|
|
{
|
|
dwSize = sizeof(DWORD);
|
|
|
|
if (RegQueryValueEx(hKey,
|
|
PASSWORD_EXPIRY_WARNING,
|
|
0,
|
|
&dwType,
|
|
(LPBYTE) &DaysToCheck,
|
|
&dwSize ) ||
|
|
(dwType != REG_DWORD) )
|
|
{
|
|
DaysToCheck = PASSWORD_EXPIRY_WARNING_DAYS;
|
|
}
|
|
|
|
RegCloseKey( hKey );
|
|
|
|
}
|
|
|
|
|
|
#define SECONDS_PER_DAY (60*60*24)
|
|
|
|
//
|
|
// Go get parameters from our user's profile
|
|
//
|
|
|
|
if (pGlobals->Profile != NULL) {
|
|
|
|
if (!RtlTimeToSecondsSince1980(&(pGlobals->Profile->PasswordMustChange),
|
|
&ElapsedSecondsPasswordExpires)) {
|
|
//
|
|
// The time was not expressable in 32-bit seconds
|
|
// Set seconds to password expiry based on whether the expiry
|
|
// time is way in the past or way in the future.
|
|
//
|
|
if ( pGlobals->Profile->PasswordMustChange.QuadPart >
|
|
pGlobals->LogonTime.QuadPart )
|
|
{
|
|
ElapsedSecondsPasswordExpires = MAXULONG; // Never
|
|
} else {
|
|
ElapsedSecondsPasswordExpires = 0; // Already expired
|
|
}
|
|
}
|
|
|
|
} else {
|
|
|
|
ElapsedSecondsPasswordExpires = MAXULONG; // Never
|
|
}
|
|
|
|
|
|
|
|
//
|
|
// Password will expire warning
|
|
//
|
|
|
|
Success = RtlTimeToSecondsSince1980(&pGlobals->LogonTime, &ElapsedSecondsNow);
|
|
|
|
if (Success) {
|
|
|
|
if (ElapsedSecondsPasswordExpires < ElapsedSecondsNow) {
|
|
DebugLog((DEB_ERROR, "password on this account has expired, yet we logged on successfully - this is inconsistent !\n"));
|
|
DaysToExpiry = 0;
|
|
} else {
|
|
DaysToExpiry = (ElapsedSecondsPasswordExpires - ElapsedSecondsNow)/SECONDS_PER_DAY;
|
|
}
|
|
|
|
if (DaysToExpiry <= DaysToCheck) {
|
|
|
|
if (DaysToExpiry > 0) {
|
|
LoadString(hDllInstance, IDS_PASSWORD_WILL_EXPIRE, Buffer1, sizeof(Buffer1));
|
|
_snwprintf(Buffer2, sizeof(Buffer2)/sizeof(TCHAR), Buffer1, DaysToExpiry);
|
|
} else {
|
|
LoadString(hDllInstance, IDS_PASSWORD_EXPIRES_TODAY, Buffer2, sizeof(Buffer2));
|
|
}
|
|
|
|
LoadString(hDllInstance, IDS_LOGON_MESSAGE, Buffer1, sizeof(Buffer1));
|
|
|
|
Result = TimeoutMessageBoxlpstr(NULL,
|
|
Buffer2,
|
|
Buffer1,
|
|
MB_YESNO | MB_ICONEXCLAMATION,
|
|
TIMEOUT_NONE);
|
|
if (Result == IDYES) {
|
|
//
|
|
// Let the user change their password now
|
|
//
|
|
|
|
RevealPassword( &pGlobals->PasswordString );
|
|
|
|
Result = ChangePasswordLogon(NULL,
|
|
pGlobals,
|
|
pGlobals->UserName,
|
|
pGlobals->Domain,
|
|
pGlobals->Password
|
|
);
|
|
|
|
}
|
|
|
|
if (DLG_INTERRUPTED(Result)) {
|
|
return(Result);
|
|
}
|
|
}
|
|
} else {
|
|
DebugLog((DEB_ERROR, "Logon time is bogus, disabling password expiry warning. Reset the system time to fix this.\n"));
|
|
}
|
|
|
|
if (pGlobals->Profile != NULL) {
|
|
|
|
//
|
|
// Logon cache used
|
|
//
|
|
|
|
if (pGlobals->Profile->UserFlags & LOGON_CACHED_ACCOUNT)
|
|
{
|
|
DoNoDCDialog( pGlobals );
|
|
}
|
|
}
|
|
|
|
return(IDOK);
|
|
}
|
|
|
|
|
|
|
|
/***************************************************************************\
|
|
* FUNCTION: SetLogonScriptVariables
|
|
*
|
|
* PURPOSE: Sets the appropriate environment variables in the user
|
|
* process environment block so that the logon script information
|
|
* can be passed into the userinit app.
|
|
*
|
|
* RETURNS: TRUE on success, FALSE on failure
|
|
*
|
|
* HISTORY:
|
|
*
|
|
* 21-Aug-92 Davidc Created.
|
|
*
|
|
\***************************************************************************/
|
|
|
|
BOOL
|
|
SetLogonScriptVariables(
|
|
PGLOBALS pGlobals,
|
|
PVOID * pEnvironment
|
|
)
|
|
{
|
|
NTSTATUS Status;
|
|
LPWSTR EncodedMultiSz;
|
|
UNICODE_STRING Name, Value;
|
|
|
|
//
|
|
// Set our primary authenticator logon script variables
|
|
//
|
|
|
|
if (pGlobals->Profile != NULL) {
|
|
|
|
//
|
|
// Set the server name variable
|
|
//
|
|
|
|
RtlInitUnicodeString(&Name, LOGON_SERVER_VARIABLE);
|
|
Status = RtlSetEnvironmentVariable(pEnvironment, &Name, &pGlobals->Profile->LogonServer);
|
|
if (!NT_SUCCESS(Status)) {
|
|
WLPrint(("Failed to set environment variable <%Z> to value <%Z>", &Name, &pGlobals->Profile->LogonServer));
|
|
goto CleanupAndExit;
|
|
}
|
|
|
|
//
|
|
// Set the script name variable
|
|
//
|
|
|
|
RtlInitUnicodeString(&Name, LOGON_SCRIPT_VARIABLE);
|
|
Status = RtlSetEnvironmentVariable(pEnvironment, &Name, &pGlobals->Profile->LogonScript);
|
|
if (!NT_SUCCESS(Status)) {
|
|
WLPrint(("Failed to set environment variable <%Z> to value <%Z>", &Name, &pGlobals->Profile->LogonScript));
|
|
goto CleanupAndExit;
|
|
}
|
|
}
|
|
|
|
//
|
|
// Set the multiple provider script name variable
|
|
//
|
|
|
|
if (pGlobals->MprLogonScripts != NULL) {
|
|
|
|
RtlInitUnicodeString(&Name, MPR_LOGON_SCRIPT_VARIABLE);
|
|
|
|
EncodedMultiSz = EncodeMultiSzW(pGlobals->MprLogonScripts);
|
|
if (EncodedMultiSz == NULL) {
|
|
WLPrint(("Failed to encode MPR logon scripts into a string"));
|
|
goto CleanupAndExit;
|
|
}
|
|
|
|
RtlInitUnicodeString(&Value, EncodedMultiSz);
|
|
Status = RtlSetEnvironmentVariable(pEnvironment, &Name, &Value);
|
|
Free(EncodedMultiSz);
|
|
if (!NT_SUCCESS(Status)) {
|
|
WLPrint(("Failed to set mpr scripts environment variable <%Z>", &Name));
|
|
goto CleanupAndExit;
|
|
}
|
|
}
|
|
|
|
|
|
return(TRUE);
|
|
|
|
|
|
CleanupAndExit:
|
|
|
|
DeleteLogonScriptVariables(pGlobals, pEnvironment);
|
|
return(FALSE);
|
|
}
|
|
|
|
|
|
/***************************************************************************\
|
|
* FUNCTION: DeleteLogonScriptVariables
|
|
*
|
|
* PURPOSE: Deletes the environment variables in the user process
|
|
* environment block that we use to communicate logon script
|
|
* information to the userinit app
|
|
*
|
|
* RETURNS: Nothing
|
|
*
|
|
* HISTORY:
|
|
*
|
|
* 21-Aug-92 Davidc Created.
|
|
*
|
|
\***************************************************************************/
|
|
|
|
VOID
|
|
DeleteLogonScriptVariables(
|
|
PGLOBALS pGlobals,
|
|
PVOID * pEnvironment
|
|
)
|
|
{
|
|
NTSTATUS Status;
|
|
UNICODE_STRING Name;
|
|
|
|
RtlInitUnicodeString(&Name, LOGON_SERVER_VARIABLE);
|
|
|
|
Status = RtlSetEnvironmentVariable(pEnvironment, &Name, NULL);
|
|
if (!NT_SUCCESS(Status) && (Status != STATUS_UNSUCCESSFUL) ) {
|
|
WLPrint(("Failed to delete environment variable <%Z>, status = 0x%lx", &Name, Status));
|
|
}
|
|
|
|
RtlInitUnicodeString(&Name, LOGON_SCRIPT_VARIABLE);
|
|
|
|
Status = RtlSetEnvironmentVariable(pEnvironment, &Name, NULL);
|
|
if (!NT_SUCCESS(Status) && (Status != STATUS_UNSUCCESSFUL) ) {
|
|
WLPrint(("Failed to delete environment variable <%Z>, status = 0x%lx", &Name, Status));
|
|
}
|
|
|
|
if (pGlobals->MprLogonScripts != NULL) {
|
|
RtlInitUnicodeString(&Name, MPR_LOGON_SCRIPT_VARIABLE);
|
|
|
|
Status = RtlSetEnvironmentVariable(pEnvironment, &Name, NULL);
|
|
if (!NT_SUCCESS(Status) && (Status != STATUS_UNSUCCESSFUL) ) {
|
|
WLPrint(("Failed to delete environment variable <%Z>, status = 0x%lx", &Name, Status));
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
BOOL
|
|
WINAPI
|
|
WlxActivateUserShell(
|
|
PVOID pWlxContext,
|
|
PWSTR pszDesktop,
|
|
PWSTR pszMprLogonScript,
|
|
PVOID pEnvironment
|
|
)
|
|
{
|
|
BOOL bExec;
|
|
PGLOBALS pGlobals;
|
|
PWSTR pchData;
|
|
|
|
pchData = AllocAndGetPrivateProfileString(APPLICATION_NAME, USERINIT_KEY,
|
|
TEXT("userinit.exe"), NULL);
|
|
|
|
if ( !pchData )
|
|
{
|
|
return( FALSE );
|
|
}
|
|
|
|
pGlobals = (PGLOBALS) pWlxContext;
|
|
|
|
pGlobals->MprLogonScripts = pszMprLogonScript;
|
|
|
|
bExec = ExecProcesses(pWlxContext, pszDesktop, pchData, pEnvironment, 0, 0);
|
|
|
|
Free( pchData );
|
|
|
|
if (!bExec && (DebugAllowNoShell == 0))
|
|
{
|
|
return(FALSE);
|
|
}
|
|
|
|
if ( pGlobals->ExtraApps )
|
|
{
|
|
ExecProcesses( pWlxContext, pszDesktop, pGlobals->ExtraApps, pEnvironment, 0, 0 );
|
|
|
|
Free( pGlobals->ExtraApps );
|
|
|
|
pGlobals->ExtraApps = NULL;
|
|
}
|
|
|
|
DisplayPostShellLogonMessages(pGlobals);
|
|
|
|
pGlobals->UserProcessData.pEnvironment = pEnvironment;
|
|
|
|
return(TRUE);
|
|
}
|
|
|
|
|
|
BOOL
|
|
WINAPI
|
|
WlxStartApplication(
|
|
PVOID pWlxContext,
|
|
PWSTR pszDesktop,
|
|
PVOID pEnvironment,
|
|
PWSTR pszCmdLine
|
|
)
|
|
{
|
|
PROCESS_INFORMATION ProcessInformation;
|
|
BOOL bExec;
|
|
PGLOBALS pGlobals = (PGLOBALS) pWlxContext;
|
|
|
|
bExec = ExecApplication (pszCmdLine,
|
|
pszDesktop,
|
|
pGlobals,
|
|
pGlobals->UserProcessData.pEnvironment,
|
|
0,
|
|
STARTF_USESHOWWINDOW,
|
|
&ProcessInformation);
|
|
|
|
if (!bExec) {
|
|
return(FALSE);
|
|
}
|
|
|
|
if (SetProcessQuotas(&ProcessInformation,
|
|
&pGlobals->UserProcessData))
|
|
{
|
|
ResumeThread(ProcessInformation.hThread);
|
|
}
|
|
else
|
|
{
|
|
TerminateProcess(ProcessInformation.hProcess,
|
|
ERROR_ACCESS_DENIED);
|
|
}
|
|
|
|
CloseHandle(ProcessInformation.hThread);
|
|
CloseHandle(ProcessInformation.hProcess);
|
|
|
|
return(TRUE);
|
|
}
|