Article ID: 142790
Article Last Modified on 7/11/2005
HeapAlloc( GetProcessHeap(), 0,
(lstrlenW(usri3_profile) + 1) * sizeof(WCHAR) // string + NULL
);
HeapAlloc( GetProcessHeap(), 0, sizeof(WLX_PROFILE_V1_0) );
/*
The following function illustrates a WlxLoggedOutSAS() which obtains
the user profile path, and returns the result if a profile path is
found. This function is a modified version of WlxLoggedOutSAS() taken
from the Win32 SDK version 3.51 gina sample, found in
Mstools/Samples/Win32/Winnt/Gina on the MSDN CD-ROM.
*/
int
WINAPI
WlxLoggedOutSAS(
PVOID pWlxContext,
DWORD dwSasType,
PLUID pAuthenticationId,
PSID pLogonSid,
PDWORD pdwOptions,
PHANDLE phToken,
PWLX_MPR_NOTIFY_INFO pMprNotifyInfo,
PVOID * pProfile
)
{
int result;
PWLX_PROFILE_V1_0 pWlxProfile;
PWSTR szProfile;
// PMiniAccount pAccount;
PGlobals pGlobals;
pGlobals = (PGlobals) pWlxContext;
result = pWlxFuncs->WlxDialogBoxParam(
hGlobalWlx,
hDllInstance,
(LPTSTR) MAKEINTRESOURCE(IDD_LOGON_DIALOG),
NULL,
LogonDlgProc,
(LPARAM) pGlobals );
if (result == WLX_SAS_ACTION_LOGON)
{
result = AttemptLogon(pGlobals, pGlobals->pAccount,
pLogonSid, pAuthenticationId);
if (result == WLX_SAS_ACTION_LOGON)
{
*pdwOptions = 0;
*phToken = pGlobals->hUserToken;
if(!GetUserProfilePath(
pGlobals->pAccount->pszUsername,
pGlobals->pAccount->pszDomain,
&szProfile
)) {
//
// error occurred acquiring profile path. Log error
// here if appropriate. Default is to not provide
// profile information as szProfile will be NULL
// which causes *pProfile to be set to NULL
//
}
//
// if no profile is specified in the userinfo, let winlogon
// handle locating the registry hive
//
if(szProfile == NULL) {
*pProfile = NULL;
}
else {
pWlxProfile = (PWLX_PROFILE_V1_0)HeapAlloc(
GetProcessHeap(), 0, sizeof(WLX_PROFILE_V1_0) );
if(pWlxProfile == NULL) {
//
// error occurred allocating memory. Log error
// here if appropriate. Free memory associated
// with the acquired profile path. Default is to
// not provide profile information by supplying
// NULL as pProfile.
//
HeapFree(GetProcessHeap(), 0, szProfile);
*pProfile = NULL;
}
else {
//
// the allocation succeeded -- fill in the profile
// information
//
pWlxProfile->dwType = WLX_PROFILE_TYPE_V1_0;
pWlxProfile->pszProfile = szProfile;
*pProfile = pWlxProfile;
}
}
pMprNotifyInfo->pszUserName =
DupString(pGlobals->pAccount->pszUsername);
pMprNotifyInfo->pszDomain =
DupString(pGlobals->pAccount->pszDomain);
pMprNotifyInfo->pszPassword =
DupString(pGlobals->pAccount->pszPassword);
pMprNotifyInfo->pszOldPassword = NULL;
}
}
return(result);
}
/*
The following function obtains the profile path for the supplied user
on the supplied domain.
If the function succeeds, the return value is TRUE.
If the function fails, the return value is FALSE, and the ProfilePath
is set to NULL.
If no profile path exists for the supplied user, the ProfilePath
parameter will be set to NULL. If ProfilePath is non-NULL, the caller
is responsible for freeing the string via HeapFree(GetProcessHeap...).
This source code relies on the lm.h header file and the netapi32.lib
import library.
*/
BOOL
GetUserProfilePath(
IN LPWSTR UserName, // UserName to retrieve profile path
IN LPWSTR Domain, // Domain user resides on
OUT LPWSTR *ProfilePath // result profile path. NULL == no profile
)
{
LPWSTR wTargetComputer;
PUSER_INFO_3 ui3 = NULL;
PUSER_MODALS_INFO_2 umi2 = NULL;
NET_API_STATUS nas;
BOOL bSuccess = FALSE; // assume this function will fail
*ProfilePath = NULL;
//
// get the local domain name.
// NOTE: in a gina, it would be wise to retrieve this only once,
// in DllMain during DLL_PROCESS_ATTACH. The pointer could be
// saved in a global variable and then compared against below.
//
nas=NetUserModalsGet(NULL, 2, (LPBYTE *)&umi2);
if(nas != NO_ERROR) {
return FALSE;
}
__try {
//
// determine if you need to look up at the domain controller
//
if(lstrcmpiW(Domain, umi2->usrmod2_domain_name) == 0) {
//
// target computer is local machine
//
wTargetComputer = NULL;
}
else {
//
// target computer is the PDC computer name for the specified
// domain
//
nas=NetGetDCName(NULL, Domain, (LPBYTE *)&wTargetComputer);
if(nas != NO_ERROR) {
__leave;
}
}
//
// fetch the info for the user on the appropriate machine
//
nas=NetUserGetInfo(
wTargetComputer,
UserName, // user name
3, // info-level
(LPBYTE *) &ui3
);
if(nas != NO_ERROR) {
__leave;
}
//
// if there is no profile, indicate success.
// Note that *ProfilePath will be a NULL pointer
//
if(*ui3->usri3_profile == L'\0') {
bSuccess = TRUE;
__leave;
}
//
// allocate storage for profile string
//
*ProfilePath = HeapAlloc(GetProcessHeap(), 0,
(lstrlenW(ui3->usri3_profile) + 1) * sizeof(WCHAR) );
if(*ProfilePath == NULL) __leave;
//
// copy the appropriate structure memory to allocated storage
//
if(lstrcpyW(*ProfilePath, ui3->usri3_profile) != NULL)
bSuccess = TRUE; // indicate success if the copy succeeded
} // try
__finally {
//
// free the allocated buffers
//
if(umi2 != NULL)
NetApiBufferFree(umi2);
if(ui3 != NULL)
NetApiBufferFree(ui3);
if(wTargetComputer != NULL)
NetApiBufferFree(wTargetComputer);
if(!bSuccess) {
if(*ProfilePath != NULL) {
HeapFree(GetProcessHeap(), 0, *ProfilePath);
*ProfilePath = NULL;
}
}
} // finally
return bSuccess;
}
Additional query words: LogonUser LsaLogonUser
Keywords: kbcode kbgina kbhowto kbkernbase kbnetwork kbsecurity KB142790