/** @framework_function="RPCClientInterfaceTerminate" Purpose: Teardown the RPC client interface by unbinding and freeing the handles. <br> <br> Notes: <br> <br> MSDN_Ref: HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA378651.aspx <br> HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA375613.aspx <br> HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA375588.aspx <br> */ UINT32 RPCClientInterfaceTerminate() { RPC_STATUS status = RPC_S_OK; if(pRPCData && pRPCData->bindingHandle) { if(pRPCData->isBound) { status = RpcBindingUnbind(pRPCData->bindingHandle); if(status != RPC_S_OK) HlprLogError(L"RPCClientInterfaceTerminate : RpcBindingUnbind() [status: %#x]", status); else pRPCData->isBound = FALSE; } status = RpcBindingFree(&(pRPCData->bindingHandle)); if(status != RPC_S_OK) HlprLogError(L"RPCClientInterfaceTerminate : RpcBindingFree() [status: %#x]", status); } HLPR_DELETE(pRPCData); return status; }
UINT32 HlprRegistryDeleteValue(_In_ HKEY hKey, _In_opt_ PWSTR pSubKey, _In_ PWSTR pValueName) { UINT32 status = NO_ERROR; HKEY keyHandle = 0; if(pSubKey) { UINT32 dispositionValue = 0; status = RegCreateKeyEx(hKey, pSubKey, 0, 0, REG_OPTION_NON_VOLATILE, KEY_WRITE, 0, &keyHandle, (LPDWORD)&dispositionValue); if(status != NO_ERROR) { HlprLogError(L"HlprRegistryDeleteValue : RegCreateKeyEx() [status: %#x][subKey: %s]", status, pSubKey); HLPR_BAIL; } } else keyHandle = hKey; status = RegDeleteValue(keyHandle, pValueName); if(status != NO_ERROR) { if(status != ERROR_FILE_NOT_FOUND) { HlprLogError(L"HlprRegistryDeleteValue : RegDeleteValue() [status: %#x][Value: %s%s%s]", status, pSubKey ? pSubKey : L"", pSubKey ? L"\\" : L"", pValueName); HLPR_BAIL; } status = NO_ERROR; } HLPR_BAIL_LABEL: return status; }
UINT32 HlprIPAddressV4StringToValue(_In_ PCWSTR pIPv4AddressString, _Inout_ UINT32* pIPv4Address) { ASSERT(pIPv4AddressString); ASSERT(pIPv4Address); UINT32 status = NO_ERROR; #pragma warning(push) #pragma warning(disable: 24002) /// function is IPv4 specific, however there is a v6 counter-part #pragma warning(disable: 24007) /// function is IPv4 specific, however there is a v6 counter-part if(HlprIPAddressV4StringIsValidFormat(pIPv4AddressString)) { UINT16 port = 0; IN_ADDR v4Addr = {0}; status = RtlIpv4StringToAddressEx(pIPv4AddressString, FALSE, &v4Addr, &port); if(status != NO_ERROR) { HlprLogError(L"HlprIPAddressV4StringToValue : RtlIpv4StringToAddressEx() [status: %#x][pIPv4AddressString: %s]", status, pIPv4AddressString); HLPR_BAIL; } CopyMemory(pIPv4Address, &v4Addr, IPV4_ADDRESS_LENGTH); *pIPv4Address = ntohl(*pIPv4Address); } else { status = ERROR_INVALID_PARAMETER; HlprLogError(L"HlprIPAddressV4StringToValue() [status: %#x][pIPv4AddressString: %#s]", status, pIPv4AddressString); } #pragma warning(pop) HLPR_BAIL_LABEL: return status; }
/* [fault_status][comm_status] */ error_status_t RPCInvokeScenarioProxy(/* [in] */ handle_t rpcBindingHandle, /* [in] */ WFPSAMPLER_SCENARIO scenario, /* [in] */ FWPM_CHANGE_TYPE changeType, /* [ref][in] */ __RPC__in const FWPM_FILTER0* pFilter, /* [unique][in] */ __RPC__in_opt const PC_PROXY_DATA* pPCProxyData) { UNREFERENCED_PARAMETER(rpcBindingHandle); UNREFERENCED_PARAMETER(scenario); ASSERT(pFilter); ASSERT(scenario == SCENARIO_PROXY); ASSERT(changeType < FWPM_CHANGE_TYPE_MAX); UINT32 status = NO_ERROR; if(changeType == FWPM_CHANGE_ADD) { if(pPCProxyData) status = ScenarioProxyAdd(pFilter, pPCProxyData); else { status = ERROR_INVALID_PARAMETER; HlprLogError(L"RPCInvokeScenarioProxy() [status: %#x][pPCProxyData: %#x]", status, pPCProxyData); } } else status = ScenarioProxyRemove(pFilter); return status; }
/* [fault_status][comm_status] */ error_status_t RPCInvokeScenarioBasicPacketModification(/* [in] */ handle_t rpcBindingHandle, /* [in] */ WFPSAMPLER_SCENARIO scenario, /* [in] */ FWPM_CHANGE_TYPE changeType, /* [ref][in] */ __RPC__in const FWPM_FILTER0* pFilter, /* [unique][in] */ __RPC__in_opt const PC_BASIC_PACKET_MODIFICATION_DATA* pPCBasicPacketModificationData) { UNREFERENCED_PARAMETER(rpcBindingHandle); UNREFERENCED_PARAMETER(scenario); ASSERT(pFilter); ASSERT(scenario == SCENARIO_BASIC_PACKET_MODIFICATION); ASSERT(changeType < FWPM_CHANGE_TYPE_MAX); UINT32 status = NO_ERROR; if(changeType == FWPM_CHANGE_ADD) { if(pPCBasicPacketModificationData) status = PrvBasicPacketModificationScenarioAdd(pFilter, pPCBasicPacketModificationData); else { status = ERROR_INVALID_PARAMETER; HlprLogError(L"RPCInvokeScenarioBasicPacketModification() [status: %#x][pPCBasicPacketModificationData: %#x]", status, pPCBasicPacketModificationData); } } else status = PrvBasicPacketModificationScenarioRemove(pFilter); return status; }
UINT32 HlprFwpmProviderContextAdd(_In_ const HANDLE engineHandle, _Inout_ FWPM_PROVIDER_CONTEXT* pProviderContext) { ASSERT(engineHandle); ASSERT(pProviderContext); UINT32 status = NO_ERROR; status = FwpmProviderContextAdd(engineHandle, pProviderContext, 0, &(pProviderContext->providerContextId)); if(status != NO_ERROR) { if(status == FWP_E_ALREADY_EXISTS) { HlprLogInfo(L"ProviderContext Already Exists"); status = NO_ERROR; } else HlprLogError(L"HlprFwpmProviderContextAdd : FwpmProviderContextAdd() [status: %#x]", status); } return status; }
UINT32 HlprFwpmProviderContextDeleteByKey(_In_ const HANDLE engineHandle, _In_ const GUID* pProviderContextKey) { ASSERT(engineHandle); ASSERT(pProviderContextKey); UINT32 status = NO_ERROR; status = FwpmProviderContextDeleteByKey(engineHandle, pProviderContextKey); if(status != NO_ERROR) { if(status != FWP_E_IN_USE && status != FWP_E_BUILTIN_OBJECT && status != FWP_E_PROVIDER_CONTEXT_NOT_FOUND) HlprLogError(L"HlprFwpmProviderContextDeleteByKey : FwpmProviderContextDeleteByKey() [status: %#x]", status); else { HlprLogInfo(L"HlprFwpmProviderContextDeleteByKey : FwpmProviderContextDeleteByKey() [status: %#x]", status); status = NO_ERROR; } } return status; }
UINT32 HlprThreadPoolDataPopulate(_Inout_ THREADPOOL_DATA* pThreadPoolData, _In_ const PTP_CLEANUP_GROUP_CANCEL_CALLBACK pGroupCancelFn) { ASSERT(pThreadPoolData); UINT32 status = NO_ERROR; InitializeThreadpoolEnvironment(&(pThreadPoolData->callbackEnvironment)); pThreadPoolData->pThreadPool = CreateThreadpool(0); if(pThreadPoolData->pThreadPool == 0) { status = GetLastError(); HlprLogError(L"HlprThreadPoolDataPopulate : CreateThreadPool() [status: %#x]", status); HLPR_BAIL; } pThreadPoolData->pCleanupGroup = CreateThreadpoolCleanupGroup(); if(pThreadPoolData->pCleanupGroup == 0) { status = GetLastError(); HlprLogError(L"HlprThreadPoolDataPopulate : CreateThreadPool() [status: %#x]", status); HLPR_BAIL; } SetThreadpoolCallbackPool(&(pThreadPoolData->callbackEnvironment), pThreadPoolData->pThreadPool); SetThreadpoolCallbackCleanupGroup(&(pThreadPoolData->callbackEnvironment), pThreadPoolData->pCleanupGroup, pGroupCancelFn); HLPR_BAIL_LABEL: if(status != NO_ERROR) HlprThreadPoolDataPurge(pThreadPoolData); return status; }
UINT32 PrvScenarioAppContainerRegister() { UINT32 status = NO_ERROR; status = NetworkIsolationRegisterForAppContainerChanges(0, PrvScenarioAppContainerActOnChange, 0, ®istrationHandle); if(status != NO_ERROR) HlprLogError(L"ScenarioAppContainerRegister : NetworkIsolationRegisterForAppContainerChanges() [status: %#x]", status); return status; }
UINT32 PrvScenarioAppContainerUnregister() { UINT32 status = NO_ERROR; if(registrationHandle) { status = NetworkIsolationUnregisterForAppContainerChanges(registrationHandle); if(status != NO_ERROR) HlprLogError(L"PrvScenarioAppContainerUnregister : NetworkIsolationUnregisterForAppContainerChanges() [status: %#x]", status); else registrationHandle = 0; } return status; }
DWORD WindowsFirewallNotifyThreadStartRoutine(_In_ LPVOID lpThreadParameter) { ASSERT(lpThreadParameter); UINT32 status = NO_ERROR; THREAD_DATA* pThreadData = (THREAD_DATA*)lpThreadParameter; SERVICE_NOTIFY svcNotify = {0}; HlprEventSet(pThreadData->threadStartEvent); svcNotify.dwVersion = SERVICE_NOTIFY_STATUS_CHANGE; svcNotify.pfnNotifyCallback = WindowsFirewallNotification; svcNotify.pContext = pWFNotifyThread; status = HlprServiceNotificationStateChangeRegister(L"MPSSvc", &svcNotify, SERVICE_NOTIFY_RUNNING, &scmHandle, &mpsSvcHandle); HLPR_BAIL_ON_FAILURE(status); status = WaitForSingleObjectEx(mpsSvcHandle, INFINITE, TRUE); if(status != WAIT_IO_COMPLETION) { if(status == WAIT_FAILED) status = GetLastError(); HlprLogError(L"WindowsFirewallNotifyThreadStartRoutine : WaitForSingleObjectEx() [status: %#x]", status); } HLPR_BAIL_LABEL: HLPR_CLOSE_SERVICE_HANDLE(mpsSvcHandle); HLPR_CLOSE_SERVICE_HANDLE(scmHandle); return status; }
/** @helper_function="HlprIPAddressV6StringIsValidFormat" Purpose: Determine if a string may be an IPv6 address by verifying the string: <br> is at least 3 characters <br> has at least 2 colons (':') <br> is not more than 40 characters <br> <br> Notes: <br> <br> MSDN_Ref: <br> */ BOOLEAN HlprIPAddressV6StringIsValidFormat(_In_ PCWSTR pIPAddress) { ASSERT(pIPAddress); UINT32 status = NO_ERROR; BOOLEAN isIPv6Address = FALSE; size_t addressSize = 0; status = StringCchLength(pIPAddress, STRSAFE_MAX_CCH, &addressSize); if(FAILED(status)) { HlprLogError(L"HlprIPAddressV6StringIsValidFormat : StringCchLength() [status: %#x]", status); HLPR_BAIL; } if(addressSize > 2 && /// minimum address size: ::1 addressSize < 40) /// maximum address size: FFFF:FFFF:FFFF:FFFF:FFFF:FFFF:FFFF:FFFF { UINT32 numColons = 0; for(UINT32 index = 0; index < addressSize; index++) { if(pIPAddress[index] == ':') numColons++; } if(numColons > 1 && numColons < 8) isIPv6Address = TRUE; } HLPR_BAIL_LABEL: return isIPv6Address; }
/** @helper_function="HlprIPAddressV4StringIsValidFormat" Purpose: Determine if a string may be an IPv4 address by verifying the string: <br> is at least 7 characters <br> has at least 3 decimals('.') <br> is not more than 16 characters <br> <br> Notes: <br> <br> MSDN_Ref: <br> */ BOOLEAN HlprIPAddressV4StringIsValidFormat(_In_ PCWSTR pIPAddress) { ASSERT(pIPAddress); UINT32 status = NO_ERROR; BOOLEAN isIPv4Address = FALSE; size_t addressSize = 0; status = StringCchLength(pIPAddress, STRSAFE_MAX_CCH, &addressSize); if(FAILED(status)) { HlprLogError(L"HlprIPAddressV4StringIsValidFormat : StringCchLength() [status: %#x]", status); HLPR_BAIL; } if(addressSize > 6 && /// minimum address size: 0.0.0.0 addressSize < 16) /// maximum address size: 255.255.255.255 { UINT32 numPeriods = 0; for(UINT32 index = 0; index < addressSize; index++) { if(pIPAddress[index] == '.') numPeriods++; } if(numPeriods == 3) isIPv4Address = TRUE; } HLPR_BAIL_LABEL: return isIPv4Address; }
/** @helper_function="HlprEthernetMACAddressStringIsValidFormat" Purpose: Determine if a string may be an Ethernet MAC address by verifying the string: <br> is at least 17 characters <br> has at least 5 colons(':') or hyphens('-') <br> <br> Notes: <br> <br> MSDN_Ref: <br> */ BOOLEAN HlprEthernetMACAddressStringIsValidFormat(_In_ PCWSTR pEthernetMACAddressString) { BOOLEAN isEthernetMACAddress = FALSE; if(pEthernetMACAddressString) { UINT32 status = NO_ERROR; size_t stringLength = 0; status = StringCchLength(pEthernetMACAddressString, STRSAFE_MAX_CCH, &stringLength); if(status != ERROR_SUCCESS) { HlprLogError(L"HlprEthernetMACAddressStringIsValidFormat : StringCchLength() [status: %#x]", status); HLPR_BAIL; } else if(stringLength <= IEEE_802_ADDRESS_STRING_BUFFER) { if(wcschr(pEthernetMACAddressString, L':')) { UINT32 numColons = 0; for(UINT32 index = 0; index < stringLength; index++) { if(pEthernetMACAddressString[index] == L':') numColons++; } if(numColons == 5) isEthernetMACAddress = TRUE; } else { if(wcschr(pEthernetMACAddressString, L'-')) { UINT32 numHyphens = 0; for(UINT32 index = 0; index < stringLength; index++) { if(pEthernetMACAddressString[index] == L'-') numHyphens++; } if(numHyphens == 5) isEthernetMACAddress = TRUE; } } } } HLPR_BAIL_LABEL: if(!isEthernetMACAddress) HlprLogError(L"HlprEthernetMACAddressStringIsValidFormat() [status: %#x][pEthernetMACAddressString: %s]", ERROR_INVALID_DATA, pEthernetMACAddressString); return isEthernetMACAddress; }
/* [fault_status][comm_status] */ error_status_t RPCInvokeScenarioAppContainer(/* [in] */ handle_t rpcBindingHandle, /* [in] */ WFPSAMPLER_SCENARIO scenario, /* [in] */ FWPM_CHANGE_TYPE changeType, /* [in] */ BOOLEAN trustWSH, /* [in] */ BOOLEAN persistent, /* [in] */ BOOLEAN bootTime) { UINT32 status = NO_ERROR; UNREFERENCED_PARAMETER(rpcBindingHandle); UNREFERENCED_PARAMETER(scenario); if(scenario < SCENARIO_MAX && changeType < FWPM_CHANGE_TYPE_MAX) { switch(scenario) { case SCENARIO_APP_CONTAINER: { if(changeType == FWPM_CHANGE_ADD) { if(!scenarioConfigured) status = ScenarioAppContainerAdd(trustWSH, persistent, bootTime); else { status = ERROR_ALREADY_EXISTS; HlprLogError(L"RPCInvokeScenarioAppContainer() [status: %#x]", status); } } else status = ScenarioAppContainerRemove(trustWSH); break; } default: { status = ERROR_INVALID_PARAMETER; HlprLogError(L"RPCInvokeScenarioAppContainer() [status: %#x][scenario: %d]", status, scenario); break; } } } else { status = ERROR_INVALID_PARAMETER; HlprLogError(L"RPCInvokeScenarioAppContainer() [status: %#x][scenario: %#x][changeType: %#x]", status, scenario, changeType); } return status; }
/** @private_function="PrvRPCTroubleshootError" Purpose: Function to retrieve extended error information about RPC's inner workings. <br> <br> Notes: <br> <br> MSDN_Ref: HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA378651.aspx <br> HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA374351.aspx <br> HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA375686.aspx <br> HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA375668.aspx <br> HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA375664.aspx <br> */ VOID PrvRPCTroubleshootError() { RPC_STATUS status = RPC_S_OK; RPC_ERROR_ENUM_HANDLE enumHandle = {0}; status = RpcErrorStartEnumeration(&enumHandle); if(status != RPC_S_OK) { if(status != RPC_S_ENTRY_NOT_FOUND) HlprLogError(L"PrvRPCTroubleshootError : RpcErrorStartEnumeration() [status: %#x]", status); HLPR_BAIL; } for(; status == RPC_S_OK; ) { RPC_EXTENDED_ERROR_INFO errorInfo = {0}; errorInfo.Version = RPC_EEINFO_VERSION; errorInfo.NumberOfParameters = MaxNumberOfEEInfoParams; status = RpcErrorGetNextRecord(&enumHandle, TRUE, &errorInfo); if(status == RPC_S_ENTRY_NOT_FOUND) { HlprLogInfo(L"PrvRPCTroubleshootError : RpcErrorGetNextRecord() [status: %#x]", status); HLPR_BAIL; } else if(status != RPC_S_OK) { HlprLogError(L"PrvRPCTroubleshootError : RpcErrorGetNextRecord() [status: %#x]", status); HLPR_BAIL; } else { if(errorInfo.ComputerName) { HlprLogInfo(L" [ComputerName: %S]", errorInfo.ComputerName); HeapFree(GetProcessHeap(), 0, errorInfo.ComputerName); } HlprLogInfo(L" [ProcessID: %d]", errorInfo.ProcessID); HlprLogInfo(L" [SystemTime: %02d/%02d/%04d %02d:%02d:%02d:%03d]", errorInfo.u.SystemTime.wMonth, errorInfo.u.SystemTime.wDay, errorInfo.u.SystemTime.wYear, errorInfo.u.SystemTime.wHour, errorInfo.u.SystemTime.wMinute, errorInfo.u.SystemTime.wSecond, errorInfo.u.SystemTime.wMilliseconds); HlprLogInfo(L" [GeneratingComponent:%d]", errorInfo.GeneratingComponent); HlprLogInfo(L" [Status: %#x]", errorInfo.Status); HlprLogInfo(L" [DetectionLocation: %d]", errorInfo.DetectionLocation); HlprLogInfo(L" [Flags: %#x]", errorInfo.Flags); HlprLogInfo(L" [NumberOfParameters: %d]", errorInfo.NumberOfParameters); for(UINT32 i = 0; i < (UINT32)errorInfo.NumberOfParameters; i++) { PWSTR pNewLine = L""; if(i == ((UINT32)errorInfo.NumberOfParameters - 1)) pNewLine = L"\n"; switch(errorInfo.Parameters[i].ParameterType) { case eeptAnsiString: { HlprLogInfo(L" [AnsiString: %s]%s", errorInfo.Parameters[i].u.AnsiString, pNewLine); HeapFree(GetProcessHeap(), 0, errorInfo.Parameters[i].u.AnsiString); break; } case eeptUnicodeString: { HlprLogInfo(L" [UnicodeString: %S]%s", errorInfo.Parameters[i].u.UnicodeString, pNewLine); HeapFree(GetProcessHeap(), 0, errorInfo.Parameters[i].u.UnicodeString); break; } case eeptLongVal: { HlprLogInfo(L" [LongVal: %#x]%s", errorInfo.Parameters[i].u.LVal, pNewLine); break; } case eeptShortVal: { HlprLogInfo(L" [ShortVal: %#x]%s", errorInfo.Parameters[i].u.SVal, pNewLine); break; } case eeptPointerVal: { HlprLogInfo(L" [PointerVal: %#p]%s", errorInfo.Parameters[i].u.PVal, pNewLine); break; } case eeptNone: { HlprLogInfo(L" [Truncated]%s", pNewLine); break; } default: HlprLogInfo(L" [ParameterType Invalid: %d]%s", errorInfo.Parameters[i].ParameterType, pNewLine); } } } } HLPR_BAIL_LABEL: RpcErrorEndEnumeration(&enumHandle); return; }
/** @helper_function="HlprThreadCleanup" Purpose: Cleans up a previously allocated thread. <br> <br> Notes: <br> <br> MSDN_Ref: HTTP://MSDN.Microsoft.com/En-Us/Library/Windows/Desktop/MS683190.aspx <br> HTTP://MSDN.Microsoft.com/En-Us/Library/Windows/Desktop/MS686717.aspx <br> */ VOID HlprThreadCleanup(_Inout_opt_ THREAD_DATA* pThreadData) { if(pThreadData) { LPTHREAD_START_ROUTINE threadStartRoutine = pThreadData->threadStartRoutine; UINT32 status = NO_ERROR; if(pThreadData->thread) { if(GetExitCodeThread(pThreadData->thread, (DWORD*)&status)) { if(status == STILL_ACTIVE) { UINT64 timeAlpha = GetTickCount64(); const UINT32 FOUR_MINUTES = 240000; for(UINT64 timeOmega = GetTickCount64(); timeOmega - timeAlpha < FOUR_MINUTES; timeOmega = GetTickCount64()) { HlprEventSet(pThreadData->threadStopEvent); status = HlprThreadWaitForCompletion(pThreadData); if(status == NO_ERROR) break; } if(status != NO_ERROR) { HlprLogInfo(L"Possible Runaway Thread"); #pragma warning(push) #pragma warning(disable: 6258) /// This is a last resort TerminateThread(pThreadData->thread, ERROR_THREAD_WAS_SUSPENDED); #pragma warning(pop) } } } else { status = GetLastError(); HlprLogError(L"HlprThreadCleanup() [status:%#x]", status); } } HLPR_CLOSE_HANDLE(pThreadData->threadStopEvent); HLPR_CLOSE_HANDLE(pThreadData->threadStartEvent); HLPR_CLOSE_HANDLE(pThreadData->threadContinueEvent); ZeroMemory(pThreadData, sizeof(THREAD_DATA)); pThreadData->threadStartRoutine = threadStartRoutine; } return; }
/** @framework_function="RPCClientInterfaceInitialize" Purpose: Initialize the RPC client interface by creating a fast binding handle. <br> <br> Notes: <br> <br> MSDN_Ref: HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA378651.aspx <br> HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA375587.aspx <br> HTTP://MSDN.Microsoft.com/En-US/Library/Windows/Desktop/AA375583.aspx <br> */ UINT32 RPCClientInterfaceInitialize() { RPC_STATUS status = RPC_S_OK; SID* pLocalSystemSID = 0; SIZE_T sidSize = 0; RPC_SECURITY_QOS_V4 securityQoS = {0}; RPC_BINDING_HANDLE_TEMPLATE_V1 bindingHandleTemplate = {0}; RPC_BINDING_HANDLE_SECURITY_V1 bindingHandleSecurity = {0}; RPC_BINDING_HANDLE_OPTIONS_V1 bindingHandleOptions = {0}; HLPR_NEW(pRPCData, RPC_DATA); HLPR_BAIL_ON_ALLOC_FAILURE(pRPCData, status); status = HlprSIDCreate(&pLocalSystemSID, &sidSize, 0, WinLocalSystemSid); HLPR_BAIL_ON_FAILURE(status); wfpSamplerBindingHandle = 0; pRPCData->rpcClientInterfaceHandle = IWFPSampler_v1_0_c_ifspec; /// MIDL generated Client Interface Handle pRPCData->protocolSequence = RPC_PROTSEQ_LRPC; /// Use Local RPC securityQoS.Version = 4; /// Use RPC_SECURITY_QOS_V4 structure securityQoS.Capabilities = RPC_C_QOS_CAPABILITIES_MUTUAL_AUTH; /// Request mutual authentication from the security provider securityQoS.IdentityTracking = RPC_C_QOS_IDENTITY_STATIC; /// Security context is created only once securityQoS.ImpersonationType = RPC_C_IMP_LEVEL_IDENTIFY; /// Allow server to get client's identity and allow it's impersonation securityQoS.Sid = pLocalSystemSID; /// Security identifier used by Local RPC securityQoS.EffectiveOnly = TRUE; /// only see enabled privileges bindingHandleTemplate.Version = 1; /// Use BINDING_HANDLE_TEMPLATE_V1 structure bindingHandleTemplate.ProtocolSequence = pRPCData->protocolSequence; /// Use Local RPC bindingHandleTemplate.StringEndpoint = (PWSTR)g_pEndpoint; /// String representation of our endpoint bindingHandleSecurity.Version = 1; /// Use BINDING_HANDLE_SECURITY_V1 structure bindingHandleSecurity.AuthnLevel = RPC_C_AUTHN_LEVEL_PKT_PRIVACY; /// Authentication level which causes Local RPC to use a secure channel bindingHandleSecurity.AuthnSvc = RPC_C_AUTHN_WINNT; /// Autherntication service to use bindingHandleSecurity.SecurityQos = (RPC_SECURITY_QOS*)&securityQoS; /// Security Qos Settings to Use bindingHandleOptions.Version = 1; /// Use BINDING_HANDLE_OPTIONS_V1 structure bindingHandleOptions.Flags = RPC_BHO_NONCAUSAL; /// Execute calls in any order bindingHandleOptions.ComTimeout = RPC_C_BINDING_DEFAULT_TIMEOUT; /// Use default communication timeout value status = RpcBindingCreate(&bindingHandleTemplate, /// Core structure of the binding handle &bindingHandleSecurity, /// Security options for the binding handle &bindingHandleOptions, /// Additional options to set on the binding handle &wfpSamplerBindingHandle); /// Created binding handle if(status != RPC_S_OK) { HlprLogError(L"RPCClientInterfaceInitialize : RpcBindingCreate() [status: %#x]", status); HLPR_BAIL; } pRPCData->bindingHandle = wfpSamplerBindingHandle; status = RpcBindingBind(0, /// These RPC calls will be synchronous pRPCData->bindingHandle, /// Binding handle that will be used to make the RPC call pRPCData->rpcClientInterfaceHandle); /// Interface handle that will be used to make the RPC call if(status != RPC_S_OK) { HlprLogError(L"RPCClientInterfaceInitialize : RpcBindingBind() [status: %#x]", status); HLPR_BAIL; } HLPR_BAIL_LABEL: if(status != RPC_S_OK) { HlprLogError(L"[status: %#x]", status); PrvRPCTroubleshootError(); RPCClientInterfaceTerminate(); } if(pLocalSystemSID) HlprSIDDestroy(&pLocalSystemSID); return status; }
/** @helper_function="HlprLogInfo" Purpose: Log an information message to the console. <br> <br> Notes: <br> <br> MSDN_Ref: <br> */ VOID HlprLogInfo(_In_ PCWSTR pMessage, ...) { ASSERT(pMessage); UINT32 status = NO_ERROR; PCWSTR pFormatMessage = L"INFO: %s\n"; PWSTR pActualMessage = 0; size_t size = 0; size_t actualSize = 9; /// Size of format Message and room for NULL Terminator '\0' WCHAR pLogMessage[MAX_CHARS] = {0}; va_list argumentList; va_start(argumentList, pMessage); status = StringCchVPrintf(pLogMessage, MAX_CHARS, pMessage, argumentList); if(status != NO_ERROR) { HlprLogError(L"HlprLogInfo : StringCchVPrintf() [status: %#x]", status); HLPR_BAIL; } status = StringCchLength(pLogMessage, STRSAFE_MAX_CCH, &size); if(status != NO_ERROR) { HlprLogError(L"HlprLogInfo : StringCchLength() [status: %#x]", status); HLPR_BAIL; } actualSize += size; HLPR_NEW_ARRAY(pActualMessage, WCHAR, actualSize); HLPR_BAIL_ON_ALLOC_FAILURE(pActualMessage, status); status = StringCchPrintf(pActualMessage, actualSize, pFormatMessage, pLogMessage); if(status != NO_ERROR) { HlprLogError(L"HlprLogInfo : StringCchPrintf() [status: %#x]", status); HLPR_BAIL; } wprintf(pActualMessage); HLPR_BAIL_LABEL: va_end(argumentList); HLPR_DELETE_ARRAY(pActualMessage); return; }
UINT32 HlprThreadStart(_Inout_ THREAD_DATA* pThreadData, _In_opt_ VOID* pData) /* 0 */ { UINT32 status = NO_ERROR; if(pThreadData) { HlprThreadCleanup(pThreadData); if(pThreadData->threadStartRoutine) { pThreadData->threadStartEvent = CreateEvent(0, TRUE, FALSE, 0); pThreadData->threadStopEvent = CreateEvent(0, TRUE, FALSE, 0); pThreadData->threadContinueEvent = CreateEvent(0, TRUE, FALSE, 0); pThreadData->thread = CreateThread(0, 0, (LPTHREAD_START_ROUTINE)pThreadData->threadStartRoutine, pData ? pData : pThreadData, 0, (LPDWORD)&(pThreadData->threadId)); if(pThreadData->threadStartEvent && pThreadData->threadStopEvent && pThreadData->threadContinueEvent && pThreadData->thread) HlprThreadWaitForEvent(pThreadData->threadStartEvent, pThreadData); else { status = ERROR_GEN_FAILURE; HlprThreadCleanup(pThreadData); HlprLogError(L"HlprThreadStart() [status: %#x]", status); } } else { status = ERROR_INVALID_DATA; HlprLogError(L"HlprThreadStart() [status: %#x][pThreadData->threadStartRoutine: %#x]", status, pThreadData->threadStartRoutine); } } else { status = ERROR_INVALID_PARAMETER; HlprLogError(L"HlprThreadStart() [status: %#x][pThread: %#x]", status, pThreadData); } return status; }