private StackPacket DecodeMcsSendDataIndicationPDU(byte[] data, DomainMCSPDU domainPdu)
{
// Get Send Data Indication
SendDataIndication indication = (SendDataIndication)domainPdu.GetData();
byte[] userData = indication.userData.ByteArrayValue;
// Get Security Header Type
SecurityHeaderType securityHeaderType = GetSecurityHeaderTypeByContext();
// Peek Security Header
bool isLicenseErrorPdu = false;
if (clientContext.IsWaitingLicenseErrorPdu)
{
isLicenseErrorPdu = IsLicenseErrorSecurityHeaderExist(userData);
}
// Decode PDU
if (isLicenseErrorPdu)
{
// License Error PDU's Basic Security Header content is alway present
int tempIndex = 0;
TS_SECURITY_HEADER header = ParseTsSecurityHeader(userData, ref tempIndex, SecurityHeaderType.Basic);
// Check if PDU is encrypted
bool isEncryptedPdu = IsFlagExist((UInt16)header.flags,
(UInt16)TS_SECURITY_HEADER_flags_Values.SEC_ENCRYPT);
// Correct Server License Error PDU's security header type if needed
if (!isEncryptedPdu || EncryptionLevel.ENCRYPTION_LEVEL_NONE == clientContext.RdpEncryptionLevel)
{
securityHeaderType = SecurityHeaderType.Basic;
}
// Get decrypted user data
byte[] decryptedUserData = DecryptSendDataIndication(userData, securityHeaderType);
// Decode Server License Error PDU
return DecodeLicenseErrorPDU(data, decryptedUserData, securityHeaderType);
}
else
{
// Get decrypted user data
byte[] decryptedUserData = DecryptSendDataIndication(userData, securityHeaderType);
if (clientContext.MessageChannelId == indication.channelId.Value)
{
if (IsInitiateMultitransportRequestSecurityHeaderExist(userData))
{
return DecodeServerInitiateMultitransportRequest(data, decryptedUserData, securityHeaderType);
}
else if (IsHeartbeatSecurityHeaderExist(userData))
{
return DecodeServerHeartbeatPDU(data, decryptedUserData, securityHeaderType);
}
else
{
return DecodeServerAutoDetectRequestPDU(data, decryptedUserData, securityHeaderType);
}
}
// Check channel ID (IO Channel ID/Virual Channel ID)
else if (clientContext.IOChannelId != indication.channelId.Value)
{
// Decode Virtual Channel PDU
return DecodeVirtualChannelPDU(data, decryptedUserData, securityHeaderType);
}
else if (IsStandardRedirectionPdu(userData, securityHeaderType))
{
return DecodeServerRedirectionPDU(data, decryptedUserData, securityHeaderType);
}
else
{
// Decode other Send Data Indication PDUs
return SwitchDecodeMcsSendDataIndicationPDU(data, decryptedUserData, securityHeaderType);
}
}
}