rdpwsx!TSrvDoConnect函数分析和rdpwsx!TSrvStackConnect函数分析之调试记录的验证
第一部分:
03:44:35.421 894EFF7C.E16655C8 TShrSRV: TSrvAllocInfo exit - 0x0
03:44:35.421 894EFF7C.E16655C8 TShrSRV: TSrvDoConnect entry
03:44:35.421 894EFF7C.E16655C8 TShrSRV: TSrvReferenceInfo entry
03:44:35.421 894EFF7C.E16655C8 TShrSRV: TSrvReferenceInfo exit
03:44:35.421 894EFF7C.E16655C8 TShrSRV: Waiting for connection Ind signal for pTSrvInfo 0xd62ad0
03:44:35.421 8954D5E4.00000000 TermDD: IcaChannelInput, bc=1076 (enter)
03:44:35.421 890EC1FC.E177A920 GCC: mcsCallback entry
03:44:35.421 890EC1FC.E177A920 GCC: Message 0x0, pvParam 0xe4ff40, pvContext 0xd62ad0
03:44:35.421 890EC1FC.E177A920 GCC: gccConnectProviderIndication entry (MCS userDataLength = 0x12f)
03:44:35.421 890EC1FC.E177A920 GCC: gccDecodeUserData entry
03:44:35.421 890EC1FC.E177A920 GCC: gccDecodeUserData (len=0x118) exit - 0x0
03:44:35.421 890EC1FC.E177A920 GCC: Performing GCC_CREATE_INDICATION callout
03:44:35.421 890EC1FC.E177A920 TShrSRV: TSrvGCCCallBack entry
03:44:35.421 890EC1FC.E177A920 TShrSRV: GCCCallback message 0x0 (GCC_CREATE_INDICATION) received
03:44:35.437 890EC1FC.E177A920 TShrSRV: TSrvHandleCreateInd entry
03:44:35.437 890EC1FC.E177A920 TShrSRV: Accepting create indication - Domain 00D62B68
03:44:35.437 890EC1FC.E177A920 TShrSRV: Conductor privilege list is NULL
03:44:35.437 890EC1FC.E177A920 TShrSRV: Conducted mode privilege list is NULL
03:44:35.437 890EC1FC.E177A920 TShrSRV: Non-conducted mode privilege list is NULL
03:44:35.437 890EC1FC.E177A920 TShrSRV: NULL conf name
03:44:35.437 890EC1FC.E177A920 TShrSRV: Attempting to save CreateInd userData
03:44:35.437 890EC1FC.E177A920 TShrSRV: TSrvSaveUserData entry
03:44:35.437 890EC1FC.E177A920 TShrSRV: TSrvCalculateUserDataSize entry
03:44:35.437 890EC1FC.E177A920 TShrSRV: number_of_user_data_members = 0x1
03:44:35.453 890EC1FC.E177A920 TShrSRV: Key_type = 0x2 (GCC_H221_NONSTANDARD_KEY)
03:44:35.453 890EC1FC.E177A920 TShrSRV: key long_string_length = 0x4
03:44:35.453 890EC1FC.E177A920 TShrSRV: data long_string_length = 0x118
03:44:35.453 890EC1FC.E177A920 TShrSRV: TSrvCalculateUserDataSize exit - 0x124
03:44:35.453 890EC1FC.E177A920 TShrSRV: Allocated 0x154 bytes for UserData save space
03:44:35.468 890EC1FC.E177A920 TShrSRV: Saving each UserDataMenber to save space
03:44:35.468 890EC1FC.E177A920 TShrSRV: TSrvSaveUserDataMember entry
03:44:35.468 890EC1FC.E177A920 TShrSRV: TSrvSaveUserDataMember exit
03:44:35.468 890EC1FC.E177A920 TShrSRV: TSrvSaveUserData exit - 0x0
03:44:35.468 890EC1FC.E177A920 TShrSRV: Save userData was successful
03:44:35.468 890EC1FC.E177A920 TShrSRV: TSrvSignalIndication entry
03:44:35.468 890EC1FC.E177A920 TShrSRV: Signaling workEvent 00000200, status 0x0
03:44:35.484 890EC1FC.E177A920 TShrSRV: TSrvSignalIndication exit
03:44:35.484 894EFF7C.E16655C8 TShrSRV: Connection Ind signal received for pTSrvInfo 00D62AD0 - 0x0
03:44:35.484 890EC1FC.E177A920 TShrSRV: TSrvHandleCreateInd exit
03:44:35.484 894EFF7C.E16655C8 TShrSRV: TSrvDoConnectResponse entry
03:44:35.484 890EC1FC.E177A920 TShrSRV: TSrvGCCCallBack exit - GCC_CALLBACK_PROCESSED
03:44:35.500 894EFF7C.E16655C8 TShrSRV: TSrvConfCreateResp entry
03:44:35.500 890EC1FC.E177A920 GCC: Returned from GCC_CREATE_INDICATION callout
03:44:35.500 894EFF7C.E16655C8 TShrSRV: Attempting ConfCreate response
03:44:35.500 890EC1FC.E177A920 GCC: gccConnectProviderIndication exit - 0x0
03:44:35.500 894EFF7C.E16655C8 TShrSRV: TSrvInitWD entry
03:44:35.500 890EC1FC.E177A920 GCC: mcsCallback exit - 0x0
03:44:35.500 894EFF7C.E16655C8 TShrSRV: Performing WDTShare connection info exchange
03:44:35.500 894EFF7C.E16655C8 TShrSRV: TSrvInitWDConnectInfo entry
03:44:35.500 894EFF7C.E16655C8 TShrSRV: Allocated 0x80 bytes to recieve WDTShare return data
03:44:35.500 894EFF7C.E16655C8 TShrSRV: Performing connect (size=128)
RDPWD: New: ShareClass at E1861440, size=1392
03:44:35.500 894EFF7C.E16655C8 RDP E1895010 WDW_OnSMConn 0677 pOutData at 00D63188
03:44:35.500 894EFF7C.E16655C8 RDP E1895010 WDW_OnSMConn 0711 Key octet at 00D631A8 (offs 00000020)
03:44:35.500 894EFF7C.E16655C8 RDP E1895010 WDW_OnSMConn 0719 Data octet pointer at 00D631AC (offs 00000024)
03:44:35.500 894EFF7C.E16655C8 RDP E1895010 WDW_OnSMConn 0733 Core data at 00D631B4 (offs 0000002C)
03:44:35.500 894EFF7C.E16655C8 RDP E1895010 WDW_OnSMConn 0738 Net data at 00D631BC (offs 00000034)
03:44:35.500 894EFF7C.E16655C8 RDP E1895010 WDW_OnSMConn 0747 Sec data at 00D631CC (offs 00000044)
03:44:35.500 894EFF7C.E16655C8 RDP E1895010 WDW_OnSMConn 0757 Build 80 bytes of returned user data
03:44:35.500 894EFF7C.E16655C8 TermDD: IcaDeviceControlStack, fc 2304, 0x0
03:44:35.500 894EFF7C.E16655C8 TShrSRV: TSrvInitWDConnectInfo exit - 0x0
03:44:35.500 894EFF7C.E16655C8 TShrSRV: TSrvInitWD exit - 0x0
03:44:35.500 894EFF7C.E16655C8 TShrSRV: TSrvCreateGCCDataList entry
03:44:35.500 894EFF7C.E16655C8 TShrSRV: Creating UserData list
03:44:35.500 894EFF7C.E16655C8 TShrSRV: Allocated 0x4 bytes for 0x1 member UserData array
03:44:35.500 894EFF7C.E16655C8 TShrSRV: TSrvCreateGCCDataList exit = 0xd63018
03:44:35.500 894EFF7C.E16655C8 TShrSRV: Accepting conference domain 00D62B68
03:44:35.500 894EFF7C.E16655C8 GCC: GCCConferenceCreateResponse entry
03:44:35.500 894EFF7C.E16655C8 GCC: gccEncodeUserData entry
03:44:35.500 894EFF7C.E16655C8 GCC: gccEncodeUserData exit - 0x0
03:44:35.500 894EFF7C.E16655C8 GCC: Calling MCSConnectProviderResponse - hDomain 0xd62b68, result 0x0, pUserData 0xd63318, UserDataLength 0x11b
03:44:35.500 894EFF7C.E16655C8 TermDD: IcaDeviceControlStack, fc 1280, 0x0
03:44:35.500 894EFF7C.E16655C8 GCC: MCSConnectProviderResponse - MCSError 0x0 (MCS_NO_ERROR)
03:44:35.500 894EFF7C.E16655C8 GCC: gccMapMcsError: mcsError 0x0 (MCS_NO_ERROR), gbbError 0x0 (GCC_NO_ERROR)
03:44:35.500 894EFF7C.E16655C8 GCC: GCCConferenceCreateResponse exit - 0x0
03:44:35.500 894EFF7C.E16655C8 TShrSRV: GCCConferenceCreateResponse - GCC rc 0x0 (GCC_NO_ERROR)
03:44:35.500 894EFF7C.E16655C8 TShrSRV: Waiting to receive client random: msec=60000
03:44:35.500 894EFF7C.E16655C8 TermDD: IcaWaitForMultipleObjects, 60000 (enter)
03:44:35.500 8954D5E4.00000000 RDP E1895010 SM_MCSSendDa 0507 Encrypting=1: security packet
03:44:35.500 894EFF7C.E16655C8 RDP E1895010 WDW_WaitForC 0920 Primary event hit
03:44:35.500 894EFF7C.E16655C8 RDP E1895010 SM_GetSecuri 1349 Back from wait for security data
03:44:35.515 894EFF7C.E16655C8 TermDD: IcaDeviceControlStack, fc 2308, 0x0
03:44:35.515 894EFF7C.E16655C8 TShrSRV: Received encrypted client random, rc=0
03:44:35.515 8954D5E4.00000000 RDP E1895010 SM_MCSSendDa 0507 Encrypting=1: security packet
03:44:35.515 8954D5E4.00000000 RDP E1895010 SMSecurityEx 0301 About to wait for session key creation
03:44:35.515 8954D5E4.00000000 TermDD: IcaWaitForMultipleObjects, -1 (enter)
03:44:35.515 894EFF7C.E16655C8 TShrSRV: Decrypted client random: rc=0
03:44:35.515 894EFF7C.E16655C8 TShrSRV: Sending sec info to WD
03:44:35.515 894EFF7C.E16655C8 TermDD: IcaDeviceControlStack, fc 2309, 0x0
03:44:35.515 8954D5E4.00000000 RDP E1895010 WDW_WaitForC 0920 Primary event hit
03:44:35.515 8954D5E4.00000000 RDP E1895010 SMSecurityEx 0304 Back from wait for session key creation
03:44:35.515 894EFF7C.E16655C8 TShrSRV: Session key transmission succeeded, PrevStatus=0
03:44:35.515 894EFF7C.E16655C8 TShrSRV: TSrvConfCreateResp exit = 0x0
03:44:35.515 894EFF7C.E16655C8 TShrSRV: TSrvDoConnectResponse exit - 0x0
03:44:35.515 894EFF7C.E16655C8 TShrSRV: TSrvDereferenceInfo entry
03:44:35.515 894EFF7C.E16655C8 TShrSRV: TSrvDereferenceInfo exit
03:44:35.515 894EFF7C.E16655C8 TShrSRV: TSrvDoConnect exit - 0x0
03:44:35.515 894EFF7C.E16655C8 TShrSRV: TSrvStackConnect exit - 0x0
03:44:35.515 894EFF7C.E16655C8 TShrSRV: WsxIcaStackIoControl exit - 0x0
03:44:35.515 894EFF7C.E16655C8 TSAPI: _IcaWaitForIca, success
03:44:35.515 894EFF7C.E16655C8 TERMSRV: Enter WsxIcaIoControl, IoControlCode=19
03:44:35.515 894EFF7C.E16655C8 TShrSRV: WsxIcaStackIoControl entry
03:44:35.515 894EFF7C.E16655C8 TShrSRV: 00D62808:00D62AD0 IoctlDetail: Ioctl 0x38004f (IOCTL_ICA_STACK_CONNECTION_QUERY)
03:44:35.515 8954D5E4.00000000 RDP E1895010 SMSecurityEx 0309 Decrypt the packet
03:44:35.531 8954D5E4.00000000 RDP E1895010 SMDecryptPac 0186 Data decrypted: 362
第二部分:
Breakpoint 19 hit
rdpwsx!TSrvConfCreateResp:
001b:70fbba04 55 push ebp
0: kd> kc
00 rdpwsx!TSrvConfCreateResp
01 rdpwsx!TSrvDoConnectResponse
02 rdpwsx!TSrvDoConnect
03 rdpwsx!TSrvStackConnect
04 rdpwsx!WsxIcaStackIoControl
05 termsrv!WsxStackIoControl
06 ICAAPI!_IcaStackIoControl
07 ICAAPI!_IcaStackWaitForIca
08 ICAAPI!IcaStackConnectionAccept
09 termsrv!TransferConnectionToIdleWinStation
0a termsrv!WinStationTransferThread
0b kernel32!BaseThreadStart
第三部分:
第三部分A:
NTSTATUS
TSrvDoConnect(IN PTSRVINFO pTSrvInfo)
{
DWORD dwStatus;
NTSTATUS ntStatus;
TRACE((DEBUG_TSHRSRV_FLOW,
"TShrSRV: TSrvDoConnect entry\n"));
ntStatus = STATUS_TRANSACTION_ABORTED;
if (pTSrvInfo->fDisconnect == FALSE)
{
TSrvReferenceInfo(pTSrvInfo);
// Wait to be told that a connection is being
// requested via the client
TRACE((DEBUG_TSHRSRV_NORMAL,
"TShrSRV: Waiting for connection Ind signal for pTSrvInfo 0x%x\n",
pTSrvInfo));
dwStatus = WaitForSingleObject(pTSrvInfo->hWorkEvent, 60000);
TRACE((DEBUG_TSHRSRV_NORMAL,
"TShrSRV: Connection Ind signal received for pTSrvInfo %p - 0x%x\n",
pTSrvInfo, dwStatus));
// If a client connection request has been recieved, then proceed
// with the acknowledgement process (CreateResponse)
switch (dwStatus)
{
case WAIT_OBJECT_0:
if (pTSrvInfo->fDisconnect == FALSE)
ntStatus = TSrvDoConnectResponse(pTSrvInfo);
else
ntStatus = STATUS_TRANSACTION_ABORTED;
break;
case WAIT_TIMEOUT:
ntStatus = STATUS_IO_TIMEOUT;
break;
}
TSrvDereferenceInfo(pTSrvInfo);
}
TRACE((DEBUG_TSHRSRV_FLOW,
"TShrSRV: TSrvDoConnect exit - 0x%x\n", ntStatus));
return (ntStatus);
}
第三部分B:
TRACE((DEBUG_TSHRSRV_NORMAL,
"TShrSRV: Waiting for connection Ind signal for pTSrvInfo 0x%x\n",
pTSrvInfo));
dwStatus = WaitForSingleObject(pTSrvInfo->hWorkEvent, 60000);
TRACE((DEBUG_TSHRSRV_NORMAL,
"TShrSRV: Connection Ind signal received for pTSrvInfo %p - 0x%x\n",
pTSrvInfo, dwStatus));
WaitForSingleObject函数之前有调试信息,有事件,也就是客户端发来请求之后才返回。
等待时间是60秒,也就是1分钟。
调试记录对应的部分:
03:44:35.421 894EFF7C.E16655C8 TShrSRV: Waiting for connection Ind signal for pTSrvInfo 0xd62ad0
03:44:35.421 8954D5E4.00000000 TermDD: IcaChannelInput, bc=1076 (enter)
03:44:35.421 890EC1FC.E177A920 GCC: mcsCallback entry
03:44:35.421 890EC1FC.E177A920 GCC: Message 0x0, pvParam 0xe4ff40, pvContext 0xd62ad0
03:44:35.421 890EC1FC.E177A920 GCC: gccConnectProviderIndication entry (MCS userDataLength = 0x12f)
03:44:35.421 890EC1FC.E177A920 GCC: gccDecodeUserData entry
03:44:35.421 890EC1FC.E177A920 GCC: gccDecodeUserData (len=0x118) exit - 0x0
03:44:35.421 890EC1FC.E177A920 GCC: Performing GCC_CREATE_INDICATION callout
03:44:35.421 890EC1FC.E177A920 TShrSRV: TSrvGCCCallBack entry
03:44:35.421 890EC1FC.E177A920 TShrSRV: GCCCallback message 0x0 (GCC_CREATE_INDICATION) received
03:44:35.437 890EC1FC.E177A920 TShrSRV: TSrvHandleCreateInd entry
03:44:35.437 890EC1FC.E177A920 TShrSRV: Accepting create indication - Domain 00D62B68
03:44:35.437 890EC1FC.E177A920 TShrSRV: Conductor privilege list is NULL
03:44:35.437 890EC1FC.E177A920 TShrSRV: Conducted mode privilege list is NULL
03:44:35.437 890EC1FC.E177A920 TShrSRV: Non-conducted mode privilege list is NULL
03:44:35.437 890EC1FC.E177A920 TShrSRV: NULL conf name
03:44:35.437 890EC1FC.E177A920 TShrSRV: Attempting to save CreateInd userData
03:44:35.437 890EC1FC.E177A920 TShrSRV: TSrvSaveUserData entry
03:44:35.437 890EC1FC.E177A920 TShrSRV: TSrvCalculateUserDataSize entry
03:44:35.437 890EC1FC.E177A920 TShrSRV: number_of_user_data_members = 0x1
03:44:35.453 890EC1FC.E177A920 TShrSRV: Key_type = 0x2 (GCC_H221_NONSTANDARD_KEY)
03:44:35.453 890EC1FC.E177A920 TShrSRV: key long_string_length = 0x4
03:44:35.453 890EC1FC.E177A920 TShrSRV: data long_string_length = 0x118
03:44:35.453 890EC1FC.E177A920 TShrSRV: TSrvCalculateUserDataSize exit - 0x124
03:44:35.453 890EC1FC.E177A920 TShrSRV: Allocated 0x154 bytes for UserData save space
03:44:35.468 890EC1FC.E177A920 TShrSRV: Saving each UserDataMenber to save space
03:44:35.468 890EC1FC.E177A920 TShrSRV: TSrvSaveUserDataMember entry
03:44:35.468 890EC1FC.E177A920 TShrSRV: TSrvSaveUserDataMember exit
03:44:35.468 890EC1FC.E177A920 TShrSRV: TSrvSaveUserData exit - 0x0
03:44:35.468 890EC1FC.E177A920 TShrSRV: Save userData was successful
03:44:35.468 890EC1FC.E177A920 TShrSRV: TSrvSignalIndication entry
03:44:35.468 890EC1FC.E177A920 TShrSRV: Signaling workEvent 00000200, status 0x0
03:44:35.484 890EC1FC.E177A920 TShrSRV: TSrvSignalIndication exit
03:44:35.484 894EFF7C.E16655C8 TShrSRV: Connection Ind signal received for pTSrvInfo 00D62AD0 - 0x0
890EC1FC.E177A920是其他线程的调试信息,把上面的890EC1FC.E177A920线程输出的信息过滤掉就剩两行了。
03:44:35.421 894EFF7C.E16655C8 TShrSRV: Waiting for connection Ind signal for pTSrvInfo 0xd62ad0
。。。
03:44:35.484 894EFF7C.E16655C8 TShrSRV: Connection Ind signal received for pTSrvInfo 00D62AD0 - 0x0
第四部分:rdpwsx!TSrvStackConnect函数分析的两大部分
NTSTATUS
TSrvStackConnect(IN HANDLE hIca,
IN HANDLE hStack,
OUT PTSRVINFO *ppTSrvInfo)
{
NTSTATUS ntStatus;
TRACE((DEBUG_TSHRSRV_FLOW,
"TShrSRV: TSrvStackConnect entry\n"));
ntStatus = STATUS_UNSUCCESSFUL;
if (TSrvIsReady(TRUE))
{
TS_ASSERT(hStack);
// Allocate a TSrvInfo object which will be used to
// track this connection instance
ntStatus = TSrvAllocInfo(ppTSrvInfo, hIca, hStack);
if (NT_SUCCESS(ntStatus))
{
TS_ASSERT(*ppTSrvInfo);
ntStatus = TSrvDoConnect(*ppTSrvInfo);
}
}
TRACE((DEBUG_TSHRSRV_FLOW,
"TShrSRV: TSrvStackConnect exit - 0x%x\n", ntStatus));
return (ntStatus);
}
17 rdpwsx!TSrvAllocInfo
18 rdpwsx!TSrvStackConnect
19 rdpwsx!WsxIcaStackIoControl
1a termsrv!WsxStackIoControl
1b ICAAPI!_IcaStackIoControl
1c ICAAPI!_IcaStackWaitForIca
02 rdpwsx!TSrvDoConnect
03 rdpwsx!TSrvStackConnect
04 rdpwsx!WsxIcaStackIoControl
05 termsrv!WsxStackIoControl
06 ICAAPI!_IcaStackIoControl
07 ICAAPI!_IcaStackWaitForIca
第五部分:ICAAPI!IcaStackConnectionAccept函数分析之ICAAPI!_IcaStackWaitForIca和之后的IOCTL_ICA_STACK_CONNECTION_QUERY
07 ICAAPI!_IcaStackWaitForIca
08 ICAAPI!IcaStackConnectionAccept
03:44:35.515 894EFF7C.E16655C8 TShrSRV: TSrvDoConnect exit - 0x0
03:44:35.515 894EFF7C.E16655C8 TShrSRV: TSrvStackConnect exit - 0x0
03:44:35.515 894EFF7C.E16655C8 TShrSRV: WsxIcaStackIoControl exit - 0x0
03:44:35.515 894EFF7C.E16655C8 TSAPI: _IcaWaitForIca, success
03:44:35.515 894EFF7C.E16655C8 TERMSRV: Enter WsxIcaIoControl, IoControlCode=19
03:44:35.515 894EFF7C.E16655C8 TShrSRV: WsxIcaStackIoControl entry
03:44:35.515 894EFF7C.E16655C8 TShrSRV: 00D62808:00D62AD0 IoctlDetail: Ioctl 0x38004f (IOCTL_ICA_STACK_CONNECTION_QUERY)
04 rdpwsx!WsxIcaStackIoControl
05 termsrv!WsxStackIoControl
06 ICAAPI!_IcaStackIoControl
ICAAPI!_IcaStackIoControl函数最终会调用到rdpwsx!WsxIcaStackIoControl
ICAAPI!_IcaStackIoControl函数并没有什么输出信息,一般调用到rdpwsx!WsxIcaStackIoControl会有调试信息输出
03:44:35.515 894EFF7C.E16655C8 TERMSRV: Enter WsxIcaIoControl, IoControlCode=19
NTSTATUS
_IcaStackIoControl( IN HANDLE pContext,
IN ULONG IoControlCode,
IN PVOID pInBuffer,
IN ULONG InBufferSize,
OUT PVOID pOutBuffer,
IN ULONG OutBufferSize,
OUT PULONG pBytesReturned )
{
NTSTATUS Status;
PSTACK pStack;
pStack = (PSTACK) pContext;
/*
* Call callback function to handle StackIoControl
*/
if ( pStack->pStackIoControlCallback ) {
/*
* Unlock critical section
*/
pStack->RefCount++;
UNLOCK( &pStack->CritSec );
Status = pStack->pStackIoControlCallback(
pStack->pCallbackContext,
pStack,
IoControlCode,
pInBuffer,
InBufferSize,
pOutBuffer,
OutBufferSize,
pBytesReturned );
/*
* Re-lock critical section
*/
LOCK( &pStack->CritSec );
_DecrementStackRef( pStack );
} else {
Status = _IcaStackIoControlWorker( pStack,
IoControlCode,
pInBuffer,
InBufferSize,
pOutBuffer,
OutBufferSize,
pBytesReturned );
}
return( Status );
}
NTSTATUS
WsxStackIoControl(
IN PVOID pContext,
IN HANDLE pStack,
IN ULONG IoControlCode,
IN PVOID pInBuffer,
IN ULONG InBufferSize,
OUT PVOID pOutBuffer,
IN ULONG OutBufferSize,
OUT PULONG pBytesReturned )
{
PWINSTATION pWinStation = (PWINSTATION)pContext;
NTSTATUS Status;
TRACE((hTrace, TC_ICASRV, TT_API1,
"TERMSRV: Enter WsxIcaIoControl, IoControlCode=%d\n",
(IoControlCode >> 2) & 0xfff));
NTSTATUS
IcaStackConnectionAccept( IN HANDLE hIca,
IN HANDLE pContext,
IN PWINSTATIONNAME pWinStationName,
IN PWINSTATIONCONFIG2 pWinStationConfig,
IN PVOID pEndpoint,
IN ULONG EndpointLength,
IN PICA_STACK_STATE_HEADER pStackState,
IN ULONG BufferLength,
IN PICA_TRACE pTrace )
{
/*
* Wait for ICA Detect string from client
*/
Status = _IcaStackWaitForIca( pContext,
pWinStationConfig,
&fStackModified );
if ( !NT_SUCCESS(Status) ) {
goto badaccept;
}
/*
* Check if the query stack is different than the template stack
*/
if ( fStackModified ) {
TRACESTACK(( pContext, TC_ICAAPI, TT_API1, "TSAPI: IcaStackConnectionAccept, load query stack\n"));
ASSERT(FALSE);
#ifdef notdef
/*
* Unload all stack drivers except the transport
* and connection drivers
* -- we can not pop the td or cd
* -- we can not issue a cancel i/o
*/
_IcaPopStack( pContext );
/*
* Load and open the new query stack
*/
Status = _IcaPushStackAndOpenEndpoint( pContext,
pWinStationName,
pWinStationConfig,
pEndpoint,
EndpointLength );
if ( !NT_SUCCESS(Status) ) {
goto badaccept;
}
#endif
}
}
/*
* At this point the stack is now set up (again). The client is
* now queried for any configuration changes.
*
* - repeat this loop until WD does not change
*/
do {
/*
* Clear query again flag
*/
fQueryAgain = FALSE;
/*
* Query the client for the optional PD's
*/
Status = _IcaStackIoControl( pStack,
IOCTL_ICA_STACK_CONNECTION_QUERY,
NULL,
0,
&IcaStackConfig,
sizeof(IcaStackConfig),
&cbReturned );