Skip to content

Commit ee6c9bf

Browse files
committed
Merge pull request #365 from Azure/iisnode-dev
v0.2.15
2 parents 57401b0 + 66d9afd commit ee6c9bf

19 files changed

+1414
-828
lines changed

src/iisnode/chttpprotocol.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -375,7 +375,7 @@ HRESULT CHttpProtocol::ParseResponseStatusLine(CNodeHttpStoredContext* context)
375375

376376
if (ERROR_MORE_DATA != hr)
377377
{
378-
context->GetNodeApplication()->GetApplicationManager()->GetEventProvider()->Log(
378+
context->GetNodeApplication()->GetApplicationManager()->GetEventProvider()->Log( context->GetHttpContext(),
379379
L"iisnode failed to parse response status line", WINEVENT_LEVEL_ERROR, context->GetActivityId());
380380
}
381381

@@ -470,7 +470,7 @@ HRESULT CHttpProtocol::ParseChunkHeader(CNodeHttpStoredContext* context)
470470

471471
if (ERROR_MORE_DATA != hr)
472472
{
473-
context->GetNodeApplication()->GetApplicationManager()->GetEventProvider()->Log(
473+
context->GetNodeApplication()->GetApplicationManager()->GetEventProvider()->Log( context->GetHttpContext(),
474474
L"iisnode failed to parse response body chunk header", WINEVENT_LEVEL_ERROR, context->GetActivityId());
475475

476476
return hr;

src/iisnode/cnodeapplication.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -57,12 +57,12 @@ HRESULT CNodeApplication::Initialize(PCWSTR scriptName, IHttpContext* context)
5757
this->GetApplicationManager(),
5858
this));
5959

60-
this->GetApplicationManager()->GetEventProvider()->Log(L"iisnode initialized a new node.js application", WINEVENT_LEVEL_INFO);
60+
this->GetApplicationManager()->GetEventProvider()->Log(context, L"iisnode initialized a new node.js application", WINEVENT_LEVEL_INFO);
6161

6262
return S_OK;
6363
Error:
6464

65-
this->GetApplicationManager()->GetEventProvider()->Log(L"iisnode failed to initialize a new node.js application", WINEVENT_LEVEL_ERROR);
65+
this->GetApplicationManager()->GetEventProvider()->Log(context, L"iisnode failed to initialize a new node.js application", WINEVENT_LEVEL_ERROR);
6666

6767
this->Cleanup();
6868

src/iisnode/cnodeapplicationmanager.cpp

Lines changed: 132 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ CNodeApplicationManager::CNodeApplicationManager(IHttpServer* server, HTTP_MODUL
55
: server(server), moduleId(moduleId), applications(NULL), asyncManager(NULL), jobObject(NULL),
66
breakAwayFromJobObject(FALSE), fileWatcher(NULL), initialized(FALSE), eventProvider(NULL),
77
currentDebugPort(0), inspector(NULL), totalRequests(0), controlSignalHandlerThread(NULL),
8-
signalPipe(NULL), signalPipeName(NULL), pPipeSecAttr(NULL)
8+
signalPipe(NULL), signalPipeName(NULL), pPipeSecAttr(NULL), _fSignalPipeInitialized( FALSE )
99
{
1010
InitializeSRWLock(&this->srwlock);
1111
}
@@ -90,13 +90,95 @@ CNodeApplicationManager::GetPipeSecurityAttributes(
9090
return this->pPipeSecAttr;
9191
}
9292

93+
HRESULT CNodeApplicationManager::InitializeControlPipe()
94+
{
95+
HRESULT hr = S_OK;
96+
UUID uuid;
97+
RPC_WSTR suuid = NULL;
98+
99+
if( _fSignalPipeInitialized )
100+
{
101+
return hr;
102+
}
103+
104+
//
105+
// generate unique pipe name
106+
//
107+
108+
ErrorIf(RPC_S_OK != UuidCreate(&uuid), ERROR_CAN_NOT_COMPLETE);
109+
ErrorIf(RPC_S_OK != UuidToStringW(&uuid, &suuid), ERROR_NOT_ENOUGH_MEMORY);
110+
ErrorIf((this->signalPipeName = new WCHAR[1024]) == NULL, ERROR_NOT_ENOUGH_MEMORY);
111+
wcscpy(this->signalPipeName, L"\\\\.\\pipe\\");
112+
wcscpy(this->signalPipeName + 9, (WCHAR*)suuid);
113+
RpcStringFreeW(&suuid);
114+
suuid = NULL;
115+
116+
this->signalPipe = CreateNamedPipeW( this->signalPipeName,
117+
PIPE_ACCESS_INBOUND,
118+
PIPE_TYPE_MESSAGE | PIPE_WAIT,
119+
1,
120+
MAX_BUFFER_SIZE,
121+
MAX_BUFFER_SIZE,
122+
0,
123+
GetPipeSecurityAttributes() );
124+
125+
ErrorIf( this->signalPipe == INVALID_HANDLE_VALUE,
126+
HRESULT_FROM_WIN32(ERROR_INVALID_HANDLE) );
127+
128+
//
129+
// start pipe reader thread.
130+
//
131+
132+
this->controlSignalHandlerThread = (HANDLE) _beginthreadex( NULL,
133+
0,
134+
CNodeApplicationManager::ControlSignalHandler,
135+
this,
136+
0,
137+
NULL);
138+
139+
ErrorIf((HANDLE)-1L == this->controlSignalHandlerThread, ERROR_NOT_ENOUGH_MEMORY);
140+
141+
this->GetEventProvider()->Log(L"iisnode initialized control pipe", WINEVENT_LEVEL_INFO);
142+
143+
_fSignalPipeInitialized = TRUE;
144+
145+
Error:
146+
147+
if(suuid != NULL)
148+
{
149+
RpcStringFreeW(&suuid);
150+
suuid = NULL;
151+
}
152+
153+
if( FAILED( hr ) )
154+
{
155+
if(NULL != this->controlSignalHandlerThread)
156+
{
157+
CloseHandle(this->controlSignalHandlerThread);
158+
this->controlSignalHandlerThread = NULL;
159+
}
160+
161+
if(NULL != this->signalPipe)
162+
{
163+
CloseHandle(this->signalPipe);
164+
this->signalPipe = NULL;
165+
}
166+
167+
if(NULL != this->signalPipeName)
168+
{
169+
delete[] this->signalPipeName;
170+
this->signalPipeName = NULL;
171+
}
172+
}
173+
174+
return hr;
175+
}
176+
93177
HRESULT CNodeApplicationManager::InitializeCore(IHttpContext* context)
94178
{
95179
HRESULT hr;
96180
BOOL isInJob, createJob;
97181
JOBOBJECT_EXTENDED_LIMIT_INFORMATION jobInfo;
98-
UUID uuid;
99-
RPC_WSTR suuid = NULL;
100182

101183
ErrorIf(NULL == (this->eventProvider = new CNodeEventProvider()), ERROR_NOT_ENOUGH_MEMORY);
102184
CheckError(this->eventProvider->Initialize());
@@ -150,62 +232,19 @@ HRESULT CNodeApplicationManager::InitializeCore(IHttpContext* context)
150232
HRESULT_FROM_WIN32(GetLastError()));
151233
}
152234

153-
if(CModuleConfiguration::GetRecycleSignalEnabled(context))
235+
if(CModuleConfiguration::GetRecycleSignalEnabled(context) && !_fSignalPipeInitialized)
154236
{
155-
//
156-
// generate unique pipe name
157-
//
158-
159-
ErrorIf(RPC_S_OK != UuidCreate(&uuid), ERROR_CAN_NOT_COMPLETE);
160-
ErrorIf(RPC_S_OK != UuidToStringW(&uuid, &suuid), ERROR_NOT_ENOUGH_MEMORY);
161-
ErrorIf((this->signalPipeName = new WCHAR[1024]) == NULL, ERROR_NOT_ENOUGH_MEMORY);
162-
wcscpy(this->signalPipeName, L"\\\\.\\pipe\\");
163-
wcscpy(this->signalPipeName + 9, (WCHAR*)suuid);
164-
RpcStringFreeW(&suuid);
165-
suuid = NULL;
166-
167-
this->signalPipe = CreateNamedPipeW( this->signalPipeName,
168-
PIPE_ACCESS_INBOUND,
169-
PIPE_TYPE_MESSAGE | PIPE_WAIT,
170-
1,
171-
MAX_BUFFER_SIZE,
172-
MAX_BUFFER_SIZE,
173-
0,
174-
GetPipeSecurityAttributes() );
175-
176-
ErrorIf( this->signalPipe == INVALID_HANDLE_VALUE,
177-
HRESULT_FROM_WIN32(ERROR_INVALID_HANDLE) );
178-
179-
//
180-
// start pipe reader thread.
181-
//
182-
183-
this->controlSignalHandlerThread = (HANDLE) _beginthreadex( NULL,
184-
0,
185-
CNodeApplicationManager::ControlSignalHandler,
186-
this,
187-
0,
188-
NULL);
189-
190-
ErrorIf((HANDLE)-1L == this->controlSignalHandlerThread, ERROR_NOT_ENOUGH_MEMORY);
191-
192-
this->GetEventProvider()->Log(L"iisnode initialized control pipe", WINEVENT_LEVEL_INFO);
237+
CheckError(InitializeControlPipe());
193238
}
194239

195240
this->initialized = TRUE;
196241

197-
this->GetEventProvider()->Log(L"iisnode initialized the application manager", WINEVENT_LEVEL_INFO);
242+
this->GetEventProvider()->Log(context, L"iisnode initialized the application manager", WINEVENT_LEVEL_INFO);
198243

199244
return S_OK;
200245
Error:
201246

202-
this->GetEventProvider()->Log(L"iisnode failed to initialize the application manager", WINEVENT_LEVEL_ERROR);
203-
204-
if(suuid != NULL)
205-
{
206-
RpcStringFreeW(&suuid);
207-
suuid = NULL;
208-
}
247+
this->GetEventProvider()->Log(context, L"iisnode failed to initialize the application manager", WINEVENT_LEVEL_ERROR);
209248

210249
if (NULL != this->asyncManager)
211250
{
@@ -230,6 +269,8 @@ HRESULT CNodeApplicationManager::InitializeCore(IHttpContext* context)
230269

231270
CNodeApplicationManager::~CNodeApplicationManager()
232271
{
272+
HANDLE hPipe = NULL;
273+
233274
while (NULL != this->applications)
234275
{
235276
delete this->applications->nodeApplication;
@@ -238,6 +279,30 @@ CNodeApplicationManager::~CNodeApplicationManager()
238279
delete current;
239280
}
240281

282+
if( _fSignalPipeInitialized )
283+
{
284+
//
285+
// try to connect to the pipe to unblock the thread
286+
// waiting on ConnectNamedPipe
287+
// We dont need to check any errors on whether the connect
288+
// succeeded because we dont care.
289+
//
290+
291+
hPipe = CreateFileW( this->GetSignalPipeName(),
292+
GENERIC_WRITE,
293+
0,
294+
NULL,
295+
OPEN_EXISTING,
296+
0,
297+
NULL );
298+
299+
if(hPipe != NULL)
300+
{
301+
CloseHandle(hPipe);
302+
hPipe = NULL;
303+
}
304+
}
305+
241306
if(NULL != this->controlSignalHandlerThread)
242307
{
243308
CloseHandle(this->controlSignalHandlerThread);
@@ -304,7 +369,7 @@ CAsyncManager* CNodeApplicationManager::GetAsyncManager()
304369

305370
HRESULT CNodeApplicationManager::Dispatch(IHttpContext* context, IHttpEventProvider* pProvider, CNodeHttpStoredContext** ctx)
306371
{
307-
HRESULT hr;
372+
HRESULT hr = S_OK;
308373
CNodeApplication* application;
309374
NodeDebugCommand debugCommand;
310375

@@ -319,6 +384,18 @@ HRESULT CNodeApplicationManager::Dispatch(IHttpContext* context, IHttpEventProvi
319384
{
320385
default:
321386

387+
if(CModuleConfiguration::GetRecycleSignalEnabled(context) && !_fSignalPipeInitialized)
388+
{
389+
ENTER_SRW_EXCLUSIVE(this->srwlock)
390+
391+
if(CModuleConfiguration::GetRecycleSignalEnabled(context) && !_fSignalPipeInitialized)
392+
{
393+
CheckError(InitializeControlPipe());
394+
}
395+
396+
LEAVE_SRW_EXCLUSIVE(this->srwlock)
397+
}
398+
322399
ENTER_SRW_SHARED(this->srwlock)
323400

324401
CheckError(this->GetOrCreateNodeApplication(context, debugCommand, FALSE, &application));
@@ -554,7 +631,7 @@ HRESULT CNodeApplicationManager::GetOrCreateNodeApplicationCore(PCWSTR physicalP
554631
}
555632
else
556633
{
557-
this->GetEventProvider()->Log(L"iisnode found an existing node.js application to dispatch the http request to", WINEVENT_LEVEL_VERBOSE);
634+
this->GetEventProvider()->Log(context, L"iisnode found an existing node.js application to dispatch the http request to", WINEVENT_LEVEL_VERBOSE);
558635
}
559636

560637
return S_OK;
@@ -569,7 +646,7 @@ HRESULT CNodeApplicationManager::GetOrCreateNodeApplicationCore(PCWSTR physicalP
569646
delete applicationEntry;
570647
}
571648

572-
this->GetEventProvider()->Log(L"iisnode failed to create a new node.js application", WINEVENT_LEVEL_ERROR);
649+
this->GetEventProvider()->Log(context, L"iisnode failed to create a new node.js application", WINEVENT_LEVEL_ERROR);
573650

574651
return hr;
575652
}
@@ -860,7 +937,7 @@ HRESULT CNodeApplicationManager::GetOrCreateDebuggedNodeApplicationCore(PCWSTR p
860937
}
861938
else
862939
{
863-
this->GetEventProvider()->Log(L"iisnode found an existing node.js debugger to dispatch the http request to", WINEVENT_LEVEL_VERBOSE);
940+
this->GetEventProvider()->Log(context, L"iisnode found an existing node.js debugger to dispatch the http request to", WINEVENT_LEVEL_VERBOSE);
864941
}
865942

866943
return S_OK;
@@ -884,7 +961,7 @@ HRESULT CNodeApplicationManager::GetOrCreateDebuggedNodeApplicationCore(PCWSTR p
884961
delete debuggerEntry;
885962
}
886963

887-
this->GetEventProvider()->Log(L"iisnode failed to create a new node.js application to debug or the debugger for that application", WINEVENT_LEVEL_ERROR);
964+
this->GetEventProvider()->Log(context, L"iisnode failed to create a new node.js application to debug or the debugger for that application", WINEVENT_LEVEL_ERROR);
888965

889966
return hr;
890967
}

src/iisnode/cnodeapplicationmanager.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ class CNodeApplicationManager
4040
HMODULE inspector;
4141
LONG totalRequests;
4242

43+
BOOL _fSignalPipeInitialized;
4344
HANDLE signalPipe;
4445
HANDLE controlSignalHandlerThread;
4546
LPWSTR signalPipeName;
@@ -65,7 +66,7 @@ class CNodeApplicationManager
6566
HRESULT FindNextDebugPort(IHttpContext* context, DWORD* port);
6667
HRESULT EnsureDebugeeReady(IHttpContext* context, DWORD debugPort);
6768
HRESULT InitializeCore(IHttpContext* context);
68-
69+
HRESULT InitializeControlPipe();
6970
static unsigned int WINAPI ControlSignalHandler(void* arg);
7071

7172
public:

0 commit comments

Comments
 (0)