Macrosify out-of-proc (#1268)

This commit is contained in:
Pavel Krymets 2018-08-21 14:11:34 -07:00 committed by GitHub
parent 2778570f0b
commit 26964b2687
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
14 changed files with 263 additions and 498 deletions

View File

@ -50,7 +50,7 @@ ASPNETCORE_SHIM_CONFIG::Populate(
ASPNETCORE_EVENT_UNKNOWN_HOSTING_MODEL_ERROR, ASPNETCORE_EVENT_UNKNOWN_HOSTING_MODEL_ERROR,
ASPNETCORE_EVENT_UNKNOWN_HOSTING_MODEL_ERROR_MSG, ASPNETCORE_EVENT_UNKNOWN_HOSTING_MODEL_ERROR_MSG,
strHostingModel.QueryStr()); strHostingModel.QueryStr());
RETURN_IF_FAILED(HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED)); RETURN_HR(HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED));
} }
RETURN_IF_FAILED(GetElementStringProperty(pAspNetCoreElement, RETURN_IF_FAILED(GetElementStringProperty(pAspNetCoreElement,

View File

@ -26,6 +26,8 @@
#endif #endif
#define OBSERVE_CAUGHT_EXCEPTION() CaughtExceptionHResult(LOCATION_INFO); #define OBSERVE_CAUGHT_EXCEPTION() CaughtExceptionHResult(LOCATION_INFO);
#define RETURN_HR(hr) do { HRESULT __hrRet = hr; if (FAILED(__hrRet)) { LogHResultFailed(LOCATION_INFO, __hrRet); } return __hrRet; } while (0, 0)
#define RETURN_LAST_ERROR() do { return LogLastError(LOCATION_INFO); } while (0, 0)
#define RETURN_IF_FAILED(hr) do { HRESULT __hrRet = hr; if (FAILED(__hrRet)) { LogHResultFailed(LOCATION_INFO, __hrRet); return __hrRet; }} while (0, 0) #define RETURN_IF_FAILED(hr) do { HRESULT __hrRet = hr; if (FAILED(__hrRet)) { LogHResultFailed(LOCATION_INFO, __hrRet); return __hrRet; }} while (0, 0)
#define RETURN_CAUGHT_EXCEPTION() return CaughtExceptionHResult(LOCATION_INFO); #define RETURN_CAUGHT_EXCEPTION() return CaughtExceptionHResult(LOCATION_INFO);
#define RETURN_LAST_ERROR_IF(condition) do { if (condition) { return LogLastError(LOCATION_INFO); }} while (0, 0) #define RETURN_LAST_ERROR_IF(condition) do { if (condition) { return LogLastError(LOCATION_INFO); }} while (0, 0)

View File

@ -224,7 +224,6 @@
</Link> </Link>
</ItemDefinitionGroup> </ItemDefinitionGroup>
<ItemGroup> <ItemGroup>
<ClInclude Include="aspnetcore_event.h" />
<ClInclude Include="disconnectcontext.h" /> <ClInclude Include="disconnectcontext.h" />
<ClInclude Include="environmentvariablehelpers.h" /> <ClInclude Include="environmentvariablehelpers.h" />
<ClInclude Include="forwarderconnection.h" /> <ClInclude Include="forwarderconnection.h" />

View File

@ -121,28 +121,29 @@ EnsureOutOfProcessInitializtion()
DBG_ASSERT(g_pHttpServer); DBG_ASSERT(g_pHttpServer);
HRESULT hr = S_OK; HRESULT hr = S_OK;
BOOL fLocked = FALSE;
if (g_fOutOfProcessInitializeError) if (g_fOutOfProcessInitializeError)
{ {
hr = E_NOT_VALID_STATE; FINISHED(E_NOT_VALID_STATE);
goto Finished;
} }
if (!g_fOutOfProcessInitialize) if (g_fOutOfProcessInitialize)
{ {
AcquireSRWLockExclusive(&g_srwLockRH); FINISHED(S_OK);
fLocked = TRUE; }
{
auto lock = SRWExclusiveLock(g_srwLockRH);
if (g_fOutOfProcessInitializeError) if (g_fOutOfProcessInitializeError)
{ {
hr = E_NOT_VALID_STATE; FINISHED(E_NOT_VALID_STATE);
goto Finished;
} }
if (g_fOutOfProcessInitialize) if (g_fOutOfProcessInitialize)
{ {
// Done by another thread // Done by another thread
goto Finished; FINISHED(S_OK);
} }
g_hWinHttpModule = GetModuleHandle(TEXT("winhttp.dll")); g_hWinHttpModule = GetModuleHandle(TEXT("winhttp.dll"));
@ -150,7 +151,7 @@ EnsureOutOfProcessInitializtion()
g_hAspNetCoreModule = GetModuleHandle(TEXT("aspnetcorev2.dll")); g_hAspNetCoreModule = GetModuleHandle(TEXT("aspnetcorev2.dll"));
hr = WINHTTP_HELPER::StaticInitialize(); hr = WINHTTP_HELPER::StaticInitialize();
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
if (hr == HRESULT_FROM_WIN32(ERROR_PROC_NOT_FOUND)) if (hr == HRESULT_FROM_WIN32(ERROR_PROC_NOT_FOUND))
{ {
@ -158,7 +159,7 @@ EnsureOutOfProcessInitializtion()
} }
else else
{ {
goto Finished; FINISHED(hr);
} }
} }
@ -167,11 +168,7 @@ EnsureOutOfProcessInitializtion()
WINHTTP_NO_PROXY_NAME, WINHTTP_NO_PROXY_NAME,
WINHTTP_NO_PROXY_BYPASS, WINHTTP_NO_PROXY_BYPASS,
WINHTTP_FLAG_ASYNC); WINHTTP_FLAG_ASYNC);
if (g_hWinhttpSession == NULL) FINISHED_LAST_ERROR_IF(g_hWinhttpSession == NULL);
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
// //
// Don't set non-blocking callbacks WINHTTP_OPTION_ASSURED_NON_BLOCKING_CALLBACKS, // Don't set non-blocking callbacks WINHTTP_OPTION_ASSURED_NON_BLOCKING_CALLBACKS,
@ -182,65 +179,33 @@ EnsureOutOfProcessInitializtion()
// //
// Setup the callback function // Setup the callback function
// //
if (WinHttpSetStatusCallback(g_hWinhttpSession, FINISHED_LAST_ERROR_IF(WinHttpSetStatusCallback(g_hWinhttpSession,
FORWARDING_HANDLER::OnWinHttpCompletion, FORWARDING_HANDLER::OnWinHttpCompletion,
(WINHTTP_CALLBACK_FLAG_ALL_COMPLETIONS | (WINHTTP_CALLBACK_FLAG_ALL_COMPLETIONS |
WINHTTP_CALLBACK_STATUS_SENDING_REQUEST), WINHTTP_CALLBACK_STATUS_SENDING_REQUEST),
NULL) == WINHTTP_INVALID_STATUS_CALLBACK) NULL) == WINHTTP_INVALID_STATUS_CALLBACK);
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
// //
// Make sure we see the redirects (rather than winhttp doing it // Make sure we see the redirects (rather than winhttp doing it
// automatically) // automatically)
// //
DWORD dwRedirectOption = WINHTTP_OPTION_REDIRECT_POLICY_NEVER; DWORD dwRedirectOption = WINHTTP_OPTION_REDIRECT_POLICY_NEVER;
if (!WinHttpSetOption(g_hWinhttpSession, FINISHED_LAST_ERROR_IF(!WinHttpSetOption(g_hWinhttpSession,
WINHTTP_OPTION_REDIRECT_POLICY, WINHTTP_OPTION_REDIRECT_POLICY,
&dwRedirectOption, &dwRedirectOption,
sizeof(dwRedirectOption))) sizeof(dwRedirectOption)));
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
g_dwTlsIndex = TlsAlloc(); g_dwTlsIndex = TlsAlloc();
if (g_dwTlsIndex == TLS_OUT_OF_INDEXES) FINISHED_LAST_ERROR_IF(g_dwTlsIndex == TLS_OUT_OF_INDEXES);
{ FINISHED_IF_FAILED(ALLOC_CACHE_HANDLER::StaticInitialize());
hr = HRESULT_FROM_WIN32(GetLastError()); FINISHED_IF_FAILED(FORWARDING_HANDLER::StaticInitialize(g_fEnableReferenceCountTracing));
goto Finished; FINISHED_IF_FAILED(WEBSOCKET_HANDLER::StaticInitialize(g_fEnableReferenceCountTracing));
}
hr = ALLOC_CACHE_HANDLER::StaticInitialize();
if (FAILED(hr))
{
goto Finished;
}
hr = FORWARDING_HANDLER::StaticInitialize(g_fEnableReferenceCountTracing);
if (FAILED(hr))
{
goto Finished;
}
hr = WEBSOCKET_HANDLER::StaticInitialize(g_fEnableReferenceCountTracing);
if (FAILED(hr))
{
goto Finished;
}
} }
Finished: Finished:
if (FAILED(hr)) if (FAILED(hr))
{ {
g_fOutOfProcessInitializeError = TRUE; g_fOutOfProcessInitializeError = TRUE;
} }
if (fLocked)
{
ReleaseSRWLockExclusive(&g_srwLockRH);
}
return hr; return hr;
} }

View File

