예제 #1
0
파일: gcc.c 프로젝트: johnsonyes/FreeRDP
void gcc_write_server_core_data(STREAM* s, rdpSettings *settings)
{
	gcc_write_user_data_header(s, SC_CORE, 12);

	stream_write_uint32(s, settings->rdp_version == 4 ? RDP_VERSION_4 : RDP_VERSION_5_PLUS);
	stream_write_uint32(s, settings->requested_protocols); /* clientRequestedProtocols */
}
예제 #2
0
파일: gcc.c 프로젝트: tenchman/FreeRDP-1.0
void gcc_write_client_monitor_data(STREAM* s, rdpSettings *settings)
{
	int i;
	uint16 length;
	uint32 left, top, right, bottom, flags;

	if (settings->num_monitors > 1)
	{
		length = (20 * settings->num_monitors) + 12;
		gcc_write_user_data_header(s, CS_MONITOR, length);

		stream_write_uint32(s, 0); /* flags */
		stream_write_uint32(s, settings->num_monitors); /* monitorCount */

		for (i = 0; i < settings->num_monitors; i++)
		{
			left = settings->monitors[i].x;
			top = settings->monitors[i].y;
			right = settings->monitors[i].x + settings->monitors[i].width - 1;
			bottom = settings->monitors[i].y + settings->monitors[i].height - 1;
			flags = settings->monitors[i].is_primary ? MONITOR_PRIMARY : 0;

			stream_write_uint32(s, left); /* left */
			stream_write_uint32(s, top); /* top */
			stream_write_uint32(s, right); /* right */
			stream_write_uint32(s, bottom); /* bottom */
			stream_write_uint32(s, flags); /* flags */
		}
	}
}
예제 #3
0
파일: gcc.c 프로젝트: AlessioLeo/FreeRDP
void gcc_write_server_core_data(wStream* s, rdpSettings* settings)
{
	gcc_write_user_data_header(s, SC_CORE, 12);

	Stream_Write_UINT32(s, settings->RdpVersion == 4 ? RDP_VERSION_4 : RDP_VERSION_5_PLUS);
	Stream_Write_UINT32(s, settings->RequestedProtocols); /* clientRequestedProtocols */
}
예제 #4
0
파일: gcc.c 프로젝트: vworkspace/FreeRDP
void gcc_write_client_monitor_data(wStream* s, rdpMcs* mcs)
{
	int i;
	UINT16 length;
	UINT32 left, top, right, bottom, flags;
	rdpSettings* settings = mcs->settings;

	if (settings->MonitorCount > 1)
	{
		length = (20 * settings->MonitorCount) + 12;
		gcc_write_user_data_header(s, CS_MONITOR, length);

		Stream_Write_UINT32(s, 0); /* flags */
		Stream_Write_UINT32(s, settings->MonitorCount); /* monitorCount */

		for (i = 0; i < settings->MonitorCount; i++)
		{
			left = settings->MonitorDefArray[i].x;
			top = settings->MonitorDefArray[i].y;
			right = settings->MonitorDefArray[i].x + settings->MonitorDefArray[i].width - 1;
			bottom = settings->MonitorDefArray[i].y + settings->MonitorDefArray[i].height - 1;
			flags = settings->MonitorDefArray[i].is_primary ? MONITOR_PRIMARY : 0;

			Stream_Write_UINT32(s, left); /* left */
			Stream_Write_UINT32(s, top); /* top */
			Stream_Write_UINT32(s, right); /* right */
			Stream_Write_UINT32(s, bottom); /* bottom */
			Stream_Write_UINT32(s, flags); /* flags */
		}
	}
}
예제 #5
0
파일: gcc.c 프로젝트: vworkspace/FreeRDP
void gcc_write_server_multitransport_channel_data(wStream* s, rdpMcs* mcs)
{
	UINT32 flags = 0;

	gcc_write_user_data_header(s, SC_MULTITRANSPORT, 8);

	Stream_Write_UINT32(s, flags); /* flags (4 bytes) */
}
예제 #6
0
파일: gcc.c 프로젝트: AhmadKabakibi/FreeRDP
void gcc_write_server_message_channel_data(wStream* s, rdpMcs* mcs)
{
	UINT16 mcsChannelId = 0;

	gcc_write_user_data_header(s, SC_MCS_MSGCHANNEL, 6);

	Stream_Write_UINT16(s, mcsChannelId); /* mcsChannelId (2 bytes) */
}
예제 #7
0
파일: gcc.c 프로젝트: AhmadKabakibi/FreeRDP
void gcc_write_server_core_data(wStream* s, rdpMcs* mcs)
{
	rdpSettings* settings = mcs->settings;

	gcc_write_user_data_header(s, SC_CORE, 16);

	Stream_Write_UINT32(s, settings->RdpVersion == 4 ? RDP_VERSION_4 : RDP_VERSION_5_PLUS);
	Stream_Write_UINT32(s, settings->RequestedProtocols); /* clientRequestedProtocols */
	Stream_Write_UINT32(s, settings->EarlyCapabilityFlags); /* earlyCapabilityFlags */
}
예제 #8
0
파일: gcc.c 프로젝트: vworkspace/FreeRDP
void gcc_write_client_multitransport_channel_data(wStream* s, rdpMcs* mcs)
{
	rdpSettings* settings = mcs->settings;

	if (settings->MultitransportFlags != 0)
	{
		gcc_write_user_data_header(s, CS_MULTITRANSPORT, 8);

		Stream_Write_UINT32(s, settings->MultitransportFlags); /* flags */
	}
}
예제 #9
0
파일: gcc.c 프로젝트: johnsonyes/FreeRDP
void gcc_write_server_security_data(STREAM* s, rdpSettings *settings)
{
	gcc_write_user_data_header(s, SC_SECURITY, 12);

	stream_write_uint32(s, ENCRYPTION_METHOD_NONE); /* encryptionMethod */
	stream_write_uint32(s, ENCRYPTION_LEVEL_NONE); /* encryptionLevel */
#if 0
	stream_write_uint32(s, 0); /* serverRandomLen */
	stream_write_uint32(s, 0); /* serverCertLen */
#endif
}
예제 #10
0
파일: gcc.c 프로젝트: vworkspace/FreeRDP
void gcc_write_client_message_channel_data(wStream* s, rdpMcs* mcs)
{
	rdpSettings* settings = mcs->settings;

	if (settings->NetworkAutoDetect ||
		settings->SupportHeartbeatPdu ||
		settings->SupportMultitransport)
	{
		gcc_write_user_data_header(s, CS_MCS_MSGCHANNEL, 8);

		Stream_Write_UINT32(s, 0); /* flags */
	}
}
예제 #11
0
파일: gcc.c 프로젝트: AlessioLeo/FreeRDP
void gcc_write_client_cluster_data(wStream* s, rdpSettings* settings)
{
	UINT32 flags;

	gcc_write_user_data_header(s, CS_CLUSTER, 12);

	flags = REDIRECTION_SUPPORTED | (REDIRECTION_VERSION4 << 2);

	if (settings->ConsoleSession || settings->RedirectedSessionId)
		flags |= REDIRECTED_SESSIONID_FIELD_VALID;

	Stream_Write_UINT32(s, flags); /* flags */
	Stream_Write_UINT32(s, settings->RedirectedSessionId); /* redirectedSessionID */
}
예제 #12
0
파일: gcc.c 프로젝트: tenchman/FreeRDP-1.0
void gcc_write_client_cluster_data(STREAM* s, rdpSettings *settings)
{
	uint32 flags;

	gcc_write_user_data_header(s, CS_CLUSTER, 12);

	flags = REDIRECTION_SUPPORTED | (REDIRECTION_VERSION4 << 2);

	if (settings->console_session || settings->redirected_session_id)
		flags |= REDIRECTED_SESSIONID_FIELD_VALID;

	stream_write_uint32(s, flags); /* flags */
	stream_write_uint32(s, settings->redirected_session_id); /* redirectedSessionID */
}
예제 #13
0
파일: gcc.c 프로젝트: tenchman/FreeRDP-1.0
void gcc_write_client_security_data(STREAM* s, rdpSettings *settings)
{
	gcc_write_user_data_header(s, CS_SECURITY, 12);

	if (settings->encryption > 0)
	{
		stream_write_uint32(s, settings->encryption_methods); /* encryptionMethods */
		stream_write_uint32(s, 0); /* extEncryptionMethods */
	}
	else
	{
		/* French locale, disable encryption */
		stream_write_uint32(s, 0); /* encryptionMethods */
		stream_write_uint32(s, settings->encryption_methods); /* extEncryptionMethods */
	}
}
예제 #14
0
파일: gcc.c 프로젝트: AlessioLeo/FreeRDP
void gcc_write_client_security_data(wStream* s, rdpSettings* settings)
{
	gcc_write_user_data_header(s, CS_SECURITY, 12);

	if (settings->DisableEncryption)
	{
		Stream_Write_UINT32(s, settings->EncryptionMethods); /* encryptionMethods */
		Stream_Write_UINT32(s, 0); /* extEncryptionMethods */
	}
	else
	{
		/* French locale, disable encryption */
		Stream_Write_UINT32(s, 0); /* encryptionMethods */
		Stream_Write_UINT32(s, settings->EncryptionMethods); /* extEncryptionMethods */
	}
}
예제 #15
0
파일: gcc.c 프로젝트: AlessioLeo/FreeRDP
void gcc_write_server_network_data(wStream* s, rdpSettings* settings)
{
	int i;

	gcc_write_user_data_header(s, SC_NET, 8 + settings->ChannelCount * 2 + (settings->ChannelCount % 2 == 1 ? 2 : 0));

	Stream_Write_UINT16(s, MCS_GLOBAL_CHANNEL_ID); /* MCSChannelId */
	Stream_Write_UINT16(s, settings->ChannelCount); /* channelCount */

	for (i = 0; i < settings->ChannelCount; i++)
	{
		Stream_Write_UINT16(s, settings->ChannelDefArray[i].ChannelId);
	}

	if (settings->ChannelCount % 2 == 1)
		Stream_Write_UINT16(s, 0);
}
예제 #16
0
파일: gcc.c 프로젝트: johnsonyes/FreeRDP
void gcc_write_server_network_data(STREAM* s, rdpSettings *settings)
{
	int i;

	gcc_write_user_data_header(s, SC_NET, 8 + settings->num_channels * 2 + (settings->num_channels % 2 == 1 ? 2 : 0));

	stream_write_uint16(s, MCS_GLOBAL_CHANNEL_ID); /* MCSChannelId */
	stream_write_uint16(s, settings->num_channels); /* channelCount */

	for (i = 0; i < settings->num_channels; i++)
	{
		stream_write_uint16(s, settings->channels[i].channel_id);
	}

	if (settings->num_channels % 2 == 1)
		stream_write_uint16(s, 0);
}
예제 #17
0
파일: gcc.c 프로젝트: vworkspace/FreeRDP
void gcc_write_server_core_data(wStream* s, rdpMcs* mcs)
{
	UINT32 version;
	UINT32 earlyCapabilityFlags = 0;
	rdpSettings* settings = mcs->settings;

	gcc_write_user_data_header(s, SC_CORE, 16);

	version = settings->RdpVersion == 4 ? RDP_VERSION_4 : RDP_VERSION_5_PLUS;

	if (settings->SupportDynamicTimeZone)
		earlyCapabilityFlags |= RNS_UD_SC_DYNAMIC_DST_SUPPORTED;

	Stream_Write_UINT32(s, version); /* version (4 bytes) */
	Stream_Write_UINT32(s, settings->RequestedProtocols); /* clientRequestedProtocols (4 bytes) */
	Stream_Write_UINT32(s, earlyCapabilityFlags); /* earlyCapabilityFlags (4 bytes) */
}
예제 #18
0
파일: gcc.c 프로젝트: vworkspace/FreeRDP
void gcc_write_server_network_data(wStream* s, rdpMcs* mcs)
{
	UINT32 i;

	gcc_write_user_data_header(s, SC_NET, 8 + mcs->channelCount * 2 + (mcs->channelCount % 2 == 1 ? 2 : 0));

	Stream_Write_UINT16(s, MCS_GLOBAL_CHANNEL_ID); /* MCSChannelId */
	Stream_Write_UINT16(s, mcs->channelCount); /* channelCount */

	for (i = 0; i < mcs->channelCount; i++)
	{
		Stream_Write_UINT16(s, mcs->channels[i].ChannelId);
	}

	if (mcs->channelCount % 2 == 1)
		Stream_Write_UINT16(s, 0);
}
예제 #19
0
파일: gcc.c 프로젝트: AlessioLeo/FreeRDP
void gcc_write_client_network_data(wStream* s, rdpSettings* settings)
{
	int i;
	UINT16 length;

	if (settings->ChannelCount > 0)
	{
		length = settings->ChannelCount * 12 + 8;
		gcc_write_user_data_header(s, CS_NET, length);

		Stream_Write_UINT32(s, settings->ChannelCount); /* channelCount */

		/* channelDefArray */
		for (i = 0; i < settings->ChannelCount; i++)
		{
			/* CHANNEL_DEF */
			Stream_Write(s, settings->ChannelDefArray[i].Name, 8); /* name (8 bytes) */
			Stream_Write_UINT32(s, settings->ChannelDefArray[i].options); /* options (4 bytes) */
		}
	}
}
예제 #20
0
파일: gcc.c 프로젝트: tenchman/FreeRDP-1.0
void gcc_write_client_network_data(STREAM* s, rdpSettings *settings)
{
	int i;
	uint16 length;

	if (settings->num_channels > 0)
	{
		length = settings->num_channels * 12 + 8;
		gcc_write_user_data_header(s, CS_NET, length);

		stream_write_uint32(s, settings->num_channels); /* channelCount */

		/* channelDefArray */
		for (i = 0; i < settings->num_channels; i++)
		{
			/* CHANNEL_DEF */
			stream_write(s, settings->channels[i].name, 8); /* name (8 bytes) */
			stream_write_uint32(s, settings->channels[i].options); /* options (4 bytes) */
		}
	}
}
예제 #21
0
파일: gcc.c 프로젝트: vworkspace/FreeRDP
void gcc_write_client_network_data(wStream* s, rdpMcs* mcs)
{
	UINT32 i;
	UINT16 length;

	if (mcs->channelCount > 0)
	{
		length = mcs->channelCount * 12 + 8;
		gcc_write_user_data_header(s, CS_NET, length);

		Stream_Write_UINT32(s, mcs->channelCount); /* channelCount */

		/* channelDefArray */
		for (i = 0; i < mcs->channelCount; i++)
		{
			/* CHANNEL_DEF */
			Stream_Write(s, mcs->channels[i].Name, 8); /* name (8 bytes) */
			Stream_Write_UINT32(s, mcs->channels[i].options); /* options (4 bytes) */
		}
	}
}
예제 #22
0
파일: gcc.c 프로젝트: blu3bird/FreeRDP
void gcc_write_server_security_data(STREAM* s, rdpSettings* settings)
{
	CryptoMd5 md5;
	uint8* sigData;
	int expLen, keyLen, sigDataLen;
	uint8 encryptedSignature[TSSK_KEY_LENGTH];
	uint8 signature[sizeof(initial_signature)];
	uint32 headerLen, serverRandomLen, serverCertLen, wPublicKeyBlobLen;

	if (!settings->encryption)
	{
		settings->encryption_method = ENCRYPTION_METHOD_NONE;
		settings->encryption_level = ENCRYPTION_LEVEL_NONE;
	}
	else if ((settings->encryption_method & ENCRYPTION_METHOD_FIPS) != 0)
	{
		settings->encryption_method = ENCRYPTION_METHOD_FIPS;
	}
	else if ((settings->encryption_method & ENCRYPTION_METHOD_128BIT) != 0)
	{
		settings->encryption_method = ENCRYPTION_METHOD_128BIT;
	}
	else if ((settings->encryption_method & ENCRYPTION_METHOD_40BIT) != 0)
	{
		settings->encryption_method = ENCRYPTION_METHOD_40BIT;
	}

	if (settings->encryption_method != ENCRYPTION_METHOD_NONE)
		settings->encryption_level = ENCRYPTION_LEVEL_CLIENT_COMPATIBLE;

	headerLen = 12;
	keyLen = 0;
	wPublicKeyBlobLen = 0;
	serverRandomLen = 0;
	serverCertLen = 0;

	if (settings->encryption_method != ENCRYPTION_METHOD_NONE ||
	    settings->encryption_level != ENCRYPTION_LEVEL_NONE)
	{
		serverRandomLen = 32;

		keyLen = settings->server_key->modulus.length;
		expLen = sizeof(settings->server_key->exponent);
		wPublicKeyBlobLen = 4; /* magic (RSA1) */
		wPublicKeyBlobLen += 4; /* keylen */
		wPublicKeyBlobLen += 4; /* bitlen */
		wPublicKeyBlobLen += 4; /* datalen */
		wPublicKeyBlobLen += expLen;
		wPublicKeyBlobLen += keyLen;
		wPublicKeyBlobLen += 8; /* 8 bytes of zero padding */

		serverCertLen = 4; /* dwVersion */
		serverCertLen += 4; /* dwSigAlgId */
		serverCertLen += 4; /* dwKeyAlgId */
		serverCertLen += 2; /* wPublicKeyBlobType */
		serverCertLen += 2; /* wPublicKeyBlobLen */
		serverCertLen += wPublicKeyBlobLen;
		serverCertLen += 2; /* wSignatureBlobType */
		serverCertLen += 2; /* wSignatureBlobLen */
		serverCertLen += sizeof(encryptedSignature); /* SignatureBlob */
		serverCertLen += 8; /* 8 bytes of zero padding */

		headerLen += sizeof(serverRandomLen);
		headerLen += sizeof(serverCertLen);
		headerLen += serverRandomLen;
		headerLen += serverCertLen;
	}

	gcc_write_user_data_header(s, SC_SECURITY, headerLen);

	stream_write_uint32(s, settings->encryption_method); /* encryptionMethod */
	stream_write_uint32(s, settings->encryption_level); /* encryptionLevel */

	if (settings->encryption_method == ENCRYPTION_METHOD_NONE &&
	    settings->encryption_level == ENCRYPTION_LEVEL_NONE)
	{
		return;
	}

	stream_write_uint32(s, serverRandomLen); /* serverRandomLen */
	stream_write_uint32(s, serverCertLen); /* serverCertLen */

	freerdp_blob_alloc(settings->server_random, serverRandomLen);
	crypto_nonce(settings->server_random->data, serverRandomLen);
	stream_write(s, settings->server_random->data, serverRandomLen);

	sigData = stream_get_tail(s);

	stream_write_uint32(s, CERT_CHAIN_VERSION_1); /* dwVersion (4 bytes) */
	stream_write_uint32(s, SIGNATURE_ALG_RSA); /* dwSigAlgId */
	stream_write_uint32(s, KEY_EXCHANGE_ALG_RSA); /* dwKeyAlgId */
	stream_write_uint16(s, BB_RSA_KEY_BLOB); /* wPublicKeyBlobType */

	stream_write_uint16(s, wPublicKeyBlobLen); /* wPublicKeyBlobLen */
	stream_write(s, "RSA1", 4); /* magic */
	stream_write_uint32(s, keyLen + 8); /* keylen */
	stream_write_uint32(s, keyLen * 8); /* bitlen */
	stream_write_uint32(s, keyLen - 1); /* datalen */

	stream_write(s, settings->server_key->exponent, expLen);
	stream_write(s, settings->server_key->modulus.data, keyLen);
	stream_write_zero(s, 8);

	sigDataLen = stream_get_tail(s) - sigData;

	stream_write_uint16(s, BB_RSA_SIGNATURE_BLOB); /* wSignatureBlobType */
	stream_write_uint16(s, keyLen + 8); /* wSignatureBlobLen */

	memcpy(signature, initial_signature, sizeof(initial_signature));

	md5 = crypto_md5_init();
	crypto_md5_update(md5, sigData, sigDataLen);
	crypto_md5_final(md5, signature);

	crypto_rsa_private_encrypt(signature, sizeof(signature), TSSK_KEY_LENGTH,
		tssk_modulus, tssk_privateExponent, encryptedSignature);

	stream_write(s, encryptedSignature, sizeof(encryptedSignature));
	stream_write_zero(s, 8);
}
예제 #23
0
파일: gcc.c 프로젝트: vworkspace/FreeRDP
void gcc_write_client_core_data(wStream* s, rdpMcs* mcs)
{
	UINT32 version;
	WCHAR* clientName = NULL;
	int clientNameLength;
	BYTE connectionType;
	UINT16 highColorDepth;
	UINT16 supportedColorDepths;
	UINT16 earlyCapabilityFlags;
	WCHAR* clientDigProductId = NULL;
	int clientDigProductIdLength;
	rdpSettings* settings = mcs->settings;

	gcc_write_user_data_header(s, CS_CORE, 216);

	version = settings->RdpVersion >= 5 ? RDP_VERSION_5_PLUS : RDP_VERSION_4;

	clientNameLength = ConvertToUnicode(CP_UTF8, 0, settings->ClientHostname, -1, &clientName, 0);
	clientDigProductIdLength = ConvertToUnicode(CP_UTF8, 0, settings->ClientProductId, -1, &clientDigProductId, 0);

	Stream_Write_UINT32(s, version); /* Version */
	Stream_Write_UINT16(s, settings->DesktopWidth); /* DesktopWidth */
	Stream_Write_UINT16(s, settings->DesktopHeight); /* DesktopHeight */
	Stream_Write_UINT16(s, RNS_UD_COLOR_8BPP); /* ColorDepth, ignored because of postBeta2ColorDepth */
	Stream_Write_UINT16(s, RNS_UD_SAS_DEL);	/* SASSequence (Secure Access Sequence) */
	Stream_Write_UINT32(s, settings->KeyboardLayout); /* KeyboardLayout */
	Stream_Write_UINT32(s, settings->ClientBuild); /* ClientBuild */

	/* clientName (32 bytes, null-terminated unicode, truncated to 15 characters) */

	if (clientNameLength >= 16)
	{
		clientNameLength = 16;
		clientName[clientNameLength - 1] = 0;
	}

	Stream_Write(s, clientName, (clientNameLength * 2));
	Stream_Zero(s, 32 - (clientNameLength * 2));
	free(clientName);

	Stream_Write_UINT32(s, settings->KeyboardType); /* KeyboardType */
	Stream_Write_UINT32(s, settings->KeyboardSubType); /* KeyboardSubType */
	Stream_Write_UINT32(s, settings->KeyboardFunctionKey); /* KeyboardFunctionKey */

	Stream_Zero(s, 64); /* imeFileName */

	Stream_Write_UINT16(s, RNS_UD_COLOR_8BPP); /* postBeta2ColorDepth */
	Stream_Write_UINT16(s, 1); /* clientProductID */
	Stream_Write_UINT32(s, 0); /* serialNumber (should be initialized to 0) */

	highColorDepth = MIN(settings->ColorDepth, 24);

	supportedColorDepths =
			RNS_UD_24BPP_SUPPORT |
			RNS_UD_16BPP_SUPPORT |
			RNS_UD_15BPP_SUPPORT;

	earlyCapabilityFlags = RNS_UD_CS_SUPPORT_ERRINFO_PDU;

	if (settings->NetworkAutoDetect)
		settings->ConnectionType = CONNECTION_TYPE_AUTODETECT;

	if (settings->RemoteFxCodec && !settings->NetworkAutoDetect)
		settings->ConnectionType = CONNECTION_TYPE_LAN;

	connectionType = settings->ConnectionType;

	if (connectionType)
		earlyCapabilityFlags |= RNS_UD_CS_VALID_CONNECTION_TYPE;

	if (settings->ColorDepth == 32)
	{
		supportedColorDepths |= RNS_UD_32BPP_SUPPORT;
		earlyCapabilityFlags |= RNS_UD_CS_WANT_32BPP_SESSION;
	}

	if (settings->NetworkAutoDetect)
		earlyCapabilityFlags |= RNS_UD_CS_SUPPORT_NETWORK_AUTODETECT;

	if (settings->SupportHeartbeatPdu)
		earlyCapabilityFlags |= RNS_UD_CS_SUPPORT_HEARTBEAT_PDU;

	if (settings->SupportGraphicsPipeline)
		earlyCapabilityFlags |= RNS_UD_CS_SUPPORT_DYNVC_GFX_PROTOCOL;

	if (settings->SupportDynamicTimeZone)
		earlyCapabilityFlags |= RNS_UD_CS_SUPPORT_DYNAMIC_TIME_ZONE;

	Stream_Write_UINT16(s, highColorDepth); /* highColorDepth */
	Stream_Write_UINT16(s, supportedColorDepths); /* supportedColorDepths */

	Stream_Write_UINT16(s, earlyCapabilityFlags); /* earlyCapabilityFlags */

	/* clientDigProductId (64 bytes, null-terminated unicode, truncated to 31 characters) */
	if (clientDigProductIdLength >= 32)
	{
		clientDigProductIdLength = 32;
		clientDigProductId[clientDigProductIdLength - 1] = 0;
	}
	Stream_Write(s, clientDigProductId, (clientDigProductIdLength * 2) );
	Stream_Zero(s, 64 - (clientDigProductIdLength * 2) );
	free(clientDigProductId);

	Stream_Write_UINT8(s, connectionType); /* connectionType */
	Stream_Write_UINT8(s, 0); /* pad1octet */

	Stream_Write_UINT32(s, settings->SelectedProtocol); /* serverSelectedProtocol */
}
예제 #24
0
파일: gcc.c 프로젝트: Arkantos7/FreeRDP
void gcc_write_client_core_data(STREAM* s, rdpSettings* settings)
{
	UINT32 version;
	WCHAR* clientName;
	int clientNameLength;
	BYTE connectionType;
	UINT16 highColorDepth;
	UINT16 supportedColorDepths;
	UINT16 earlyCapabilityFlags;
	WCHAR* clientDigProductId;
	int clientDigProductIdLength;

	gcc_write_user_data_header(s, CS_CORE, 216);

	version = settings->RdpVersion >= 5 ? RDP_VERSION_5_PLUS : RDP_VERSION_4;

	clientNameLength = ConvertToUnicode(CP_UTF8, 0, settings->ClientHostname, -1, &clientName, 0);
	clientDigProductIdLength = ConvertToUnicode(CP_UTF8, 0, settings->ClientProductId, -1, &clientDigProductId, 0);

	stream_write_UINT32(s, version); /* Version */
	stream_write_UINT16(s, settings->DesktopWidth); /* DesktopWidth */
	stream_write_UINT16(s, settings->DesktopHeight); /* DesktopHeight */
	stream_write_UINT16(s, RNS_UD_COLOR_8BPP); /* ColorDepth, ignored because of postBeta2ColorDepth */
	stream_write_UINT16(s, RNS_UD_SAS_DEL);	/* SASSequence (Secure Access Sequence) */
	stream_write_UINT32(s, settings->KeyboardLayout); /* KeyboardLayout */
	stream_write_UINT32(s, settings->ClientBuild); /* ClientBuild */

	/* clientName (32 bytes, null-terminated unicode, truncated to 15 characters) */

	if (clientNameLength >= 16)
	{
		clientNameLength = 16;
		clientName[clientNameLength-1] = 0;
	}

	stream_write(s, clientName, (clientNameLength * 2));
	stream_write_zero(s, 32 - (clientNameLength * 2));
	free(clientName);

	stream_write_UINT32(s, settings->KeyboardType); /* KeyboardType */
	stream_write_UINT32(s, settings->KeyboardSubType); /* KeyboardSubType */
	stream_write_UINT32(s, settings->KeyboardFunctionKey); /* KeyboardFunctionKey */

	stream_write_zero(s, 64); /* imeFileName */

	stream_write_UINT16(s, RNS_UD_COLOR_8BPP); /* postBeta2ColorDepth */
	stream_write_UINT16(s, 1); /* clientProductID */
	stream_write_UINT32(s, 0); /* serialNumber (should be initialized to 0) */

	highColorDepth = MIN(settings->ColorDepth, 24);

	supportedColorDepths =
			RNS_UD_24BPP_SUPPORT |
			RNS_UD_16BPP_SUPPORT |
			RNS_UD_15BPP_SUPPORT;

	connectionType = settings->ConnectionType;
	earlyCapabilityFlags = RNS_UD_CS_SUPPORT_ERRINFO_PDU;

	if (settings->RemoteFxCodec)
		connectionType = CONNECTION_TYPE_LAN;

	if (connectionType != 0)
		earlyCapabilityFlags |= RNS_UD_CS_VALID_CONNECTION_TYPE;

	if (settings->ColorDepth == 32)
	{
		supportedColorDepths |= RNS_UD_32BPP_SUPPORT;
		earlyCapabilityFlags |= RNS_UD_CS_WANT_32BPP_SESSION;
	}

	stream_write_UINT16(s, highColorDepth); /* highColorDepth */
	stream_write_UINT16(s, supportedColorDepths); /* supportedColorDepths */

	stream_write_UINT16(s, earlyCapabilityFlags); /* earlyCapabilityFlags */

	/* clientDigProductId (64 bytes, null-terminated unicode, truncated to 31 characters) */
	if (clientDigProductIdLength >= 32)
	{
		clientDigProductIdLength = 32;
		clientDigProductId[clientDigProductIdLength-1] = 0;
	}
	stream_write(s, clientDigProductId, (clientDigProductIdLength * 2) );
	stream_write_zero(s, 64 - (clientDigProductIdLength * 2) );
	free(clientDigProductId);

	stream_write_BYTE(s, connectionType); /* connectionType */
	stream_write_BYTE(s, 0); /* pad1octet */

	stream_write_UINT32(s, settings->SelectedProtocol); /* serverSelectedProtocol */
}
예제 #25
0
파일: gcc.c 프로젝트: tenchman/FreeRDP-1.0
void gcc_write_client_core_data(STREAM* s, rdpSettings *settings)
{
	uint32 version;
	uint8* clientName;
	size_t clientNameLength;
	uint8 connectionType;
	uint16 highColorDepth;
	uint16 supportedColorDepths;
	uint16 earlyCapabilityFlags;
	uint8* clientDigProductId;
	size_t clientDigProductIdLength;

	gcc_write_user_data_header(s, CS_CORE, 216);

	version = settings->rdp_version >= 5 ? RDP_VERSION_5_PLUS : RDP_VERSION_4;
	clientName = freerdp_uniconv_out(settings->uniconv, settings->client_hostname, &clientNameLength);
	clientDigProductId = freerdp_uniconv_out(settings->uniconv, settings->client_product_id, &clientDigProductIdLength);

	stream_write_uint32(s, version); /* version */
	stream_write_uint16(s, settings->width); /* desktopWidth */
	stream_write_uint16(s, settings->height); /* desktopHeight */
	stream_write_uint16(s, RNS_UD_COLOR_8BPP); /* colorDepth, ignored because of postBeta2ColorDepth */
	stream_write_uint16(s, RNS_UD_SAS_DEL);	/* SASSequence (Secure Access Sequence) */
	stream_write_uint32(s, settings->kbd_layout); /* keyboardLayout */
	stream_write_uint32(s, settings->client_build); /* clientBuild */

	/* clientName (32 bytes, null-terminated unicode, truncated to 15 characters) */
	if (clientNameLength > 30)
	{
		clientNameLength = 30;
		clientName[clientNameLength] = 0;
		clientName[clientNameLength + 1] = 0;
	}
	stream_write(s, clientName, clientNameLength + 2);
	stream_write_zero(s, 32 - clientNameLength - 2);
	xfree(clientName);

	stream_write_uint32(s, settings->kbd_type); /* keyboardType */
	stream_write_uint32(s, settings->kbd_subtype); /* keyboardSubType */
	stream_write_uint32(s, settings->kbd_fn_keys); /* keyboardFunctionKey */

	stream_write_zero(s, 64); /* imeFileName */

	stream_write_uint16(s, RNS_UD_COLOR_8BPP); /* postBeta2ColorDepth */
	stream_write_uint16(s, 1); /* clientProductID */
	stream_write_uint32(s, 0); /* serialNumber (should be initialized to 0) */

	highColorDepth = MIN(settings->color_depth, 24);

	supportedColorDepths =
			RNS_UD_32BPP_SUPPORT |
			RNS_UD_24BPP_SUPPORT |
			RNS_UD_16BPP_SUPPORT |
			RNS_UD_15BPP_SUPPORT;

	connectionType = 0;
	earlyCapabilityFlags = RNS_UD_CS_SUPPORT_ERRINFO_PDU;

	if (settings->performance_flags == PERF_FLAG_NONE)
	{
		earlyCapabilityFlags |= RNS_UD_CS_VALID_CONNECTION_TYPE;
		connectionType = CONNECTION_TYPE_LAN;
	}

	if (settings->color_depth == 32)
	{
		supportedColorDepths |= RNS_UD_32BPP_SUPPORT;
		earlyCapabilityFlags |= RNS_UD_CS_WANT_32BPP_SESSION;
	}

	stream_write_uint16(s, highColorDepth); /* highColorDepth */
	stream_write_uint16(s, supportedColorDepths); /* supportedColorDepths */

	stream_write_uint16(s, earlyCapabilityFlags); /* earlyCapabilityFlags */

	/* clientDigProductId (64 bytes, null-terminated unicode, truncated to 30 characters) */
	if (clientDigProductIdLength > 62)
	{
		clientDigProductIdLength = 62;
		clientDigProductId[clientDigProductIdLength] = 0;
		clientDigProductId[clientDigProductIdLength + 1] = 0;
	}
	stream_write(s, clientDigProductId, clientDigProductIdLength + 2);
	stream_write_zero(s, 64 - clientDigProductIdLength - 2);
	xfree(clientDigProductId);

	stream_write_uint8(s, connectionType); /* connectionType */
	stream_write_uint8(s, 0); /* pad1octet */

	stream_write_uint32(s, settings->selected_protocol); /* serverSelectedProtocol */
}
예제 #26
0
파일: gcc.c 프로젝트: vworkspace/FreeRDP
void gcc_write_server_security_data(wStream* s, rdpMcs* mcs)
{
	CryptoMd5 md5;
	BYTE* sigData;
	int expLen, keyLen, sigDataLen;
	BYTE encryptedSignature[TSSK_KEY_LENGTH];
	BYTE signature[sizeof(initial_signature)];
	UINT32 headerLen, serverRandomLen, serverCertLen, wPublicKeyBlobLen;
	rdpSettings* settings = mcs->settings;

	/**
	 * Re: settings->EncryptionLevel:
	 * This is configured/set by the server implementation and serves the same
	 * purpose as the "Encryption Level" setting in the RDP-Tcp configuration
	 * dialog of Microsoft's Remote Desktop Session Host Configuration.
	 * Re: settings->EncryptionMethods:
	 * at this point this setting contains the client's supported encryption
	 * methods we've received in gcc_read_client_security_data()
	 */

	if (!settings->UseRdpSecurityLayer)
	{
		/* TLS/NLA is used: disable rdp style encryption */
		settings->EncryptionLevel = ENCRYPTION_LEVEL_NONE;
	}

	/* verify server encryption level value */
	switch (settings->EncryptionLevel)
	{
		case ENCRYPTION_LEVEL_NONE:
			WLog_INFO(TAG, "Active rdp encryption level: NONE");
			break;
		case ENCRYPTION_LEVEL_FIPS:
			WLog_INFO(TAG, "Active rdp encryption level: FIPS Compliant");
			break;
		case ENCRYPTION_LEVEL_HIGH:
			WLog_INFO(TAG, "Active rdp encryption level: HIGH");
			break;
		case ENCRYPTION_LEVEL_LOW:
			WLog_INFO(TAG, "Active rdp encryption level: LOW");
			break;
		case ENCRYPTION_LEVEL_CLIENT_COMPATIBLE:
			WLog_INFO(TAG, "Active rdp encryption level: CLIENT-COMPATIBLE");
			break;
		default:
			WLog_ERR(TAG, "Invalid server encryption level 0x%08X", settings->EncryptionLevel);
			WLog_ERR(TAG, "Switching to encryption level CLIENT-COMPATIBLE");
			settings->EncryptionLevel = ENCRYPTION_LEVEL_CLIENT_COMPATIBLE;
	}

	/* choose rdp encryption method based on server level and client methods */
	switch (settings->EncryptionLevel)
	{
		case ENCRYPTION_LEVEL_NONE:
			/* The only valid method is NONE in this case */
			settings->EncryptionMethods = ENCRYPTION_METHOD_NONE;
			break;
		case ENCRYPTION_LEVEL_FIPS:
			/* The only valid method is FIPS in this case */
			if (!(settings->EncryptionMethods & ENCRYPTION_METHOD_FIPS))
			{
				WLog_WARN(TAG, "client does not support FIPS as required by server configuration");
			}
			settings->EncryptionMethods = ENCRYPTION_METHOD_FIPS;
			break;
		case ENCRYPTION_LEVEL_HIGH:
			/* Maximum key strength supported by the server must be used (128 bit)*/
			if (!(settings->EncryptionMethods & ENCRYPTION_METHOD_128BIT))
			{
				WLog_WARN(TAG, "client does not support 128 bit encryption method as required by server configuration");
			}
			settings->EncryptionMethods = ENCRYPTION_METHOD_128BIT;
			break;
		case ENCRYPTION_LEVEL_LOW:
		case ENCRYPTION_LEVEL_CLIENT_COMPATIBLE:
			/* Maximum key strength supported by the client must be used */
			if (settings->EncryptionMethods & ENCRYPTION_METHOD_128BIT)
				settings->EncryptionMethods = ENCRYPTION_METHOD_128BIT;
			else if (settings->EncryptionMethods & ENCRYPTION_METHOD_56BIT)
				settings->EncryptionMethods = ENCRYPTION_METHOD_56BIT;
			else if (settings->EncryptionMethods & ENCRYPTION_METHOD_40BIT)
				settings->EncryptionMethods = ENCRYPTION_METHOD_40BIT;
			else if (settings->EncryptionMethods & ENCRYPTION_METHOD_FIPS)
				settings->EncryptionMethods = ENCRYPTION_METHOD_FIPS;
			else
			{
				WLog_WARN(TAG, "client has not announced any supported encryption methods");
				settings->EncryptionMethods = ENCRYPTION_METHOD_128BIT;
			}
			break;
		default:
			WLog_ERR(TAG, "internal error: unknown encryption level");
	}

	/* log selected encryption method */
	switch (settings->EncryptionMethods)
	{
		case ENCRYPTION_METHOD_NONE:
			WLog_INFO(TAG, "Selected rdp encryption method: NONE");
			break;
		case ENCRYPTION_METHOD_40BIT:
			WLog_INFO(TAG, "Selected rdp encryption method: 40BIT");
			break;
		case ENCRYPTION_METHOD_56BIT:
			WLog_INFO(TAG, "Selected rdp encryption method: 56BIT");
			break;
		case ENCRYPTION_METHOD_128BIT:
			WLog_INFO(TAG, "Selected rdp encryption method: 128BIT");
			break;
		case ENCRYPTION_METHOD_FIPS:
			WLog_INFO(TAG, "Selected rdp encryption method: FIPS");
			break;
		default:
			WLog_ERR(TAG, "internal error: unknown encryption method");
	}

	headerLen = 12;
	keyLen = 0;
	wPublicKeyBlobLen = 0;
	serverRandomLen = 0;
	serverCertLen = 0;

	if (settings->EncryptionMethods != ENCRYPTION_METHOD_NONE)
	{
		serverRandomLen = 32;

		keyLen = settings->RdpServerRsaKey->ModulusLength;
		expLen = sizeof(settings->RdpServerRsaKey->exponent);
		wPublicKeyBlobLen = 4; /* magic (RSA1) */
		wPublicKeyBlobLen += 4; /* keylen */
		wPublicKeyBlobLen += 4; /* bitlen */
		wPublicKeyBlobLen += 4; /* datalen */
		wPublicKeyBlobLen += expLen;
		wPublicKeyBlobLen += keyLen;
		wPublicKeyBlobLen += 8; /* 8 bytes of zero padding */

		serverCertLen = 4; /* dwVersion */
		serverCertLen += 4; /* dwSigAlgId */
		serverCertLen += 4; /* dwKeyAlgId */
		serverCertLen += 2; /* wPublicKeyBlobType */
		serverCertLen += 2; /* wPublicKeyBlobLen */
		serverCertLen += wPublicKeyBlobLen;
		serverCertLen += 2; /* wSignatureBlobType */
		serverCertLen += 2; /* wSignatureBlobLen */
		serverCertLen += sizeof(encryptedSignature); /* SignatureBlob */
		serverCertLen += 8; /* 8 bytes of zero padding */

		headerLen += sizeof(serverRandomLen);
		headerLen += sizeof(serverCertLen);
		headerLen += serverRandomLen;
		headerLen += serverCertLen;
	}

	gcc_write_user_data_header(s, SC_SECURITY, headerLen);

	Stream_Write_UINT32(s, settings->EncryptionMethods); /* encryptionMethod */
	Stream_Write_UINT32(s, settings->EncryptionLevel); /* encryptionLevel */

	if (settings->EncryptionMethods == ENCRYPTION_METHOD_NONE)
	{
		return;
	}

	Stream_Write_UINT32(s, serverRandomLen); /* serverRandomLen */
	Stream_Write_UINT32(s, serverCertLen); /* serverCertLen */

	settings->ServerRandomLength = serverRandomLen;
	settings->ServerRandom = (BYTE*) malloc(serverRandomLen);
	crypto_nonce(settings->ServerRandom, serverRandomLen);
	Stream_Write(s, settings->ServerRandom, serverRandomLen);

	sigData = Stream_Pointer(s);

	Stream_Write_UINT32(s, CERT_CHAIN_VERSION_1); /* dwVersion (4 bytes) */
	Stream_Write_UINT32(s, SIGNATURE_ALG_RSA); /* dwSigAlgId */
	Stream_Write_UINT32(s, KEY_EXCHANGE_ALG_RSA); /* dwKeyAlgId */
	Stream_Write_UINT16(s, BB_RSA_KEY_BLOB); /* wPublicKeyBlobType */

	Stream_Write_UINT16(s, wPublicKeyBlobLen); /* wPublicKeyBlobLen */
	Stream_Write(s, "RSA1", 4); /* magic */
	Stream_Write_UINT32(s, keyLen + 8); /* keylen */
	Stream_Write_UINT32(s, keyLen * 8); /* bitlen */
	Stream_Write_UINT32(s, keyLen - 1); /* datalen */

	Stream_Write(s, settings->RdpServerRsaKey->exponent, expLen);
	Stream_Write(s, settings->RdpServerRsaKey->Modulus, keyLen);
	Stream_Zero(s, 8);

	sigDataLen = Stream_Pointer(s) - sigData;

	Stream_Write_UINT16(s, BB_RSA_SIGNATURE_BLOB); /* wSignatureBlobType */
	Stream_Write_UINT16(s, sizeof(encryptedSignature) + 8); /* wSignatureBlobLen */

	memcpy(signature, initial_signature, sizeof(initial_signature));

	md5 = crypto_md5_init();
	if (!md5)
	{
		WLog_ERR(TAG,  "unable to allocate a md5");
		return;
	}

	crypto_md5_update(md5, sigData, sigDataLen);
	crypto_md5_final(md5, signature);

	crypto_rsa_private_encrypt(signature, sizeof(signature), TSSK_KEY_LENGTH,
		tssk_modulus, tssk_privateExponent, encryptedSignature);

	Stream_Write(s, encryptedSignature, sizeof(encryptedSignature));
	Stream_Zero(s, 8);
}
예제 #27
0
파일: gcc.c 프로젝트: AhmadKabakibi/FreeRDP
void gcc_write_server_security_data(wStream* s, rdpMcs* mcs)
{
	CryptoMd5 md5;
	BYTE* sigData;
	int expLen, keyLen, sigDataLen;
	BYTE encryptedSignature[TSSK_KEY_LENGTH];
	BYTE signature[sizeof(initial_signature)];
	UINT32 headerLen, serverRandomLen, serverCertLen, wPublicKeyBlobLen;
	rdpSettings* settings = mcs->settings;

	if (!settings->DisableEncryption)
	{
		settings->EncryptionMethods = ENCRYPTION_METHOD_NONE;
		settings->EncryptionLevel = ENCRYPTION_LEVEL_NONE;
	}
	else if ((settings->EncryptionMethods & ENCRYPTION_METHOD_FIPS) != 0)
	{
		settings->EncryptionMethods = ENCRYPTION_METHOD_FIPS;
	}
	else if ((settings->EncryptionMethods & ENCRYPTION_METHOD_128BIT) != 0)
	{
		settings->EncryptionMethods = ENCRYPTION_METHOD_128BIT;
	}
	else if ((settings->EncryptionMethods & ENCRYPTION_METHOD_40BIT) != 0)
	{
		settings->EncryptionMethods = ENCRYPTION_METHOD_40BIT;
	}

	if (settings->EncryptionMethods != ENCRYPTION_METHOD_NONE)
		settings->EncryptionLevel = ENCRYPTION_LEVEL_CLIENT_COMPATIBLE;

	headerLen = 12;
	keyLen = 0;
	wPublicKeyBlobLen = 0;
	serverRandomLen = 0;
	serverCertLen = 0;

	if (settings->EncryptionMethods != ENCRYPTION_METHOD_NONE ||
	    settings->EncryptionLevel != ENCRYPTION_LEVEL_NONE)
	{
		serverRandomLen = 32;

		keyLen = settings->RdpServerRsaKey->ModulusLength;
		expLen = sizeof(settings->RdpServerRsaKey->exponent);
		wPublicKeyBlobLen = 4; /* magic (RSA1) */
		wPublicKeyBlobLen += 4; /* keylen */
		wPublicKeyBlobLen += 4; /* bitlen */
		wPublicKeyBlobLen += 4; /* datalen */
		wPublicKeyBlobLen += expLen;
		wPublicKeyBlobLen += keyLen;
		wPublicKeyBlobLen += 8; /* 8 bytes of zero padding */

		serverCertLen = 4; /* dwVersion */
		serverCertLen += 4; /* dwSigAlgId */
		serverCertLen += 4; /* dwKeyAlgId */
		serverCertLen += 2; /* wPublicKeyBlobType */
		serverCertLen += 2; /* wPublicKeyBlobLen */
		serverCertLen += wPublicKeyBlobLen;
		serverCertLen += 2; /* wSignatureBlobType */
		serverCertLen += 2; /* wSignatureBlobLen */
		serverCertLen += sizeof(encryptedSignature); /* SignatureBlob */
		serverCertLen += 8; /* 8 bytes of zero padding */

		headerLen += sizeof(serverRandomLen);
		headerLen += sizeof(serverCertLen);
		headerLen += serverRandomLen;
		headerLen += serverCertLen;
	}

	gcc_write_user_data_header(s, SC_SECURITY, headerLen);

	Stream_Write_UINT32(s, settings->EncryptionMethods); /* encryptionMethod */
	Stream_Write_UINT32(s, settings->EncryptionLevel); /* encryptionLevel */

	if (settings->EncryptionMethods == ENCRYPTION_METHOD_NONE &&
	    settings->EncryptionLevel == ENCRYPTION_LEVEL_NONE)
	{
		return;
	}

	Stream_Write_UINT32(s, serverRandomLen); /* serverRandomLen */
	Stream_Write_UINT32(s, serverCertLen); /* serverCertLen */

	settings->ServerRandomLength = serverRandomLen;
	settings->ServerRandom = (BYTE*) malloc(serverRandomLen);
	crypto_nonce(settings->ServerRandom, serverRandomLen);
	Stream_Write(s, settings->ServerRandom, serverRandomLen);

	sigData = Stream_Pointer(s);

	Stream_Write_UINT32(s, CERT_CHAIN_VERSION_1); /* dwVersion (4 bytes) */
	Stream_Write_UINT32(s, SIGNATURE_ALG_RSA); /* dwSigAlgId */
	Stream_Write_UINT32(s, KEY_EXCHANGE_ALG_RSA); /* dwKeyAlgId */
	Stream_Write_UINT16(s, BB_RSA_KEY_BLOB); /* wPublicKeyBlobType */

	Stream_Write_UINT16(s, wPublicKeyBlobLen); /* wPublicKeyBlobLen */
	Stream_Write(s, "RSA1", 4); /* magic */
	Stream_Write_UINT32(s, keyLen + 8); /* keylen */
	Stream_Write_UINT32(s, keyLen * 8); /* bitlen */
	Stream_Write_UINT32(s, keyLen - 1); /* datalen */

	Stream_Write(s, settings->RdpServerRsaKey->exponent, expLen);
	Stream_Write(s, settings->RdpServerRsaKey->Modulus, keyLen);
	Stream_Zero(s, 8);

	sigDataLen = Stream_Pointer(s) - sigData;

	Stream_Write_UINT16(s, BB_RSA_SIGNATURE_BLOB); /* wSignatureBlobType */
	Stream_Write_UINT16(s, keyLen + 8); /* wSignatureBlobLen */

	memcpy(signature, initial_signature, sizeof(initial_signature));

	md5 = crypto_md5_init();
	crypto_md5_update(md5, sigData, sigDataLen);
	crypto_md5_final(md5, signature);

	crypto_rsa_private_encrypt(signature, sizeof(signature), TSSK_KEY_LENGTH,
		tssk_modulus, tssk_privateExponent, encryptedSignature);

	Stream_Write(s, encryptedSignature, sizeof(encryptedSignature));
	Stream_Zero(s, 8);
}