#define TAG CHANNELS_TAG("drdynvc.client")
+static UINT dvcman_close_channel(IWTSVirtualChannelManager* pChannelMgr, UINT32 ChannelId,
+ BOOL bSendClosePDU);
static void dvcman_free(drdynvcPlugin* drdynvc, IWTSVirtualChannelManager* pChannelMgr);
static void dvcman_channel_free(void* channel);
static UINT drdynvc_write_data(drdynvcPlugin* drdynvc, UINT32 ChannelId, const BYTE* data,
- UINT32 dataSize);
+ UINT32 dataSize, BOOL* close);
static UINT drdynvc_send(drdynvcPlugin* drdynvc, wStream* s);
static void dvcman_wtslistener_free(DVCMAN_LISTENER* listener)
static UINT dvcman_write_channel(IWTSVirtualChannel* pChannel, ULONG cbSize, const BYTE* pBuffer,
void* pReserved)
{
+ BOOL close = FALSE;
UINT status;
DVCMAN_CHANNEL* channel = (DVCMAN_CHANNEL*)pChannel;
return CHANNEL_RC_BAD_CHANNEL;
EnterCriticalSection(&(channel->lock));
- status = drdynvc_write_data(channel->dvcman->drdynvc, channel->channel_id, pBuffer, cbSize);
+ status =
+ drdynvc_write_data(channel->dvcman->drdynvc, channel->channel_id, pBuffer, cbSize, &close);
LeaveCriticalSection(&(channel->lock));
+ /* Close delayed, it removes the channel struct */
+ if (close)
+ dvcman_close_channel(channel->dvcman->drdynvc->channel_mgr, channel->channel_id, TRUE);
return status;
}
*
* @return 0 on success, otherwise a Win32 error code
*/
-static UINT dvcman_close_channel(IWTSVirtualChannelManager* pChannelMgr, UINT32 ChannelId,
- BOOL bSendClosePDU)
+UINT dvcman_close_channel(IWTSVirtualChannelManager* pChannelMgr, UINT32 ChannelId,
+ BOOL bSendClosePDU)
{
DVCMAN_CHANNEL* channel;
UINT error = CHANNEL_RC_OK;
* @return 0 on success, otherwise a Win32 error code
*/
static UINT drdynvc_write_data(drdynvcPlugin* drdynvc, UINT32 ChannelId, const BYTE* data,
- UINT32 dataSize)
+ UINT32 dataSize, BOOL* close)
{
wStream* data_out;
size_t pos;
if (dataSize == 0)
{
- dvcman_close_channel(drdynvc->channel_mgr, ChannelId, TRUE);
+ *close = TRUE;
Stream_Release(data_out);
}
else if (dataSize <= CHANNEL_CHUNK_LENGTH - pos)