NTSTATUS NetrInitIdentityInfo( OUT PVOID *pIdentity, IN OUT PDWORD pdwOffset, IN OUT PDWORD pdwSpaceLeft, IN PCWSTR pwszDomain, IN PCWSTR pwszWorkstation, IN PCWSTR pwszAccount, IN UINT32 ParamControl, IN UINT32 LogonIdLow, IN UINT32 LogonIdHigh, IN OUT PDWORD pdwSize ) { NTSTATUS ntStatus = STATUS_SUCCESS; DWORD dwError = ERROR_SUCCESS; PVOID pBuffer = pIdentity; PWSTR pwszNbtWorkstation = NULL; size_t sNbtWorkstationLen = 0; BAIL_ON_INVALID_PTR(pdwOffset, ntStatus); BAIL_ON_INVALID_PTR(pwszWorkstation, ntStatus); BAIL_ON_INVALID_PTR(pwszAccount, ntStatus); BAIL_ON_INVALID_PTR(pdwSize, ntStatus); /* * Create "\\WORKSTATION" name */ dwError = LwWc16sLen(pwszWorkstation, &sNbtWorkstationLen); BAIL_ON_WIN_ERROR(dwError); ntStatus = NetrAllocateMemory(OUT_PPVOID(&pwszNbtWorkstation), sizeof(WCHAR) * (sNbtWorkstationLen + 3)); BAIL_ON_NT_STATUS(ntStatus); if (sw16printfw( pwszNbtWorkstation, sNbtWorkstationLen + 3, L"\\\\%ws", pwszWorkstation) < 0) { ntStatus = ErrnoToNtStatus(errno); BAIL_ON_NT_STATUS(ntStatus); } LWBUF_ALLOC_UNICODE_STRING_FROM_WC16STR(pBuffer, pwszDomain); LWBUF_ALLOC_DWORD(pBuffer, ParamControl); LWBUF_ALLOC_DWORD(pBuffer, LogonIdLow); LWBUF_ALLOC_DWORD(pBuffer, LogonIdHigh); LWBUF_ALLOC_UNICODE_STRING_FROM_WC16STR(pBuffer, pwszAccount); LWBUF_ALLOC_UNICODE_STRING_FROM_WC16STR(pBuffer, pwszNbtWorkstation); cleanup: if (pwszNbtWorkstation) { NetrFreeMemory(pwszNbtWorkstation); } if (ntStatus == STATUS_SUCCESS && dwError != ERROR_SUCCESS) { ntStatus = LwWin32ErrorToNtStatus(dwError); } return ntStatus; error: goto cleanup; }
NTSTATUS NetrSamLogoff( IN NETR_BINDING hBinding, IN NetrCredentials *pCreds, IN PCWSTR pwszServer, IN PCWSTR pwszDomain, IN PCWSTR pwszComputer, IN PCWSTR pwszUsername, IN PCWSTR pwszPassword, IN UINT32 LogonLevel ) { NTSTATUS ntStatus = STATUS_SUCCESS; DWORD dwError = ERROR_SUCCESS; PWSTR pwszServerName = NULL; PWSTR pwszComputerName = NULL; NetrAuth *pAuth = NULL; NetrAuth *pReturnedAuth = NULL; NetrLogonInfo LogonInfo = {0}; NetrPasswordInfo *pPassInfo = NULL; DWORD dwOffset = 0; DWORD dwSpaceLeft = 0; DWORD dwSize = 0; BAIL_ON_INVALID_PTR(hBinding, ntStatus); BAIL_ON_INVALID_PTR(pCreds, ntStatus); BAIL_ON_INVALID_PTR(pwszServer, ntStatus); /* pwszDomain can be NULL */ BAIL_ON_INVALID_PTR(pwszComputer, ntStatus); BAIL_ON_INVALID_PTR(pwszUsername, ntStatus); BAIL_ON_INVALID_PTR(pwszPassword, ntStatus); if (!(LogonLevel == 1 || LogonLevel == 3 || LogonLevel == 5)) { ntStatus = STATUS_INVALID_INFO_CLASS; BAIL_ON_NT_STATUS(ntStatus); } dwError = LwAllocateWc16String(&pwszServerName, pwszServer); BAIL_ON_WIN_ERROR(dwError); dwError = LwAllocateWc16String(&pwszComputerName, pwszComputer); BAIL_ON_WIN_ERROR(dwError); /* Create authenticator info with credentials chain */ ntStatus = NetrAllocateMemory(OUT_PPVOID(&pAuth), sizeof(NetrAuth)); BAIL_ON_NT_STATUS(ntStatus); pCreds->sequence += 2; NetrCredentialsCliStep(pCreds); pAuth->timestamp = pCreds->sequence; memcpy(pAuth->cred.data, pCreds->cli_chal.data, sizeof(pAuth->cred.data)); /* Allocate returned authenticator */ ntStatus = NetrAllocateMemory(OUT_PPVOID(&pReturnedAuth), sizeof(NetrAuth)); BAIL_ON_NT_STATUS(ntStatus); ntStatus = NetrAllocateLogonPasswordInfo(NULL, &dwOffset, NULL, pwszDomain, pwszComputerName, pwszUsername, pwszPassword, pCreds, &dwSize); BAIL_ON_NT_STATUS(ntStatus); dwSpaceLeft = dwSize; dwSize = 0; dwOffset = 0; ntStatus = NetrAllocateMemory(OUT_PPVOID(&pPassInfo), dwSpaceLeft); BAIL_ON_NT_STATUS(ntStatus); ntStatus = NetrAllocateLogonPasswordInfo(pPassInfo, &dwOffset, &dwSpaceLeft, pwszDomain, pwszComputerName, pwszUsername, pwszPassword, pCreds, &dwSize); BAIL_ON_NT_STATUS(ntStatus); switch (LogonLevel) { case 1: LogonInfo.password1 = pPassInfo; break; case 3: LogonInfo.password3 = pPassInfo; break; case 5: LogonInfo.password5 = pPassInfo; break; } DCERPC_CALL(ntStatus, cli_NetrLogonSamLogoff(hBinding, pwszServerName, pwszComputerName, pAuth, pReturnedAuth, LogonLevel, &LogonInfo)); BAIL_ON_NT_STATUS(ntStatus); cleanup: LW_SAFE_FREE_MEMORY(pwszServerName); LW_SAFE_FREE_MEMORY(pwszComputerName); if (pAuth) { NetrFreeMemory(pAuth); } if (pReturnedAuth) { NetrFreeMemory(pReturnedAuth); } if (pPassInfo) { NetrFreeMemory(pPassInfo); } if (ntStatus == STATUS_SUCCESS && dwError != ERROR_SUCCESS) { ntStatus = LwWin32ErrorToNtStatus(dwError); } return ntStatus; error: goto cleanup; }
static DWORD TestNetlogonEnumDomainTrusts( PTEST pTest, PCWSTR pwszHostname, PCWSTR pwszBindingString, PCREDENTIALS pCreds, PPARAMETER pOptions, DWORD dwOptcount ) { const DWORD dwDefTrustFlags = NETR_TRUST_FLAG_IN_FOREST | NETR_TRUST_FLAG_OUTBOUND | NETR_TRUST_FLAG_TREEROOT | NETR_TRUST_FLAG_PRIMARY | NETR_TRUST_FLAG_NATIVE | NETR_TRUST_FLAG_INBOUND; BOOLEAN bRet = TRUE; NTSTATUS ntStatus = STATUS_SUCCESS; WINERROR err = ERROR_SUCCESS; NETR_BINDING hNetr = NULL; enum param_err perr = perr_success; DWORD dwTrustFlags = 0; DWORD dwCount = 0; NetrDomainTrust *pTrusts = NULL; DWORD iTrust = 0; TESTINFO(pTest, pwszHostname); perr = fetch_value(pOptions, dwOptcount, "trustflags", pt_uint32, &dwTrustFlags, &dwDefTrustFlags); if (!perr_is_ok(perr)) perr_fail(perr); PARAM_INFO("trustflags", pt_uint32, &dwTrustFlags); bRet &= CreateRpcBinding(OUT_PPVOID(&hNetr), RPC_NETLOGON_BINDING, pwszHostname, pwszBindingString, pCreds); CALL_NETAPI(err, DsrEnumerateDomainTrusts(hNetr, pwszHostname, dwTrustFlags, &pTrusts, &dwCount)); BAIL_ON_WIN_ERROR(err); bRet &= TestValidateDomainTrusts(pTrusts, dwCount); for (iTrust = 0; iTrust < dwCount; iTrust++) { OUTPUT_ARG_WSTR(pTrusts[iTrust].netbios_name); OUTPUT_ARG_WSTR(pTrusts[iTrust].dns_name); OUTPUT_ARG_UINT(pTrusts[iTrust].trust_flags); } error: if (pTrusts) { NetrFreeMemory(pTrusts); } NetrFreeBinding(&hNetr); if (ntStatus != STATUS_SUCCESS || err != ERROR_SUCCESS) { bRet = FALSE; } return bRet; }
static DWORD TestNetlogonEnumTrustedDomains( PTEST pTest, PCWSTR pwszHostname, PCWSTR pwszBindingString, PCREDENTIALS pCreds, PPARAMETER pOptions, DWORD dwOptcount ) { PCSTR pszDefServer = "TEST"; BOOLEAN bRet = TRUE; NTSTATUS ntStatus = STATUS_SUCCESS; NETR_BINDING hNetr = NULL; enum param_err perr = perr_success; PWSTR pwszServer = NULL; DWORD dwCount = 0; NetrDomainTrust *pTrusts = NULL; DWORD iTrust = 0; TESTINFO(pTest, pwszHostname); perr = fetch_value(pOptions, dwOptcount, "server", pt_w16string, &pwszServer, &pszDefServer); if (!perr_is_ok(perr)) perr_fail(perr); PARAM_INFO("server", pt_w16string, pwszServer); bRet &= CreateRpcBinding(OUT_PPVOID(&hNetr), RPC_NETLOGON_BINDING, pwszHostname, pwszBindingString, pCreds); CALL_MSRPC(ntStatus, NetrEnumerateTrustedDomainsEx(hNetr, pwszServer, &pTrusts, &dwCount)); BAIL_ON_NT_STATUS(ntStatus); bRet &= TestValidateDomainTrusts(pTrusts, dwCount); for (iTrust = 0; iTrust < dwCount; iTrust++) { OUTPUT_ARG_WSTR(pTrusts[iTrust].netbios_name); OUTPUT_ARG_WSTR(pTrusts[iTrust].dns_name); OUTPUT_ARG_UINT(pTrusts[iTrust].trust_flags); } error: if (pTrusts) { NetrFreeMemory(pTrusts); } NetrFreeBinding(&hNetr); LW_SAFE_FREE_MEMORY(pwszServer); if (ntStatus != STATUS_SUCCESS) { bRet = FALSE; } return bRet; }
static DWORD TestNetlogonSamLogonInteractiveEx( PTEST pTest, PCWSTR pwszHostname, PCWSTR pwszBindingString, PCREDENTIALS pCreds, PPARAMETER pOptions, DWORD dwOptcount ) { PCSTR pszDefComputer = "TestWks4"; PCSTR pszDefMachpass = "******"; const DWORD dwDefLogonLevel = 0; const DWORD dwDefValidationLevel = 2; BOOLEAN bRet = TRUE; DWORD dwError = ERROR_SUCCESS; NETR_BINDING hNetr = NULL; NETR_BINDING hSchn = NULL; enum param_err perr = perr_success; NetrCredentials NetlogonCreds = {0}; NetrValidationInfo **ppSamLogonInfo = NULL; PSTR pszComputer = NULL; PSTR pszMachpass = NULL; PWSTR pwszComputer = NULL; PWSTR pwszMachAcct = NULL; PWSTR pwszMachpass = NULL; PWSTR pwszServer = NULL; PWSTR pwszDomain = NULL; PWSTR pwszDnsDomain = NULL; PWSTR pwszUsername = NULL; PWSTR pwszPassword = NULL; DWORD dwLogonLevel = 0; DWORD dwValidationLevel = 0; DWORD pDefaultLogonLevels[] = { 1, 3, 4}; DWORD numLogonLevels = (sizeof(pDefaultLogonLevels) /sizeof(pDefaultLogonLevels[0])); PDWORD pLogonLevels = NULL; DWORD pDefaultValidationLevels[] = { 2, 3, 6 }; DWORD numValidationLevels = (sizeof(pDefaultValidationLevels) /sizeof(pDefaultValidationLevels[0])); PDWORD pValidationLevels = NULL; DWORD iLogonLevel = 0; DWORD iValidationLevel = 0; TESTINFO(pTest, pwszHostname); perr = fetch_value(pOptions, dwOptcount, "computer", pt_w16string, &pwszComputer, &pszDefComputer); if (!perr_is_ok(perr)) perr_fail(perr); perr = fetch_value(pOptions, dwOptcount, "machpass", pt_w16string, &pwszMachpass, &pszDefMachpass); if (!perr_is_ok(perr)) perr_fail(perr); perr = fetch_value(pOptions, dwOptcount, "server", pt_w16string, &pwszServer, NULL); if (perr_is_err(perr)) perr_fail(perr); perr = fetch_value(pOptions, dwOptcount, "domain", pt_w16string, &pwszDomain, NULL); if (perr_is_err(perr)) perr_fail(perr); perr = fetch_value(pOptions, dwOptcount, "dnsdomain", pt_w16string, &pwszDnsDomain, NULL); if (perr_is_err(perr)) perr_fail(perr); perr = fetch_value(pOptions, dwOptcount, "username", pt_w16string, &pwszUsername, NULL); if (!perr_is_ok(perr)) perr_fail(perr); perr = fetch_value(pOptions, dwOptcount, "password", pt_w16string, &pwszPassword, NULL); if (!perr_is_ok(perr)) perr_fail(perr); perr = fetch_value(pOptions, dwOptcount, "logon_level", pt_uint32, &dwLogonLevel, &dwDefLogonLevel); if (!perr_is_ok(perr)) perr_fail(perr); perr = fetch_value(pOptions, dwOptcount, "validation_level", pt_uint32, &dwValidationLevel, &dwDefValidationLevel); if (!perr_is_ok(perr)) perr_fail(perr); dwError = LwWc16sToMbs(pwszComputer, &pszComputer); BAIL_ON_WIN_ERROR(dwError); dwError = LwWc16sToMbs(pwszMachpass, &pszMachpass); BAIL_ON_WIN_ERROR(dwError); if (strcmp(pszComputer, pszDefComputer) == 0 && strcmp(pszMachpass, pszDefMachpass) == 0) { LW_SAFE_FREE_MEMORY(pwszComputer); LW_SAFE_FREE_MEMORY(pwszMachpass); dwError = GetMachinePassword( &pwszDnsDomain, &pwszDomain, &pwszMachAcct, &pwszMachpass, &pwszComputer); BAIL_ON_WIN_ERROR(dwError); } PARAM_INFO("computer", pt_w16string, pwszComputer); PARAM_INFO("machpass", pt_w16string, pwszMachpass); PARAM_INFO("server", pt_w16string, pwszServer); PARAM_INFO("domain", pt_w16string, pwszDomain); PARAM_INFO("dnsdomain", pt_w16string, pwszDnsDomain); PARAM_INFO("username", pt_w16string, pwszUsername); PARAM_INFO("password", pt_w16string, pwszPassword); PARAM_INFO("logon_level", pt_int32, &dwLogonLevel); PARAM_INFO("validation_level", pt_int32, &dwValidationLevel); bRet &= CreateRpcBinding(OUT_PPVOID(&hNetr), RPC_NETLOGON_BINDING, pwszHostname, pwszBindingString, pCreds); bRet &= CallOpenSchannel(hNetr, pwszMachAcct, pwszHostname, pwszServer, pwszDomain, pwszDnsDomain, pwszComputer, pwszMachpass, &NetlogonCreds, &hSchn); if (hSchn == NULL) { bRet = FALSE; goto done; } if (dwLogonLevel) { pLogonLevels = &dwLogonLevel; numLogonLevels = 1; } else { pLogonLevels = pDefaultLogonLevels; } if (dwValidationLevel) { pValidationLevels = &dwValidationLevel; numValidationLevels = 1; } else { pValidationLevels = pDefaultValidationLevels; } for (iLogonLevel = 0; iLogonLevel < numLogonLevels; iLogonLevel++) { bRet &= CallNetrSamLogonInteractiveEx( hSchn, &NetlogonCreds, pwszServer, pwszDomain, pwszComputer, pwszUsername, pwszPassword, pLogonLevels[iLogonLevel], pValidationLevels, numValidationLevels, &ppSamLogonInfo); if (bRet) { bRet &= TestValidateSamLogonInfo(&ppSamLogonInfo, 1); for (iValidationLevel = 0; ppSamLogonInfo && iValidationLevel <= 6; iValidationLevel++) { if (ppSamLogonInfo[iValidationLevel]) { NetrFreeMemory(ppSamLogonInfo[iValidationLevel]); ppSamLogonInfo[iValidationLevel] = NULL; } } } } bRet &= CallCloseSchannel(hSchn); done: error: for (iValidationLevel = 0; ppSamLogonInfo && iValidationLevel <= 6; iValidationLevel++) { if (ppSamLogonInfo[iValidationLevel]) { NetrFreeMemory(ppSamLogonInfo[iValidationLevel]); ppSamLogonInfo[iValidationLevel] = NULL; } } NetrFreeBinding(&hNetr); LW_SAFE_FREE_MEMORY(pwszMachAcct); LW_SECURE_FREE_WSTRING(pwszMachpass); LW_SAFE_FREE_MEMORY(pwszComputer); LW_SAFE_FREE_MEMORY(pwszServer); LW_SAFE_FREE_MEMORY(pwszDomain); LW_SAFE_FREE_MEMORY(pwszUsername); LW_SAFE_FREE_MEMORY(pwszPassword); LW_SAFE_FREE_MEMORY(pszComputer); LW_SAFE_FREE_MEMORY(pszMachpass); return (int)bRet; }
static DWORD TestNetlogonGetDcName( PTEST pTest, PCWSTR pwszHostname, PCWSTR pwszBindingString, PCREDENTIALS pCreds, PPARAMETER pOptions, DWORD dwOptcount ) { const DWORD dwDefGetDcFlags = DS_FORCE_REDISCOVERY; const PSTR pszDefDomainName = "DOMAIN"; BOOLEAN bRet = TRUE; NTSTATUS ntStatus = STATUS_SUCCESS; WINERROR err = ERROR_SUCCESS; NETR_BINDING hNetr = NULL; enum param_err perr = perr_success; DWORD dwGetDcFlags = 0; PWSTR pwszDomainName = NULL; DsrDcNameInfo *pInfo = NULL; TESTINFO(pTest, pwszHostname); perr = fetch_value(pOptions, dwOptcount, "getdcflags", pt_uint32, &dwGetDcFlags, &dwDefGetDcFlags); if (!perr_is_ok(perr)) perr_fail(perr); perr = fetch_value(pOptions, dwOptcount, "domainname", pt_w16string, &pwszDomainName, &pszDefDomainName); if (!perr_is_ok(perr)) perr_fail(perr); PARAM_INFO("getdcflags", pt_uint32, &dwGetDcFlags); PARAM_INFO("domainname", pt_w16string, pwszDomainName); bRet &= CreateRpcBinding(OUT_PPVOID(&hNetr), RPC_NETLOGON_BINDING, pwszHostname, pwszBindingString, pCreds); CALL_NETAPI(err, DsrGetDcName(hNetr, pwszHostname, pwszDomainName, NULL, NULL, dwGetDcFlags, &pInfo)); BAIL_ON_WIN_ERROR(err); error: if (pInfo) { NetrFreeMemory(pInfo); } NetrFreeBinding(&hNetr); if (ntStatus != STATUS_SUCCESS || err != ERROR_SUCCESS) { bRet = FALSE; } return bRet; }