@ -2,12 +2,13 @@
// Licensed under the MIT License. See License.txt in the project root for license information. // Licensed under the MIT License. See License.txt in the project root for license information.
#include "forwarderconnection.h" #include "forwarderconnection.h"
#include "exceptions.h"
FORWARDER_CONNECTION::FORWARDER_CONNECTION( FORWARDER_CONNECTION::FORWARDER_CONNECTION(
VOID VOID
) : m_cRefs (1), ) : m_cRefs (1),
m_hConnection (NULL) m_hConnection (NULL)
{ {
} }
HRESULT HRESULT
@ -15,38 +16,19 @@ FORWARDER_CONNECTION::Initialize(
DWORD dwPort DWORD dwPort
) )
{ {
HRESULT hr = S_OK; RETURN_IF_FAILED(m_ConnectionKey.Initialize( dwPort ));
hr = m_ConnectionKey.Initialize( dwPort );
if ( FAILED( hr ) )
{
goto Finished;
}
m_hConnection = WinHttpConnect(g_hWinhttpSession, m_hConnection = WinHttpConnect(g_hWinhttpSession,
L"127.0.0.1", L"127.0.0.1",
(USHORT) dwPort, (USHORT) dwPort,
0); 0);
if (m_hConnection == NULL) RETURN_LAST_ERROR_IF_NULL(m_hConnection);
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
// //
// Since WinHttp will not emit WINHTTP_CALLBACK_STATUS_HANDLE_CLOSING // Since WinHttp will not emit WINHTTP_CALLBACK_STATUS_HANDLE_CLOSING
// when closing WebSocket handle on Win8. Register callback at Connect level as a workaround // when closing WebSocket handle on Win8. Register callback at Connect level as a workaround
// //
if (WinHttpSetStatusCallback(m_hConnection, RETURN_LAST_ERROR_IF (WinHttpSetStatusCallback(m_hConnection,
FORWARDING_HANDLER::OnWinHttpCompletion, FORWARDING_HANDLER::OnWinHttpCompletion,
WINHTTP_CALLBACK_FLAG_HANDLES, WINHTTP_CALLBACK_FLAG_HANDLES,
NULL) == WINHTTP_INVALID_STATUS_CALLBACK) NULL) == WINHTTP_INVALID_STATUS_CALLBACK);
{ return S_OK;
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
Finished:
return hr;
} }

View File

@ -3,6 +3,7 @@
#include "forwardinghandler.h" #include "forwardinghandler.h"
#include "url_utility.h" #include "url_utility.h"
#include "exceptions.h"
// Just to be aware of the FORWARDING_HANDLER object size. // Just to be aware of the FORWARDING_HANDLER object size.
C_ASSERT(sizeof(FORWARDING_HANDLER) <= 632); C_ASSERT(sizeof(FORWARDING_HANDLER) <= 632);
@ -140,7 +141,7 @@ FORWARDING_HANDLER::OnExecuteRequestHandler()
} }
hr = pApplication->GetProcess(&pServerProcess); hr = pApplication->GetProcess(&pServerProcess);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
fFailedToStartKestrel = TRUE; fFailedToStartKestrel = TRUE;
goto Failure; goto Failure;
@ -165,7 +166,7 @@ FORWARDING_HANDLER::OnExecuteRequestHandler()
// //
// parse original url // parse original url
// //
if (FAILED(hr = URL_UTILITY::SplitUrl(pRequest->GetRawHttpRequest()->CookedUrl.pFullUrl, if (FAILED_LOG(hr = URL_UTILITY::SplitUrl(pRequest->GetRawHttpRequest()->CookedUrl.pFullUrl,
&fSecure, &fSecure,
&strDestination, &strDestination,
&strUrl))) &strUrl)))
@ -173,7 +174,7 @@ FORWARDING_HANDLER::OnExecuteRequestHandler()
goto Failure; goto Failure;
} }
if (FAILED(hr = URL_UTILITY::EscapeAbsPath(pRequest, &struEscapedUrl))) if (FAILED_LOG(hr = URL_UTILITY::EscapeAbsPath(pRequest, &struEscapedUrl)))
{ {
goto Failure; goto Failure;
} }
@ -200,7 +201,7 @@ FORWARDING_HANDLER::OnExecuteRequestHandler()
hConnect, hConnect,
&struEscapedUrl, &struEscapedUrl,
pServerProcess); pServerProcess);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Failure; goto Failure;
} }
@ -222,7 +223,7 @@ FORWARDING_HANDLER::OnExecuteRequestHandler()
SetConnectionModuleContext(m_pDisconnect, SetConnectionModuleContext(m_pDisconnect,
m_pModuleId); m_pModuleId);
DBG_ASSERT(hr != HRESULT_FROM_WIN32(ERROR_ALREADY_ASSIGNED)); DBG_ASSERT(hr != HRESULT_FROM_WIN32(ERROR_ALREADY_ASSIGNED));
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Failure; goto Failure;
} }
@ -477,7 +478,7 @@ REQUEST_NOTIFICATION_STATUS
InterlockedIncrement(&m_dwHandlers); InterlockedIncrement(&m_dwHandlers);
} }
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
// This failure could happen when client disconnect happens or backend server fails // This failure could happen when client disconnect happens or backend server fails
// after websocket upgrade // after websocket upgrade
@ -514,7 +515,7 @@ REQUEST_NOTIFICATION_STATUS
// failure, if there is more data available from WinHTTP, read it // failure, if there is more data available from WinHTTP, read it
// or else ask if there is more. // or else ask if there is more.
// //
if (FAILED(hrCompletionStatus)) if (FAILED_LOG(hrCompletionStatus))
{ {
hr = hrCompletionStatus; hr = hrCompletionStatus;
fClientError = TRUE; fClientError = TRUE;
@ -522,7 +523,7 @@ REQUEST_NOTIFICATION_STATUS
} }
hr = OnReceivingResponse(); hr = OnReceivingResponse();
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Failure; goto Failure;
} }
@ -533,7 +534,7 @@ REQUEST_NOTIFICATION_STATUS
hr = OnSendingRequest(cbCompletion, hr = OnSendingRequest(cbCompletion,
hrCompletionStatus, hrCompletionStatus,
&fClientError); &fClientError);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Failure; goto Failure;
} }
@ -730,7 +731,7 @@ HRESULT
hr = sm_pAlloc->Initialize(sizeof(FORWARDING_HANDLER), hr = sm_pAlloc->Initialize(sizeof(FORWARDING_HANDLER),
64); // nThreshold 64); // nThreshold
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -743,14 +744,14 @@ HRESULT
} }
hr = sm_pResponseHeaderHash->Initialize(); hr = sm_pResponseHeaderHash->Initialize();
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
// Initialize PROTOCOL_CONFIG // Initialize PROTOCOL_CONFIG
hr = sm_ProtocolConfig.Initialize(); hr = sm_ProtocolConfig.Initialize();
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -786,7 +787,7 @@ HRESULT
</div></body></html>"); </div></body></html>");
Finished: Finished:
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
StaticTerminate(); StaticTerminate();
} }
@ -871,12 +872,12 @@ FORWARDING_HANDLER::GetHeaders(
// //
if (!pProtocol->QueryPreserveHostHeader()) if (!pProtocol->QueryPreserveHostHeader())
{ {
if (FAILED(hr = URL_UTILITY::SplitUrl(pRequest->GetRawHttpRequest()->CookedUrl.pFullUrl, if (FAILED_LOG(hr = URL_UTILITY::SplitUrl(pRequest->GetRawHttpRequest()->CookedUrl.pFullUrl,
&fSecure, &fSecure,
&struDestination, &struDestination,
&struUrl)) || &struUrl)) ||
FAILED(hr = strTemp.CopyW(struDestination.QueryStr())) || FAILED_LOG(hr = strTemp.CopyW(struDestination.QueryStr())) ||
FAILED(hr = pRequest->SetHeader(HttpHeaderHost, FAILED_LOG(hr = pRequest->SetHeader(HttpHeaderHost,
strTemp.QueryStr(), strTemp.QueryStr(),
static_cast<USHORT>(strTemp.QueryCCH()), static_cast<USHORT>(strTemp.QueryCCH()),
TRUE))) // fReplace TRUE))) // fReplace
@ -917,7 +918,7 @@ FORWARDING_HANDLER::GetHeaders(
pServerProcess->QueryGuid(), pServerProcess->QueryGuid(),
(USHORT)strlen(pServerProcess->QueryGuid()), (USHORT)strlen(pServerProcess->QueryGuid()),
TRUE); TRUE);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
return hr; return hr;
} }
@ -933,7 +934,7 @@ FORWARDING_HANDLER::GetHeaders(
HANDLE hTargetTokenHandle = NULL; HANDLE hTargetTokenHandle = NULL;
hr = pServerProcess->SetWindowsAuthToken(m_pW3Context->GetUser()->GetPrimaryToken(), hr = pServerProcess->SetWindowsAuthToken(m_pW3Context->GetUser()->GetPrimaryToken(),
&hTargetTokenHandle); &hTargetTokenHandle);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
return hr; return hr;
} }
@ -952,7 +953,7 @@ FORWARDING_HANDLER::GetHeaders(
pszHandleStr, pszHandleStr,
(USHORT)strlen(pszHandleStr), (USHORT)strlen(pszHandleStr),
TRUE); TRUE);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
return hr; return hr;
} }
@ -966,14 +967,14 @@ FORWARDING_HANDLER::GetHeaders(
pszCurrentHeader = pRequest->GetHeader(pProtocol->QueryXForwardedForName()->QueryStr(), &cchCurrentHeader); pszCurrentHeader = pRequest->GetHeader(pProtocol->QueryXForwardedForName()->QueryStr(), &cchCurrentHeader);
if (pszCurrentHeader != NULL) if (pszCurrentHeader != NULL)
{ {
if (FAILED(hr = strTemp.Copy(pszCurrentHeader, cchCurrentHeader)) || if (FAILED_LOG(hr = strTemp.Copy(pszCurrentHeader, cchCurrentHeader)) ||
FAILED(hr = strTemp.Append(", ", 2))) FAILED_LOG(hr = strTemp.Append(", ", 2)))
{ {
return hr; return hr;
} }
} }
if (FAILED(hr = m_pW3Context->GetServerVariable("REMOTE_ADDR", if (FAILED_LOG(hr = m_pW3Context->GetServerVariable("REMOTE_ADDR",
&pszFinalHeader, &pszFinalHeader,
&cchFinalHeader))) &cchFinalHeader)))
{ {
@ -982,16 +983,16 @@ FORWARDING_HANDLER::GetHeaders(
if (pRequest->GetRawHttpRequest()->Address.pRemoteAddress->sa_family == AF_INET6) if (pRequest->GetRawHttpRequest()->Address.pRemoteAddress->sa_family == AF_INET6)
{ {
if (FAILED(hr = strTemp.Append("[", 1)) || if (FAILED_LOG(hr = strTemp.Append("[", 1)) ||
FAILED(hr = strTemp.Append(pszFinalHeader, cchFinalHeader)) || FAILED_LOG(hr = strTemp.Append(pszFinalHeader, cchFinalHeader)) ||
FAILED(hr = strTemp.Append("]", 1))) FAILED_LOG(hr = strTemp.Append("]", 1)))
{ {
return hr; return hr;
} }
} }
else else
{ {
if (FAILED(hr = strTemp.Append(pszFinalHeader, cchFinalHeader))) if (FAILED_LOG(hr = strTemp.Append(pszFinalHeader, cchFinalHeader)))
{ {
return hr; return hr;
} }
@ -999,21 +1000,21 @@ FORWARDING_HANDLER::GetHeaders(
if (pProtocol->QueryIncludePortInXForwardedFor()) if (pProtocol->QueryIncludePortInXForwardedFor())
{ {
if (FAILED(hr = m_pW3Context->GetServerVariable("REMOTE_PORT", if (FAILED_LOG(hr = m_pW3Context->GetServerVariable("REMOTE_PORT",
&pszFinalHeader, &pszFinalHeader,
&cchFinalHeader))) &cchFinalHeader)))
{ {
return hr; return hr;
} }
if (FAILED(hr = strTemp.Append(":", 1)) || if (FAILED_LOG(hr = strTemp.Append(":", 1)) ||
FAILED(hr = strTemp.Append(pszFinalHeader, cchFinalHeader))) FAILED_LOG(hr = strTemp.Append(pszFinalHeader, cchFinalHeader)))
{ {
return hr; return hr;
} }
} }
if (FAILED(hr = pRequest->SetHeader(pProtocol->QueryXForwardedForName()->QueryStr(), if (FAILED_LOG(hr = pRequest->SetHeader(pProtocol->QueryXForwardedForName()->QueryStr(),
strTemp.QueryStr(), strTemp.QueryStr(),
static_cast<USHORT>(strTemp.QueryCCH()), static_cast<USHORT>(strTemp.QueryCCH()),
TRUE))) // fReplace TRUE))) // fReplace
@ -1036,19 +1037,19 @@ FORWARDING_HANDLER::GetHeaders(
pszCurrentHeader = pRequest->GetHeader(pProtocol->QuerySslHeaderName()->QueryStr(), &cchCurrentHeader); pszCurrentHeader = pRequest->GetHeader(pProtocol->QuerySslHeaderName()->QueryStr(), &cchCurrentHeader);
if (pszCurrentHeader != NULL) if (pszCurrentHeader != NULL)
{ {
if (FAILED(hr = strTemp.Copy(pszCurrentHeader, cchCurrentHeader)) || if (FAILED_LOG(hr = strTemp.Copy(pszCurrentHeader, cchCurrentHeader)) ||
FAILED(hr = strTemp.Append(", ", 2))) FAILED_LOG(hr = strTemp.Append(", ", 2)))
{ {
return hr; return hr;
} }
} }
if (FAILED(hr = strTemp.Append(pszScheme))) if (FAILED_LOG(hr = strTemp.Append(pszScheme)))
{ {
return hr; return hr;
} }
if (FAILED(pRequest->SetHeader(pProtocol->QuerySslHeaderName()->QueryStr(), if (FAILED_LOG(pRequest->SetHeader(pProtocol->QuerySslHeaderName()->QueryStr(),
strTemp.QueryStr(), strTemp.QueryStr(),
(USHORT)strTemp.QueryCCH(), (USHORT)strTemp.QueryCCH(),
TRUE))) TRUE)))
@ -1067,7 +1068,7 @@ FORWARDING_HANDLER::GetHeaders(
else else
{ {
// Resize the buffer large enough to hold the encoded certificate info // Resize the buffer large enough to hold the encoded certificate info
if (FAILED(hr = strTemp.Resize( if (FAILED_LOG(hr = strTemp.Resize(
1 + (pRequest->GetRawHttpRequest()->pSslInfo->pClientCertInfo->CertEncodedSize + 2) / 3 * 4))) 1 + (pRequest->GetRawHttpRequest()->pSslInfo->pClientCertInfo->CertEncodedSize + 2) / 3 * 4)))
{ {
return hr; return hr;
@ -1081,7 +1082,7 @@ FORWARDING_HANDLER::GetHeaders(
NULL); NULL);
strTemp.SyncWithBuffer(); strTemp.SyncWithBuffer();
if (FAILED(hr = pRequest->SetHeader( if (FAILED_LOG(hr = pRequest->SetHeader(
pProtocol->QueryClientCertName()->QueryStr(), pProtocol->QueryClientCertName()->QueryStr(),
strTemp.QueryStr(), strTemp.QueryStr(),
static_cast<USHORT>(strTemp.QueryCCH()), static_cast<USHORT>(strTemp.QueryCCH()),
@ -1106,7 +1107,7 @@ FORWARDING_HANDLER::GetHeaders(
hr = m_pW3Context->GetServerVariable("ALL_RAW", hr = m_pW3Context->GetServerVariable("ALL_RAW",
ppszHeaders, ppszHeaders,
pcchHeaders); pcchHeaders);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
return hr; return hr;
} }
@ -1134,7 +1135,7 @@ FORWARDING_HANDLER::CreateWinHttpRequest(
// we will fill them when sending the request) // we will fill them when sending the request)
// //
pszVerb = pRequest->GetHttpMethod(); pszVerb = pRequest->GetHttpMethod();
if (FAILED(hr = strVerb.CopyA(pszVerb))) if (FAILED_LOG(hr = strVerb.CopyA(pszVerb)))
{ {
goto Finished; goto Finished;
} }
@ -1147,7 +1148,7 @@ FORWARDING_HANDLER::CreateWinHttpRequest(
"HTTP_VERSION", "HTTP_VERSION",
&pszVersion, &pszVersion,
&cchUnused); &cchUnused);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -1235,7 +1236,7 @@ FORWARDING_HANDLER::CreateWinHttpRequest(
pServerProcess, pServerProcess,
&m_pszHeaders, &m_pszHeaders,
&m_cchHeaders); &m_cchHeaders);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -1514,7 +1515,7 @@ None
// //
// Handle failure code for switch statement above. // Handle failure code for switch statement above.
// //
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Failure; goto Failure;
} }
@ -1762,7 +1763,7 @@ FORWARDING_HANDLER::OnWinHttpCompletionSendRequestOrWriteComplete(
goto Finished; goto Finished;
} }
} }
else if (FAILED(hr)) else if (FAILED_LOG(hr))
{ {
*pfClientError = TRUE; *pfClientError = TRUE;
goto Finished; goto Finished;
@ -1842,7 +1843,7 @@ FORWARDING_HANDLER::OnWinHttpCompletionStatusHeadersAvailable(
} }
} }
if (FAILED(hr = strHeaders.CopyW( if (FAILED_LOG(hr = strHeaders.CopyW(
reinterpret_cast<PWSTR>(bufHeaderBuffer.QueryPtr())))) reinterpret_cast<PWSTR>(bufHeaderBuffer.QueryPtr()))))
{ {
goto Finished; goto Finished;
@ -1859,13 +1860,13 @@ FORWARDING_HANDLER::OnWinHttpCompletionStatusHeadersAvailable(
if (!strHeaders.IsEmpty() && strHeaders.QueryStr()[strHeaders.QueryCCH() - 1] != '\n') if (!strHeaders.IsEmpty() && strHeaders.QueryStr()[strHeaders.QueryCCH() - 1] != '\n')
{ {
hr = strHeaders.Append("\r\n"); hr = strHeaders.Append("\r\n");
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
} }
if (FAILED(hr = SetStatusAndHeaders( if (FAILED_LOG(hr = SetStatusAndHeaders(
strHeaders.QueryStr(), strHeaders.QueryStr(),
strHeaders.QueryCCH()))) strHeaders.QueryCCH())))
{ {
@ -1890,7 +1891,7 @@ FORWARDING_HANDLER::OnWinHttpCompletionStatusHeadersAvailable(
NULL, NULL,
NULL); NULL);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
*pfAnotherCompletionExpected = FALSE; *pfAnotherCompletionExpected = FALSE;
} }
@ -2022,7 +2023,7 @@ FORWARDING_HANDLER::OnWinHttpCompletionStatusReadComplete(
Chunk.DataChunkType = HttpDataChunkFromMemory; Chunk.DataChunkType = HttpDataChunkFromMemory;
Chunk.FromMemory.pBuffer = m_pEntityBuffer; Chunk.FromMemory.pBuffer = m_pEntityBuffer;
Chunk.FromMemory.BufferLength = dwStatusInformationLength; Chunk.FromMemory.BufferLength = dwStatusInformationLength;
if (FAILED(hr = pResponse->WriteEntityChunkByReference(&Chunk))) if (FAILED_LOG(hr = pResponse->WriteEntityChunkByReference(&Chunk)))
{ {
goto Finished; goto Finished;
} }
@ -2036,7 +2037,7 @@ FORWARDING_HANDLER::OnWinHttpCompletionStatusReadComplete(
hr = pResponse->Flush(TRUE, // fAsync hr = pResponse->Flush(TRUE, // fAsync
TRUE, // fMoreData TRUE, // fMoreData
NULL); // pcbSent NULL); // pcbSent
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -2357,10 +2358,10 @@ FORWARDING_HANDLER::SetStatusAndHeaders(
// //
// Copy the status description // Copy the status description
// //
if (FAILED(hr = strHeaderValue.Copy( if (FAILED_LOG(hr = strHeaderValue.Copy(
pchStatus, pchStatus,
(DWORD)(pchEndofHeaderValue - pchStatus) + 1)) || (DWORD)(pchEndofHeaderValue - pchStatus) + 1)) ||
FAILED(hr = pResponse->SetStatus(uStatus, FAILED_LOG(hr = pResponse->SetStatus(uStatus,
strHeaderValue.QueryStr(), strHeaderValue.QueryStr(),
0, 0,
S_OK, S_OK,
@ -2422,7 +2423,7 @@ FORWARDING_HANDLER::SetStatusAndHeaders(
// //
// Copy the header name // Copy the header name
// //
if (FAILED(hr = strHeaderName.Copy( if (FAILED_LOG(hr = strHeaderName.Copy(
pszHeaders + index, pszHeaders + index,
(DWORD)(pchEndofHeaderName - pszHeaders) - index))) (DWORD)(pchEndofHeaderName - pszHeaders) - index)))
{ {
@ -2458,7 +2459,7 @@ FORWARDING_HANDLER::SetStatusAndHeaders(
{ {
strHeaderValue.Reset(); strHeaderValue.Reset();
} }
else if (FAILED(hr = strHeaderValue.Copy( else if (FAILED_LOG(hr = strHeaderValue.Copy(
pszHeaders + index, pszHeaders + index,
(DWORD)(pchEndofHeaderValue - pszHeaders) - index))) (DWORD)(pchEndofHeaderValue - pszHeaders) - index)))
{ {
@ -2508,7 +2509,7 @@ FORWARDING_HANDLER::SetStatusAndHeaders(
static_cast<USHORT>(strHeaderValue.QueryCCH()), static_cast<USHORT>(strHeaderValue.QueryCCH()),
TRUE); // fReplace TRUE); // fReplace
} }
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
return hr; return hr;
} }
@ -2526,7 +2527,7 @@ FORWARDING_HANDLER::SetStatusAndHeaders(
if (m_fDoReverseRewriteHeaders) if (m_fDoReverseRewriteHeaders)
{ {
hr = DoReverseRewrite(pResponse); hr = DoReverseRewrite(pResponse);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
return hr; return hr;
} }
@ -2573,17 +2574,17 @@ FORWARDING_HANDLER::DoReverseRewrite(
pszEndHost = strchr(pszStartHost, '/'); pszEndHost = strchr(pszStartHost, '/');
if (FAILED(hr = strTemp.Copy(fSecure ? "https://" : "http://")) || if (FAILED_LOG(hr = strTemp.Copy(fSecure ? "https://" : "http://")) ||
FAILED(hr = strTemp.Append(m_pszOriginalHostHeader))) FAILED_LOG(hr = strTemp.Append(m_pszOriginalHostHeader)))
{ {
return hr; return hr;
} }
if (pszEndHost != NULL && if (pszEndHost != NULL &&
FAILED(hr = strTemp.Append(pszEndHost))) FAILED_LOG(hr = strTemp.Append(pszEndHost)))
{ {
return hr; return hr;
} }
if (FAILED(hr = pResponse->SetHeader(HttpHeaderContentLocation, if (FAILED_LOG(hr = pResponse->SetHeader(HttpHeaderContentLocation,
strTemp.QueryStr(), strTemp.QueryStr(),
static_cast<USHORT>(strTemp.QueryCCH()), static_cast<USHORT>(strTemp.QueryCCH()),
TRUE))) TRUE)))
@ -2612,17 +2613,17 @@ Location:
pszEndHost = strchr(pszStartHost, '/'); pszEndHost = strchr(pszStartHost, '/');
if (FAILED(hr = strTemp.Copy(fSecure ? "https://" : "http://")) || if (FAILED_LOG(hr = strTemp.Copy(fSecure ? "https://" : "http://")) ||
FAILED(hr = strTemp.Append(m_pszOriginalHostHeader))) FAILED_LOG(hr = strTemp.Append(m_pszOriginalHostHeader)))
{ {
return hr; return hr;
} }
if (pszEndHost != NULL && if (pszEndHost != NULL &&
FAILED(hr = strTemp.Append(pszEndHost))) FAILED_LOG(hr = strTemp.Append(pszEndHost)))
{ {
return hr; return hr;
} }
if (FAILED(hr = pResponse->SetHeader(HttpHeaderLocation, if (FAILED_LOG(hr = pResponse->SetHeader(HttpHeaderLocation,
strTemp.QueryStr(), strTemp.QueryStr(),
static_cast<USHORT>(strTemp.QueryCCH()), static_cast<USHORT>(strTemp.QueryCCH()),
TRUE))) TRUE)))
@ -2687,9 +2688,9 @@ SetCookie:
pszEndHost++; pszEndHost++;
} }
if (FAILED(hr = strTemp.Copy(pszHeader, static_cast<DWORD>(pszStartHost - pszHeader))) || if (FAILED_LOG(hr = strTemp.Copy(pszHeader, static_cast<DWORD>(pszStartHost - pszHeader))) ||
FAILED(hr = strTemp.Append(m_pszOriginalHostHeader)) || FAILED_LOG(hr = strTemp.Append(m_pszOriginalHostHeader)) ||
FAILED(hr = strTemp.Append(pszEndHost))) FAILED_LOG(hr = strTemp.Append(pszEndHost)))
{ {
return hr; return hr;
} }

View File

@ -4,6 +4,7 @@
#include "outprocessapplication.h" #include "outprocessapplication.h"
#include "SRWExclusiveLock.h" #include "SRWExclusiveLock.h"
#include "exceptions.h"
OUT_OF_PROCESS_APPLICATION::OUT_OF_PROCESS_APPLICATION( OUT_OF_PROCESS_APPLICATION::OUT_OF_PROCESS_APPLICATION(
IHttpApplication& pApplication, IHttpApplication& pApplication,
@ -30,25 +31,12 @@ HRESULT
OUT_OF_PROCESS_APPLICATION::Initialize( OUT_OF_PROCESS_APPLICATION::Initialize(
) )
{ {
HRESULT hr = S_OK;
if (m_pProcessManager == NULL) if (m_pProcessManager == NULL)
{ {
m_pProcessManager = new PROCESS_MANAGER; m_pProcessManager = new PROCESS_MANAGER();
if (m_pProcessManager == NULL) RETURN_IF_FAILED(m_pProcessManager->Initialize());
{
hr = E_OUTOFMEMORY;
goto Finished;
}
hr = m_pProcessManager->Initialize();
if (FAILED(hr))
{
goto Finished;
}
} }
return S_OK;
Finished:
return hr;
} }
HRESULT HRESULT
@ -76,7 +64,6 @@ OUT_OF_PROCESS_APPLICATION::CreateHandler(
_In_ IHttpContext *pHttpContext, _In_ IHttpContext *pHttpContext,
_Out_ IREQUEST_HANDLER **pRequestHandler) _Out_ IREQUEST_HANDLER **pRequestHandler)
{ {
HRESULT hr = S_OK;
IREQUEST_HANDLER* pHandler = NULL; IREQUEST_HANDLER* pHandler = NULL;
//add websocket check here //add websocket check here
@ -86,14 +73,8 @@ OUT_OF_PROCESS_APPLICATION::CreateHandler(
} }
pHandler = new FORWARDING_HANDLER(pHttpContext, this); pHandler = new FORWARDING_HANDLER(pHttpContext, this);
if (pHandler == NULL)
{
hr = HRESULT_FROM_WIN32(ERROR_OUTOFMEMORY);
}
*pRequestHandler = pHandler; *pRequestHandler = pHandler;
return hr; return S_OK;
} }
VOID VOID
@ -105,10 +86,8 @@ OUT_OF_PROCESS_APPLICATION::SetWebsocketStatus(
// the websocket module may still not be enabled. // the websocket module may still not be enabled.
PCWSTR pszTempWebsocketValue; PCWSTR pszTempWebsocketValue;
DWORD cbLength; DWORD cbLength;
HRESULT hr;
hr = pHttpContext->GetServerVariable("WEBSOCKET_VERSION", &pszTempWebsocketValue, &cbLength); if (FAILED_LOG(pHttpContext->GetServerVariable("WEBSOCKET_VERSION", &pszTempWebsocketValue, &cbLength)))
if (FAILED(hr))
{ {
m_fWebSocketSupported = WEBSOCKET_STATUS::WEBSOCKET_NOT_SUPPORTED; m_fWebSocketSupported = WEBSOCKET_STATUS::WEBSOCKET_NOT_SUPPORTED;
} }

View File

@ -3,6 +3,8 @@
#include "processmanager.h" #include "processmanager.h"
#include "EventLog.h" #include "EventLog.h"
#include "exceptions.h"
#include "SRWSharedLock.h"
volatile BOOL PROCESS_MANAGER::sm_fWSAStartupDone = FALSE; volatile BOOL PROCESS_MANAGER::sm_fWSAStartupDone = FALSE;
@ -11,28 +13,21 @@ PROCESS_MANAGER::Initialize(
VOID VOID
) )
{ {
HRESULT hr = S_OK;
WSADATA wsaData; WSADATA wsaData;
int result; int result;
BOOL fLocked = FALSE;
if( !sm_fWSAStartupDone ) if( !sm_fWSAStartupDone )
{ {
AcquireSRWLockExclusive( &m_srwLock ); auto lock = SRWExclusiveLock(m_srwLock);
fLocked = TRUE;
if( !sm_fWSAStartupDone ) if( !sm_fWSAStartupDone )
{ {
if( (result = WSAStartup(MAKEWORD(2, 2), &wsaData)) != 0 ) if( (result = WSAStartup(MAKEWORD(2, 2), &wsaData)) != 0 )
{ {
hr = HRESULT_FROM_WIN32( result ); RETURN_HR(HRESULT_FROM_WIN32( result ));
goto Finished;
} }
sm_fWSAStartupDone = TRUE; sm_fWSAStartupDone = TRUE;
} }
ReleaseSRWLockExclusive( &m_srwLock );
fLocked = FALSE;
} }
m_dwRapidFailTickStart = GetTickCount(); m_dwRapidFailTickStart = GetTickCount();
@ -51,55 +46,14 @@ PROCESS_MANAGER::Initialize(
CREATE_ALWAYS, CREATE_ALWAYS,
FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_NORMAL,
NULL ); NULL );
if( m_hNULHandle == INVALID_HANDLE_VALUE ) RETURN_LAST_ERROR_IF( m_hNULHandle == INVALID_HANDLE_VALUE );
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
} }
Finished: return S_OK;
if(fLocked)
{
ReleaseSRWLockExclusive( &m_srwLock );
}
return hr;
} }
PROCESS_MANAGER::~PROCESS_MANAGER() PROCESS_MANAGER::~PROCESS_MANAGER()
{ {
AcquireSRWLockExclusive(&m_srwLock);
//if( m_ppServerProcessList != NULL )
//{
// for( DWORD i = 0; i < m_dwProcessesPerApplication; ++i )
// {
// if( m_ppServerProcessList[i] != NULL )
// {
// m_ppServerProcessList[i]->DereferenceServerProcess();
// m_ppServerProcessList[i] = NULL;
// }
// }
// delete[] m_ppServerProcessList;
// m_ppServerProcessList = NULL;
//}
//if( m_hNULHandle != NULL )
//{
// CloseHandle( m_hNULHandle );
// m_hNULHandle = NULL;
//}
//if( sm_fWSAStartupDone )
//{
// WSACleanup();
// sm_fWSAStartupDone = FALSE;
//}
ReleaseSRWLockExclusive(&m_srwLock);
} }
HRESULT HRESULT
@ -109,31 +63,22 @@ PROCESS_MANAGER::GetProcess(
_Out_ SERVER_PROCESS **ppServerProcess _Out_ SERVER_PROCESS **ppServerProcess
) )
{ {
HRESULT hr = S_OK;
BOOL fSharedLock = FALSE;
BOOL fExclusiveLock = FALSE;
DWORD dwProcessIndex = 0; DWORD dwProcessIndex = 0;
SERVER_PROCESS *pSelectedServerProcess = NULL; std::unique_ptr<SERVER_PROCESS> pSelectedServerProcess;
if (InterlockedCompareExchange(&m_lStopping, 1L, 1L) == 1L) if (InterlockedCompareExchange(&m_lStopping, 1L, 1L) == 1L)
{ {
return hr = E_APPLICATION_EXITING; RETURN_IF_FAILED(E_APPLICATION_EXITING);
} }
if (!m_fServerProcessListReady) if (!m_fServerProcessListReady)
{ {
AcquireSRWLockExclusive(&m_srwLock); auto lock = SRWExclusiveLock(m_srwLock);
fExclusiveLock = TRUE;
if (!m_fServerProcessListReady) if (!m_fServerProcessListReady)
{ {
m_dwProcessesPerApplication = pConfig->QueryProcessesPerApplication(); m_dwProcessesPerApplication = pConfig->QueryProcessesPerApplication();
m_ppServerProcessList = new SERVER_PROCESS*[m_dwProcessesPerApplication]; m_ppServerProcessList = new SERVER_PROCESS*[m_dwProcessesPerApplication];
if (m_ppServerProcessList == NULL)
{
hr = E_OUTOFMEMORY;
goto Finished;
}
for (DWORD i = 0; i < m_dwProcessesPerApplication; ++i) for (DWORD i = 0; i < m_dwProcessesPerApplication; ++i)
{ {
@ -141,35 +86,30 @@ PROCESS_MANAGER::GetProcess(
} }
} }
m_fServerProcessListReady = TRUE; m_fServerProcessListReady = TRUE;
ReleaseSRWLockExclusive(&m_srwLock);
fExclusiveLock = FALSE;
} }
AcquireSRWLockShared(&m_srwLock);
fSharedLock = TRUE;
//
// round robin through to the next available process.
//
dwProcessIndex = (DWORD)InterlockedIncrement64((LONGLONG*)&m_dwRouteToProcessIndex);
dwProcessIndex = dwProcessIndex % m_dwProcessesPerApplication;
if (m_ppServerProcessList[dwProcessIndex] != NULL &&
m_ppServerProcessList[dwProcessIndex]->IsReady())
{ {
*ppServerProcess = m_ppServerProcessList[dwProcessIndex]; auto lock = SRWSharedLock(m_srwLock);
goto Finished;
}
ReleaseSRWLockShared(&m_srwLock); //
fSharedLock = FALSE; // round robin through to the next available process.
//
dwProcessIndex = (DWORD)InterlockedIncrement64((LONGLONG*)&m_dwRouteToProcessIndex);
dwProcessIndex = dwProcessIndex % m_dwProcessesPerApplication;
if (m_ppServerProcessList[dwProcessIndex] != NULL &&
m_ppServerProcessList[dwProcessIndex]->IsReady())
{
*ppServerProcess = m_ppServerProcessList[dwProcessIndex];
return S_OK;
}
}
// should make the lock per process so that we can start processes simultaneously ? // should make the lock per process so that we can start processes simultaneously ?
if (m_ppServerProcessList[dwProcessIndex] == NULL || if (m_ppServerProcessList[dwProcessIndex] == NULL ||
!m_ppServerProcessList[dwProcessIndex]->IsReady()) !m_ppServerProcessList[dwProcessIndex]->IsReady())
{ {
AcquireSRWLockExclusive(&m_srwLock); auto lock = SRWExclusiveLock(m_srwLock);
fExclusiveLock = TRUE;
if (m_ppServerProcessList[dwProcessIndex] != NULL) if (m_ppServerProcessList[dwProcessIndex] != NULL)
{ {
@ -186,7 +126,7 @@ PROCESS_MANAGER::GetProcess(
// server is already up and ready to serve requests. // server is already up and ready to serve requests.
//m_ppServerProcessList[dwProcessIndex]->ReferenceServerProcess(); //m_ppServerProcessList[dwProcessIndex]->ReferenceServerProcess();
*ppServerProcess = m_ppServerProcessList[dwProcessIndex]; *ppServerProcess = m_ppServerProcessList[dwProcessIndex];
goto Finished; return S_OK;
} }
} }
@ -200,22 +140,14 @@ PROCESS_MANAGER::GetProcess(
ASPNETCORE_EVENT_RAPID_FAIL_COUNT_EXCEEDED_MSG, ASPNETCORE_EVENT_RAPID_FAIL_COUNT_EXCEEDED_MSG,
pConfig->QueryRapidFailsPerMinute()); pConfig->QueryRapidFailsPerMinute());
hr = HRESULT_FROM_WIN32(ERROR_SERVER_DISABLED); RETURN_HR(HRESULT_FROM_WIN32(ERROR_SERVER_DISABLED));
goto Finished;
} }
if (m_ppServerProcessList[dwProcessIndex] == NULL) if (m_ppServerProcessList[dwProcessIndex] == NULL)
{ {
pSelectedServerProcess = new SERVER_PROCESS(); pSelectedServerProcess = std::make_unique<SERVER_PROCESS>();
if (pSelectedServerProcess == NULL) RETURN_IF_FAILED(pSelectedServerProcess->Initialize(
{
hr = E_OUTOFMEMORY;
goto Finished;
}
hr = pSelectedServerProcess->Initialize(
this, //ProcessManager this, //ProcessManager
pConfig->QueryProcessPath(), // pConfig->QueryProcessPath(), //
pConfig->QueryArguments(), // pConfig->QueryArguments(), //
@ -231,50 +163,18 @@ PROCESS_MANAGER::GetProcess(
pConfig->QueryApplicationPhysicalPath(), // physical path pConfig->QueryApplicationPhysicalPath(), // physical path
pConfig->QueryApplicationPath(), // app path pConfig->QueryApplicationPath(), // app path
pConfig->QueryApplicationVirtualPath() // App relative virtual path pConfig->QueryApplicationVirtualPath() // App relative virtual path
); ));
if (FAILED(hr)) RETURN_IF_FAILED(pSelectedServerProcess->StartProcess());
{
goto Finished;
}
hr = pSelectedServerProcess->StartProcess();
if (FAILED(hr))
{
goto Finished;
}
} }
if (!pSelectedServerProcess->IsReady()) if (!pSelectedServerProcess->IsReady())
{ {
hr = HRESULT_FROM_WIN32(ERROR_CREATE_FAILED); RETURN_HR(HRESULT_FROM_WIN32(ERROR_CREATE_FAILED));
goto Finished;
} }
m_ppServerProcessList[dwProcessIndex] = pSelectedServerProcess; m_ppServerProcessList[dwProcessIndex] = pSelectedServerProcess.release();
pSelectedServerProcess = NULL;
} }
*ppServerProcess = m_ppServerProcessList[dwProcessIndex]; *ppServerProcess = m_ppServerProcessList[dwProcessIndex];
Finished: return S_OK;
if (fSharedLock)
{
ReleaseSRWLockShared(&m_srwLock);
fSharedLock = FALSE;
}
if (fExclusiveLock)
{
ReleaseSRWLockExclusive(&m_srwLock);
fExclusiveLock = FALSE;
}
if (pSelectedServerProcess != NULL)
{
delete pSelectedServerProcess;
pSelectedServerProcess = NULL;
}
return hr;
} }

View File

@ -2,41 +2,25 @@
// Licensed under the MIT License. See License.txt in the project root for license information. // Licensed under the MIT License. See License.txt in the project root for license information.
#include "protocolconfig.h" #include "protocolconfig.h"
#include "exceptions.h"
HRESULT HRESULT
PROTOCOL_CONFIG::Initialize() PROTOCOL_CONFIG::Initialize()
{ {
HRESULT hr;
STRU strTemp;
m_fKeepAlive = TRUE; m_fKeepAlive = TRUE;
m_msTimeout = 120000; m_msTimeout = 120000;
m_fPreserveHostHeader = TRUE; m_fPreserveHostHeader = TRUE;
m_fReverseRewriteHeaders = FALSE; m_fReverseRewriteHeaders = FALSE;
if (FAILED(hr = m_strXForwardedForName.CopyW(L"X-Forwarded-For"))) RETURN_IF_FAILED(m_strXForwardedForName.CopyW(L"X-Forwarded-For"));
{ RETURN_IF_FAILED(m_strSslHeaderName.CopyW(L"X-Forwarded-Proto"));
goto Finished; RETURN_IF_FAILED(m_strClientCertName.CopyW(L"MS-ASPNETCORE-CLIENTCERT"));
}
if (FAILED(hr = m_strSslHeaderName.CopyW(L"X-Forwarded-Proto")))
{
goto Finished;
}
if (FAILED(hr = m_strClientCertName.CopyW(L"MS-ASPNETCORE-CLIENTCERT")))
{
goto Finished;
}
m_fIncludePortInXForwardedFor = TRUE; m_fIncludePortInXForwardedFor = TRUE;
m_dwMinResponseBuffer = 0; // no response buffering m_dwMinResponseBuffer = 0; // no response buffering
m_dwResponseBufferLimit = 4096*1024; m_dwResponseBufferLimit = 4096*1024;
m_dwMaxResponseHeaderSize = 65536; m_dwMaxResponseHeaderSize = 65536;
return S_OK;
Finished:
return hr;
} }
VOID VOID

View File

@ -2,8 +2,9 @@
// Licensed under the MIT License. See License.txt in the project root for license information. // Licensed under the MIT License. See License.txt in the project root for license information.
#include "responseheaderhash.h" #include "responseheaderhash.h"
#include "exceptions.h"
HEADER_RECORD RESPONSE_HEADER_HASH::sm_rgHeaders[] = HEADER_RECORD RESPONSE_HEADER_HASH::sm_rgHeaders[] =
{ {
{ "Cache-Control", HttpHeaderCacheControl }, { "Cache-Control", HttpHeaderCacheControl },
{ "Connection", HttpHeaderConnection }, { "Connection", HttpHeaderConnection },
@ -65,8 +66,6 @@ Return Value:
--*/ --*/
{ {
HRESULT hr;
// //
// 31 response headers. // 31 response headers.
// Make sure to update the number of buckets it new headers // Make sure to update the number of buckets it new headers
@ -79,20 +78,13 @@ Return Value:
// Known collisions are "Age" colliding with "Expire" and "Location" // Known collisions are "Age" colliding with "Expire" and "Location"
// colliding with both "Expire" and "Age". // colliding with both "Expire" and "Age".
// //
hr = HASH_TABLE::Initialize(79); RETURN_IF_FAILED(HASH_TABLE::Initialize(79));
if (FAILED(hr))
{
return hr;
}
for ( DWORD Index = 0; Index < _countof(sm_rgHeaders); ++Index ) for ( DWORD Index = 0; Index < _countof(sm_rgHeaders); ++Index )
{ {
if (FAILED(hr = InsertRecord(&sm_rgHeaders[Index]))) RETURN_IF_FAILED(InsertRecord(&sm_rgHeaders[Index]));
{
return hr;
}
} }
return S_OK; return S_OK;
} }

View File

@ -6,6 +6,7 @@
#include <IPHlpApi.h> #include <IPHlpApi.h>
#include "EventLog.h" #include "EventLog.h"
#include "file_utility.h" #include "file_utility.h"
#include "exceptions.h"
//#include <share.h> //#include <share.h>
//extern BOOL g_fNsiApiNotSupported; //extern BOOL g_fNsiApiNotSupported;
@ -45,13 +46,13 @@ SERVER_PROCESS::Initialize(
m_pProcessManager->ReferenceProcessManager(); m_pProcessManager->ReferenceProcessManager();
m_fDebuggerAttached = FALSE; m_fDebuggerAttached = FALSE;
if (FAILED(hr = m_ProcessPath.Copy(*pszProcessExePath)) || if (FAILED_LOG(hr = m_ProcessPath.Copy(*pszProcessExePath)) ||
FAILED(hr = m_struLogFile.Copy(*pstruStdoutLogFile))|| FAILED_LOG(hr = m_struLogFile.Copy(*pstruStdoutLogFile))||
FAILED(hr = m_struPhysicalPath.Copy(*pszAppPhysicalPath))|| FAILED_LOG(hr = m_struPhysicalPath.Copy(*pszAppPhysicalPath))||
FAILED(hr = m_struAppFullPath.Copy(*pszAppPath))|| FAILED_LOG(hr = m_struAppFullPath.Copy(*pszAppPath))||
FAILED(hr = m_struAppVirtualPath.Copy(*pszAppVirtualPath))|| FAILED_LOG(hr = m_struAppVirtualPath.Copy(*pszAppVirtualPath))||
FAILED(hr = m_Arguments.Copy(*pszArguments)) || FAILED_LOG(hr = m_Arguments.Copy(*pszArguments)) ||
FAILED(hr = SetupJobObject())) FAILED_LOG(hr = SetupJobObject()))
{ {
goto Finished; goto Finished;
} }
@ -180,7 +181,7 @@ SERVER_PROCESS::SetupListenPort(
} }
WCHAR buffer[15]; WCHAR buffer[15];
if (FAILED(hr = GetRandomPort(&m_dwPort))) if (FAILED_LOG(hr = GetRandomPort(&m_dwPort)))
{ {
goto Finished; goto Finished;
} }
@ -198,9 +199,9 @@ SERVER_PROCESS::SetupListenPort(
goto Finished; goto Finished;
} }
if (FAILED(hr = pEntry->Initialize(ASPNETCORE_PORT_ENV_STR, buffer)) || if (FAILED_LOG(hr = pEntry->Initialize(ASPNETCORE_PORT_ENV_STR, buffer)) ||
FAILED(hr = pEnvironmentVarTable->InsertRecord(pEntry)) || FAILED_LOG(hr = pEnvironmentVarTable->InsertRecord(pEntry)) ||
FAILED(hr = m_struPort.Copy(buffer))) FAILED_LOG(hr = m_struPort.Copy(buffer)))
{ {
goto Finished; goto Finished;
} }
@ -212,7 +213,7 @@ Finished:
pEntry = NULL; pEntry = NULL;
} }
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
EventLog::Error( EventLog::Error(
ASPNETCORE_EVENT_PROCESS_START_SUCCESS, ASPNETCORE_EVENT_PROCESS_START_SUCCESS,
@ -252,8 +253,8 @@ SERVER_PROCESS::SetupAppPath(
goto Finished; goto Finished;
} }
if (FAILED(hr = pEntry->Initialize(ASPNETCORE_APP_PATH_ENV_STR, m_struAppVirtualPath.QueryStr())) || if (FAILED_LOG(hr = pEntry->Initialize(ASPNETCORE_APP_PATH_ENV_STR, m_struAppVirtualPath.QueryStr())) ||
FAILED(hr = pEnvironmentVarTable->InsertRecord(pEntry))) FAILED_LOG(hr = pEnvironmentVarTable->InsertRecord(pEntry)))
{ {
goto Finished; goto Finished;
} }
@ -311,7 +312,7 @@ SERVER_PROCESS::SetupAppToken(
fRpcStringAllocd = TRUE; fRpcStringAllocd = TRUE;
if (FAILED(hr = m_straGuid.Copy(pszLogUuid))) if (FAILED_LOG(hr = m_straGuid.Copy(pszLogUuid)))
{ {
goto Finished; goto Finished;
} }
@ -324,9 +325,9 @@ SERVER_PROCESS::SetupAppToken(
goto Finished; goto Finished;
} }
if (FAILED(strAppToken.CopyA(m_straGuid.QueryStr())) || if (FAILED_LOG(strAppToken.CopyA(m_straGuid.QueryStr())) ||
FAILED(hr = pEntry->Initialize(ASPNETCORE_APP_TOKEN_ENV_STR, strAppToken.QueryStr())) || FAILED_LOG(hr = pEntry->Initialize(ASPNETCORE_APP_TOKEN_ENV_STR, strAppToken.QueryStr())) ||
FAILED(hr = pEnvironmentVarTable->InsertRecord(pEntry))) FAILED_LOG(hr = pEnvironmentVarTable->InsertRecord(pEntry)))
{ {
goto Finished; goto Finished;
} }
@ -382,7 +383,7 @@ SERVER_PROCESS::OutputEnvironmentVariables
pszEqualChar = wcschr(pszCurrentVariable, L'='); pszEqualChar = wcschr(pszCurrentVariable, L'=');
if (pszEqualChar != NULL) if (pszEqualChar != NULL)
{ {
if (FAILED(hr = strEnvVar.Copy(pszCurrentVariable, (DWORD)(pszEqualChar - pszCurrentVariable) + 1))) if (FAILED_LOG(hr = strEnvVar.Copy(pszCurrentVariable, (DWORD)(pszEqualChar - pszCurrentVariable) + 1)))
{ {
goto Finished; goto Finished;
} }
@ -390,7 +391,7 @@ SERVER_PROCESS::OutputEnvironmentVariables
if (pEntry != NULL) if (pEntry != NULL)
{ {
// same env variable is defined in configuration, use it // same env variable is defined in configuration, use it
if (FAILED(hr = strEnvVar.Append(pEntry->QueryValue()))) if (FAILED_LOG(hr = strEnvVar.Append(pEntry->QueryValue())))
{ {
goto Finished; goto Finished;
} }
@ -453,9 +454,9 @@ SERVER_PROCESS::SetupCommandLine(
if ((wcsstr(pszPath, L":") == NULL) && (wcsstr(pszPath, L"%") == NULL)) if ((wcsstr(pszPath, L":") == NULL) && (wcsstr(pszPath, L"%") == NULL))
{ {
// let's check whether it is a relative path // let's check whether it is a relative path
if (FAILED(hr = strRelativePath.Copy(m_struPhysicalPath.QueryStr())) || if (FAILED_LOG(hr = strRelativePath.Copy(m_struPhysicalPath.QueryStr())) ||
FAILED(hr = strRelativePath.Append(L"\\")) || FAILED_LOG(hr = strRelativePath.Append(L"\\")) ||
FAILED(hr = strRelativePath.Append(pszPath))) FAILED_LOG(hr = strRelativePath.Append(pszPath)))
{ {
goto Finished; goto Finished;
} }
@ -482,9 +483,9 @@ SERVER_PROCESS::SetupCommandLine(
pszPath = pszFullPath; pszPath = pszFullPath;
} }
} }
if (FAILED(hr = pstrCommandLine->Copy(pszPath)) || if (FAILED_LOG(hr = pstrCommandLine->Copy(pszPath)) ||
FAILED(hr = pstrCommandLine->Append(L" ")) || FAILED_LOG(hr = pstrCommandLine->Append(L" ")) ||
FAILED(hr = pstrCommandLine->Append(m_Arguments.QueryStr()))) FAILED_LOG(hr = pstrCommandLine->Append(m_Arguments.QueryStr())))
{ {
goto Finished; goto Finished;
} }
@ -566,7 +567,7 @@ SERVER_PROCESS::PostStartCheck(
} }
// register call back with the created process // register call back with the created process
if (FAILED(hr = RegisterProcessWait(&m_hProcessWaitHandle, m_hProcessHandle))) if (FAILED_LOG(hr = RegisterProcessWait(&m_hProcessWaitHandle, m_hProcessHandle)))
{ {
goto Finished; goto Finished;
} }
@ -595,7 +596,7 @@ SERVER_PROCESS::PostStartCheck(
if (!fProcessMatch) if (!fProcessMatch)
{ {
// could be the scenario that backend creates child process // could be the scenario that backend creates child process
if (FAILED(hr = GetChildProcessHandles())) if (FAILED_LOG(hr = GetChildProcessHandles()))
{ {
goto Finished; goto Finished;
} }
@ -617,7 +618,7 @@ SERVER_PROCESS::PostStartCheck(
fDebuggerAttached = FALSE; fDebuggerAttached = FALSE;
} }
if (FAILED(hr = RegisterProcessWait(&m_hChildProcessWaitHandles[i], if (FAILED_LOG(hr = RegisterProcessWait(&m_hChildProcessWaitHandles[i],
m_hChildProcessHandles[i]))) m_hChildProcessHandles[i])))
{ {
goto Finished; goto Finished;
@ -678,7 +679,7 @@ SERVER_PROCESS::PostStartCheck(
hr = CheckIfServerIsUp(m_dwPort, &dwActualProcessId, &fReady); hr = CheckIfServerIsUp(m_dwPort, &dwActualProcessId, &fReady);
if ((FAILED(hr) || fReady == FALSE)) if ((FAILED_LOG(hr) || fReady == FALSE))
{ {
strEventMsg.SafeSnwprintf( strEventMsg.SafeSnwprintf(
ASPNETCORE_EVENT_PROCESS_START_NOTREADY_ERROR_MSG, ASPNETCORE_EVENT_PROCESS_START_NOTREADY_ERROR_MSG,
@ -705,7 +706,7 @@ SERVER_PROCESS::PostStartCheck(
} }
hr = m_pForwarderConnection->Initialize(m_dwPort); hr = m_pForwarderConnection->Initialize(m_dwPort);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -726,7 +727,7 @@ SERVER_PROCESS::PostStartCheck(
Finished: Finished:
m_fDebuggerAttached = fDebuggerAttached; m_fDebuggerAttached = fDebuggerAttached;
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
if (m_pForwarderConnection != NULL) if (m_pForwarderConnection != NULL)
{ {
@ -773,13 +774,13 @@ SERVER_PROCESS::StartProcess(
// //
// generate process command line. // generate process command line.
// //
if (FAILED(hr = SetupCommandLine(&m_struCommandLine))) if (FAILED_LOG(hr = SetupCommandLine(&m_struCommandLine)))
{ {
pStrStage = L"SetupCommandLine"; pStrStage = L"SetupCommandLine";
goto Failure; goto Failure;
} }
if (FAILED(hr = ENVIRONMENT_VAR_HELPERS::InitEnvironmentVariablesTable( if (FAILED_LOG(hr = ENVIRONMENT_VAR_HELPERS::InitEnvironmentVariablesTable(
m_pEnvironmentVarTable, m_pEnvironmentVarTable,
m_fWindowsAuthEnabled, m_fWindowsAuthEnabled,
m_fBasicAuthEnabled, m_fBasicAuthEnabled,
@ -790,7 +791,7 @@ SERVER_PROCESS::StartProcess(
goto Failure; goto Failure;
} }
if (FAILED(hr = ENVIRONMENT_VAR_HELPERS::AddWebsocketEnabledToEnvironmentVariables( if (FAILED_LOG(hr = ENVIRONMENT_VAR_HELPERS::AddWebsocketEnabledToEnvironmentVariables(
pHashTable, pHashTable,
m_fWebSocketSupported m_fWebSocketSupported
))) )))
@ -803,7 +804,7 @@ SERVER_PROCESS::StartProcess(
// //
// setup the the port that the backend process will listen on // setup the the port that the backend process will listen on
// //
if (FAILED(hr = SetupListenPort(pHashTable, &fCriticalError))) if (FAILED_LOG(hr = SetupListenPort(pHashTable, &fCriticalError)))
{ {
pStrStage = L"SetupListenPort"; pStrStage = L"SetupListenPort";
goto Failure; goto Failure;
@ -812,7 +813,7 @@ SERVER_PROCESS::StartProcess(
// //
// get app path // get app path
// //
if (FAILED(hr = SetupAppPath(pHashTable))) if (FAILED_LOG(hr = SetupAppPath(pHashTable)))
{ {
pStrStage = L"SetupAppPath"; pStrStage = L"SetupAppPath";
goto Failure; goto Failure;
@ -821,7 +822,7 @@ SERVER_PROCESS::StartProcess(
// //
// generate new guid for each process // generate new guid for each process
// //
if (FAILED(hr = SetupAppToken(pHashTable))) if (FAILED_LOG(hr = SetupAppToken(pHashTable)))
{ {
pStrStage = L"SetupAppToken"; pStrStage = L"SetupAppToken";
goto Failure; goto Failure;
@ -830,7 +831,7 @@ SERVER_PROCESS::StartProcess(
// //
// setup environment variables for new process // setup environment variables for new process
// //
if (FAILED(hr = OutputEnvironmentVariables(&mszNewEnvironment, pHashTable))) if (FAILED_LOG(hr = OutputEnvironmentVariables(&mszNewEnvironment, pHashTable)))
{ {
pStrStage = L"OutputEnvironmentVariables"; pStrStage = L"OutputEnvironmentVariables";
goto Failure; goto Failure;
@ -861,7 +862,7 @@ SERVER_PROCESS::StartProcess(
m_hProcessHandle = processInformation.hProcess; m_hProcessHandle = processInformation.hProcess;
m_dwProcessId = processInformation.dwProcessId; m_dwProcessId = processInformation.dwProcessId;
if (FAILED(hr = SetupJobObject())) if (FAILED_LOG(hr = SetupJobObject()))
{ {
pStrStage = L"SetupJobObject"; pStrStage = L"SetupJobObject";
goto Failure; goto Failure;
@ -890,7 +891,7 @@ SERVER_PROCESS::StartProcess(
// //
// need to make sure the server is up and listening on the port specified. // need to make sure the server is up and listening on the port specified.
// //
if (FAILED(hr = PostStartCheck())) if (FAILED_LOG(hr = PostStartCheck()))
{ {
pStrStage = L"PostStartCheck"; pStrStage = L"PostStartCheck";
goto Failure; goto Failure;
@ -944,7 +945,7 @@ SERVER_PROCESS::StartProcess(
} }
Finished: Finished:
if (FAILED(hr) || m_fReady == FALSE) if (FAILED_LOG(hr) || m_fReady == FALSE)
{ {
if (m_hStdoutHandle != NULL) if (m_hStdoutHandle != NULL)
{ {
@ -1034,7 +1035,7 @@ SERVER_PROCESS::SetupStdHandles(
m_struLogFile.QueryStr(), m_struLogFile.QueryStr(),
m_struPhysicalPath.QueryStr(), m_struPhysicalPath.QueryStr(),
&struPath); &struPath);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -1049,13 +1050,13 @@ SERVER_PROCESS::SetupStdHandles(
systemTime.wMinute, systemTime.wMinute,
systemTime.wSecond, systemTime.wSecond,
GetCurrentProcessId()); GetCurrentProcessId());
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
hr = FILE_UTILITY::EnsureDirectoryPathExist(struPath.QueryStr()); hr = FILE_UTILITY::EnsureDirectoryPathExist(struPath.QueryStr());
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -1086,7 +1087,7 @@ SERVER_PROCESS::SetupStdHandles(
m_Timer.InitializeTimer(STTIMER::TimerCallback, &m_struFullLogFile, 3000, 3000); m_Timer.InitializeTimer(STTIMER::TimerCallback, &m_struFullLogFile, 3000, 3000);
Finished: Finished:
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
pStartupInfo->dwFlags = STARTF_USESTDHANDLES; pStartupInfo->dwFlags = STARTF_USESTDHANDLES;
pStartupInfo->hStdInput = INVALID_HANDLE_VALUE; pStartupInfo->hStdInput = INVALID_HANDLE_VALUE;
@ -1305,7 +1306,7 @@ Finished:
hThread = NULL; hThread = NULL;
} }
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
TerminateBackendProcess(); TerminateBackendProcess();
} }
@ -1874,7 +1875,7 @@ SERVER_PROCESS::RegisterProcessWait(
Finished: Finished:
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
*phWaitHandle = NULL; *phWaitHandle = NULL;
DereferenceServerProcess(); DereferenceServerProcess();
@ -1981,10 +1982,10 @@ SERVER_PROCESS::SendShutdownHttpMessage( VOID )
} }
// set up the shutdown headers // set up the shutdown headers
if (FAILED(hr = strHeaders.Append(L"MS-ASPNETCORE-EVENT:shutdown \r\n")) || if (FAILED_LOG(hr = strHeaders.Append(L"MS-ASPNETCORE-EVENT:shutdown \r\n")) ||
FAILED(hr = strAppToken.Append(L"MS-ASPNETCORE-TOKEN:")) || FAILED_LOG(hr = strAppToken.Append(L"MS-ASPNETCORE-TOKEN:")) ||
FAILED(hr = strAppToken.AppendA(m_straGuid.QueryStr())) || FAILED_LOG(hr = strAppToken.AppendA(m_straGuid.QueryStr())) ||
FAILED(hr = strHeaders.Append(strAppToken.QueryStr()))) FAILED_LOG(hr = strHeaders.Append(strAppToken.QueryStr())))
{ {
goto Finished; goto Finished;
} }
@ -2072,7 +2073,7 @@ SERVER_PROCESS::SendShutDownSignalInternal(
{ {
ReferenceServerProcess(); ReferenceServerProcess();
if (FAILED(SendShutdownHttpMessage())) if (FAILED_LOG(SendShutdownHttpMessage()))
{ {
// //
// failed to send shutdown http message // failed to send shutdown http message

View File

@ -5,6 +5,7 @@
#include <Shlwapi.h> #include <Shlwapi.h>
#include "debugutil.h" #include "debugutil.h"
#include "exceptions.h"
// static // static
HRESULT HRESULT
@ -38,8 +39,6 @@ Return Value:
--*/ --*/
{ {
HRESULT hr;
// //
// First determine if the target is secure // First determine if the target is secure
// //
@ -55,12 +54,12 @@ Return Value:
} }
else else
{ {
return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); RETURN_HR(HRESULT_FROM_WIN32(ERROR_INVALID_DATA));
} }
if (*pszDestinationUrl == L'\0') if (*pszDestinationUrl == L'\0')
{ {
return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); RETURN_HR(HRESULT_FROM_WIN32(ERROR_INVALID_DATA));
} }
// //
@ -69,20 +68,14 @@ Return Value:
LPCWSTR pszSlash = wcschr(pszDestinationUrl, L'/'); LPCWSTR pszSlash = wcschr(pszDestinationUrl, L'/');
if (pszSlash == NULL) if (pszSlash == NULL)
{ {
if (FAILED(hr = pstrUrl->Copy(L"/", 1)) || RETURN_IF_FAILED(pstrUrl->Copy(L"/", 1));
FAILED(hr = pstrDestination->Copy(pszDestinationUrl))) RETURN_IF_FAILED(pstrDestination->Copy(pszDestinationUrl));
{
return hr;
}
} }
else else
{ {
if (FAILED(hr = pstrUrl->Copy(pszSlash)) || RETURN_IF_FAILED(pstrUrl->Copy(pszSlash));
FAILED(hr = pstrDestination->Copy(pszDestinationUrl, RETURN_IF_FAILED(pstrDestination->Copy(pszDestinationUrl,
(DWORD)(pszSlash - pszDestinationUrl)))) (DWORD)(pszSlash - pszDestinationUrl)));
{
return hr;
}
} }
return S_OK; return S_OK;
@ -102,34 +95,28 @@ URL_UTILITY::EscapeAbsPath(
STRU * strEscapedUrl STRU * strEscapedUrl
) )
{ {
HRESULT hr = S_OK;
STRU strAbsPath; STRU strAbsPath;
LPCWSTR pszAbsPath = NULL; LPCWSTR pszAbsPath = NULL;
LPCWSTR pszFindStr = NULL; LPCWSTR pszFindStr = NULL;
hr = strAbsPath.Copy( pRequest->GetRawHttpRequest()->CookedUrl.pAbsPath, RETURN_IF_FAILED(strAbsPath.Copy( pRequest->GetRawHttpRequest()->CookedUrl.pAbsPath,
pRequest->GetRawHttpRequest()->CookedUrl.AbsPathLength / sizeof(WCHAR) ); pRequest->GetRawHttpRequest()->CookedUrl.AbsPathLength / sizeof(WCHAR) ));
if(FAILED(hr))
{
goto Finished;
}
pszAbsPath = strAbsPath.QueryStr(); pszAbsPath = strAbsPath.QueryStr();
pszFindStr = wcschr(pszAbsPath, L'?'); pszFindStr = wcschr(pszAbsPath, L'?');
while(pszFindStr != NULL) while(pszFindStr != NULL)
{ {
strEscapedUrl->Append( pszAbsPath, pszFindStr - pszAbsPath); RETURN_IF_FAILED(strEscapedUrl->Append( pszAbsPath, pszFindStr - pszAbsPath));
strEscapedUrl->Append(L"%3F"); RETURN_IF_FAILED(strEscapedUrl->Append(L"%3F"));
pszAbsPath = pszFindStr + 1; pszAbsPath = pszFindStr + 1;
pszFindStr = wcschr(pszAbsPath, L'?'); pszFindStr = wcschr(pszAbsPath, L'?');
} }
strEscapedUrl->Append(pszAbsPath); RETURN_IF_FAILED(strEscapedUrl->Append(pszAbsPath));
strEscapedUrl->Append(pRequest->GetRawHttpRequest()->CookedUrl.pQueryString, RETURN_IF_FAILED(strEscapedUrl->Append(pRequest->GetRawHttpRequest()->CookedUrl.pQueryString,
pRequest->GetRawHttpRequest()->CookedUrl.QueryStringLength / sizeof(WCHAR)); pRequest->GetRawHttpRequest()->CookedUrl.QueryStringLength / sizeof(WCHAR)));
Finished: return S_OK;
return hr;
} }

View File

@ -28,6 +28,7 @@ This prevents the need for data buffering at the Asp.Net Core Module level.
--*/ --*/
#include "websockethandler.h" #include "websockethandler.h"
#include "exceptions.h"
SRWLOCK WEBSOCKET_HANDLER::sm_RequestsListLock; SRWLOCK WEBSOCKET_HANDLER::sm_RequestsListLock;
@ -86,7 +87,7 @@ HRESULT
WEBSOCKET_HANDLER::StaticInitialize( WEBSOCKET_HANDLER::StaticInitialize(
BOOL fEnableReferenceCountTracing BOOL fEnableReferenceCountTracing
) )
/*++ /*++
Routine Description: Routine Description:
@ -145,7 +146,7 @@ WEBSOCKET_HANDLER::InsertRequest(
} }
} }
//static //static
VOID VOID
WEBSOCKET_HANDLER::RemoveRequest( WEBSOCKET_HANDLER::RemoveRequest(
VOID VOID
@ -244,11 +245,11 @@ WEBSOCKET_HANDLER::ProcessRequest(
Routine Description: Routine Description:
Entry point to WebSocket Handler: Entry point to WebSocket Handler:
This routine is called after the 101 response was successfully sent to This routine is called after the 101 response was successfully sent to
the client. the client.
This routine get's a websocket handle to winhttp, This routine get's a websocket handle to winhttp,
websocket handle to IIS's websocket context, and initiates IO websocket handle to IIS's websocket context, and initiates IO
in these two endpoints. in these two endpoints.
@ -267,10 +268,10 @@ Routine Description:
// //
// Cache the points to IHttpContext3 // Cache the points to IHttpContext3
// //
hr = HttpGetExtendedInterface(g_pHttpServer, hr = HttpGetExtendedInterface(g_pHttpServer,
pHttpContext, pHttpContext,
&_pHttpContext); &_pHttpContext);
if (FAILED (hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -338,7 +339,7 @@ Routine Description:
// Initiate Read on IIS // Initiate Read on IIS
// //
hr = DoIisWebSocketReceive(); hr = DoIisWebSocketReceive();
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -348,7 +349,7 @@ Routine Description:
// //
hr = DoWinHttpWebSocketReceive(); hr = DoWinHttpWebSocketReceive();
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -356,7 +357,7 @@ Routine Description:
Finished: Finished:
LeaveCriticalSection(&_RequestLock); LeaveCriticalSection(&_RequestLock);
if (FAILED (hr)) if (FAILED_LOG(hr))
{ {
DebugPrintf (ASPNETCORE_DEBUG_FLAG_ERROR, DebugPrintf (ASPNETCORE_DEBUG_FLAG_ERROR,
"Process Request Failed with HR=%08x", hr); "Process Request Failed with HR=%08x", hr);
@ -399,7 +400,7 @@ Routine Description:
OnReadIoCompletion, OnReadIoCompletion,
this, this,
NULL); NULL);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
DecrementOutstandingIo(); DecrementOutstandingIo();
DebugPrintf(ASPNETCORE_DEBUG_FLAG_ERROR, DebugPrintf(ASPNETCORE_DEBUG_FLAG_ERROR,
@ -498,7 +499,7 @@ Routine Description:
// //
hr = strCloseReason.CopyA((PCSTR)&_WinHttpReceiveBuffer, hr = strCloseReason.CopyA((PCSTR)&_WinHttpReceiveBuffer,
dwReceived); dwReceived);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -549,13 +550,13 @@ Routine Description:
NULL); NULL);
} }
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
DecrementOutstandingIo(); DecrementOutstandingIo();
} }
Finished: Finished:
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
DebugPrintf(ASPNETCORE_DEBUG_FLAG_ERROR, DebugPrintf(ASPNETCORE_DEBUG_FLAG_ERROR,
"WEBSOCKET_HANDLER::DoIisWebSocketSend failed with %08x", hr); "WEBSOCKET_HANDLER::DoIisWebSocketSend failed with %08x", hr);
@ -592,10 +593,10 @@ Routine Description:
// //
// Get Close status from IIS. // Get Close status from IIS.
// //
hr = _pWebSocketContext->GetCloseStatus(&uStatus, hr = _pWebSocketContext->GetCloseStatus(&uStatus,
&pszReason); &pszReason);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -604,7 +605,7 @@ Routine Description:
// Convert status to UTF8 // Convert status to UTF8
// //
hr = strCloseReason.CopyWToUTF8Unescaped(pszReason); hr = strCloseReason.CopyWToUTF8Unescaped(pszReason);
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
@ -663,7 +664,7 @@ Routine Description:
} }
Finished: Finished:
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
DebugPrintf(ASPNETCORE_DEBUG_FLAG_ERROR, DebugPrintf(ASPNETCORE_DEBUG_FLAG_ERROR,
"WEBSOCKET_HANDLER::DoWinHttpWebSocketSend failed with %08x", hr); "WEBSOCKET_HANDLER::DoWinHttpWebSocketSend failed with %08x", hr);
@ -691,7 +692,7 @@ WEBSOCKET_HANDLER::OnReadIoCompletion(
--*/ --*/
{ {
WEBSOCKET_HANDLER * pHandler = (WEBSOCKET_HANDLER *) WEBSOCKET_HANDLER * pHandler = (WEBSOCKET_HANDLER *)
pvCompletionContext; pvCompletionContext;
pHandler->OnIisReceiveComplete( pHandler->OnIisReceiveComplete(
@ -721,7 +722,7 @@ WEBSOCKET_HANDLER::OnWriteIoCompletion(
--*/ --*/
{ {
WEBSOCKET_HANDLER * pHandler = (WEBSOCKET_HANDLER *) WEBSOCKET_HANDLER * pHandler = (WEBSOCKET_HANDLER *)
pvCompletionContext; pvCompletionContext;
UNREFERENCED_PARAMETER(fUTF8Encoded); UNREFERENCED_PARAMETER(fUTF8Encoded);
@ -776,18 +777,18 @@ Routine Description:
// //
hr = DoIisWebSocketReceive(); hr = DoIisWebSocketReceive();
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
goto Finished; goto Finished;
} }
Finished: Finished:
if (fLocked) if (fLocked)
{ {
LeaveCriticalSection(&_RequestLock); LeaveCriticalSection(&_RequestLock);
} }
if (FAILED (hr)) if (FAILED_LOG(hr))
{ {
Cleanup (cleanupReason); Cleanup (cleanupReason);
@ -848,7 +849,7 @@ Routine Description:
Issue send on the Client(IIS) if the receive was Issue send on the Client(IIS) if the receive was
successful. successful.
If the receive completed with zero bytes, that If the receive completed with zero bytes, that
indicates that the server has disconnected the connection. indicates that the server has disconnected the connection.
Issue cleanup for the websocket handler. Issue cleanup for the websocket handler.
--*/ --*/
@ -877,18 +878,18 @@ Routine Description:
pCompletionStatus->eBufferType pCompletionStatus->eBufferType
); );
if (FAILED (hr)) if (FAILED_LOG(hr))
{ {
cleanupReason = ClientDisconnect; cleanupReason = ClientDisconnect;
goto Finished; goto Finished;
} }
Finished: Finished:
if (fLocked) if (fLocked)
{ {
LeaveCriticalSection(&_RequestLock); LeaveCriticalSection(&_RequestLock);
} }
if (FAILED (hr)) if (FAILED_LOG(hr))
{ {
Cleanup (cleanupReason); Cleanup (cleanupReason);
@ -917,7 +918,7 @@ Routine Description:
Completion callback executed when a send Completion callback executed when a send
completes from the client. completes from the client.
If send was successful,issue read on the If send was successful,issue read on the
server endpoint, to continue the readloop. server endpoint, to continue the readloop.
--*/ --*/
@ -930,7 +931,7 @@ Routine Description:
DebugPrintf(ASPNETCORE_DEBUG_FLAG_INFO, "WEBSOCKET_HANDLER::OnIisSendComplete"); DebugPrintf(ASPNETCORE_DEBUG_FLAG_INFO, "WEBSOCKET_HANDLER::OnIisSendComplete");
if (FAILED(hrCompletion)) if (FAILED_LOG(hrCompletion))
{ {
hr = hrCompletion; hr = hrCompletion;
cleanupReason = ClientDisconnect; cleanupReason = ClientDisconnect;
@ -957,7 +958,7 @@ Routine Description:
// Write Completed, initiate next read from backend server. // Write Completed, initiate next read from backend server.
// //
hr = DoWinHttpWebSocketReceive(); hr = DoWinHttpWebSocketReceive();
if (FAILED(hr)) if (FAILED_LOG(hr))
{ {
cleanupReason = ServerDisconnect; cleanupReason = ServerDisconnect;
goto Finished; goto Finished;
@ -969,7 +970,7 @@ Finished:
{ {
LeaveCriticalSection(&_RequestLock); LeaveCriticalSection(&_RequestLock);
} }
if (FAILED (hr)) if (FAILED_LOG(hr))
{ {
Cleanup (cleanupReason); Cleanup (cleanupReason);
@ -1016,7 +1017,7 @@ Routine Description:
DebugPrintf(ASPNETCORE_DEBUG_FLAG_INFO, DebugPrintf(ASPNETCORE_DEBUG_FLAG_INFO,
"WEBSOCKET_HANDLER::OnIisReceiveComplete"); "WEBSOCKET_HANDLER::OnIisReceiveComplete");
if (FAILED(hrCompletion)) if (FAILED_LOG(hrCompletion))
{ {
cleanupReason = ClientDisconnect; cleanupReason = ClientDisconnect;
hr = hrCompletion; hr = hrCompletion;
@ -1029,7 +1030,7 @@ Routine Description:
} }
EnterCriticalSection(&_RequestLock); EnterCriticalSection(&_RequestLock);
fLocked = TRUE; fLocked = TRUE;
if (_fCleanupInProgress) if (_fCleanupInProgress)
{ {
@ -1049,7 +1050,7 @@ Routine Description:
// //
hr = DoWinHttpWebSocketSend(cbIO, BufferType); hr = DoWinHttpWebSocketSend(cbIO, BufferType);
if (FAILED (hr)) if (FAILED_LOG(hr))
{ {
cleanupReason = ServerDisconnect; cleanupReason = ServerDisconnect;
goto Finished; goto Finished;
@ -1060,7 +1061,7 @@ Finished:
{ {
LeaveCriticalSection(&_RequestLock); LeaveCriticalSection(&_RequestLock);
} }
if (FAILED (hr)) if (FAILED_LOG(hr))
{ {
Cleanup (cleanupReason); Cleanup (cleanupReason);

View File

@ -2,6 +2,7 @@
// Licensed under the MIT License. See License.txt in the project root for license information. // Licensed under the MIT License. See License.txt in the project root for license information.
#include "winhttphelper.h" #include "winhttphelper.h"
#include "exceptions.h"
PFN_WINHTTP_WEBSOCKET_COMPLETE_UPGRADE PFN_WINHTTP_WEBSOCKET_COMPLETE_UPGRADE
WINHTTP_HELPER::sm_pfnWinHttpWebSocketCompleteUpgrade; WINHTTP_HELPER::sm_pfnWinHttpWebSocketCompleteUpgrade;
@ -24,8 +25,6 @@ WINHTTP_HELPER::StaticInitialize(
VOID VOID
) )
{ {
HRESULT hr = S_OK;
// //
// Initialize the function pointers for WinHttp Websocket API's. // Initialize the function pointers for WinHttp Websocket API's.
// //
@ -35,54 +34,29 @@ WINHTTP_HELPER::StaticInitialize(
} }
HMODULE hWinHttp = GetModuleHandleA("winhttp.dll"); HMODULE hWinHttp = GetModuleHandleA("winhttp.dll");
if (hWinHttp == NULL) RETURN_LAST_ERROR_IF (hWinHttp == NULL);
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
sm_pfnWinHttpWebSocketCompleteUpgrade = (PFN_WINHTTP_WEBSOCKET_COMPLETE_UPGRADE) sm_pfnWinHttpWebSocketCompleteUpgrade = (PFN_WINHTTP_WEBSOCKET_COMPLETE_UPGRADE)
GetProcAddress(hWinHttp, "WinHttpWebSocketCompleteUpgrade"); GetProcAddress(hWinHttp, "WinHttpWebSocketCompleteUpgrade");
if (sm_pfnWinHttpWebSocketCompleteUpgrade == NULL) RETURN_LAST_ERROR_IF (sm_pfnWinHttpWebSocketCompleteUpgrade == NULL);
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
sm_pfnWinHttpWebSocketQueryCloseStatus = (PFN_WINHTTP_WEBSOCKET_QUERY_CLOSE_STATUS) sm_pfnWinHttpWebSocketQueryCloseStatus = (PFN_WINHTTP_WEBSOCKET_QUERY_CLOSE_STATUS)
GetProcAddress(hWinHttp, "WinHttpWebSocketQueryCloseStatus"); GetProcAddress(hWinHttp, "WinHttpWebSocketQueryCloseStatus");
if (sm_pfnWinHttpWebSocketQueryCloseStatus == NULL) RETURN_LAST_ERROR_IF (sm_pfnWinHttpWebSocketQueryCloseStatus == NULL);
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
sm_pfnWinHttpWebSocketReceive = (PFN_WINHTTP_WEBSOCKET_RECEIVE) sm_pfnWinHttpWebSocketReceive = (PFN_WINHTTP_WEBSOCKET_RECEIVE)
GetProcAddress(hWinHttp, "WinHttpWebSocketReceive"); GetProcAddress(hWinHttp, "WinHttpWebSocketReceive");
if (sm_pfnWinHttpWebSocketReceive == NULL) RETURN_LAST_ERROR_IF (sm_pfnWinHttpWebSocketReceive == NULL);
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
sm_pfnWinHttpWebSocketSend = (PFN_WINHTTP_WEBSOCKET_SEND) sm_pfnWinHttpWebSocketSend = (PFN_WINHTTP_WEBSOCKET_SEND)
GetProcAddress(hWinHttp, "WinHttpWebSocketSend"); GetProcAddress(hWinHttp, "WinHttpWebSocketSend");
if (sm_pfnWinHttpWebSocketSend == NULL) RETURN_LAST_ERROR_IF (sm_pfnWinHttpWebSocketSend == NULL);
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
sm_pfnWinHttpWebSocketShutdown = (PFN_WINHTTP_WEBSOCKET_SHUTDOWN) sm_pfnWinHttpWebSocketShutdown = (PFN_WINHTTP_WEBSOCKET_SHUTDOWN)
GetProcAddress(hWinHttp, "WinHttpWebSocketShutdown"); GetProcAddress(hWinHttp, "WinHttpWebSocketShutdown");
if (sm_pfnWinHttpWebSocketShutdown == NULL) RETURN_LAST_ERROR_IF (sm_pfnWinHttpWebSocketShutdown == NULL);
{
hr = HRESULT_FROM_WIN32(GetLastError());
goto Finished;
}
Finished: return S_OK;
return hr;
} }
@ -170,6 +144,4 @@ WINHTTP_HELPER::GetBufferTypeFromFlags(
*pBufferType = WINHTTP_WEB_SOCKET_BINARY_FRAGMENT_BUFFER_TYPE; *pBufferType = WINHTTP_WEB_SOCKET_BINARY_FRAGMENT_BUFFER_TYPE;
} }
} }
return;
} }