diff --git a/cunit/test_mcs.c b/cunit/test_mcs.c index de456b38e..eaf866781 100644 --- a/cunit/test_mcs.c +++ b/cunit/test_mcs.c @@ -44,6 +44,16 @@ int add_mcs_suite(void) return 0; } +/* +7F 65 82 01 94 04 01 01 04 01 01 01 01 FF 30 19 +02 01 22 02 01 02 02 01 00 02 01 01 02 01 00 02 +01 01 02 02 FF FF 02 01 02 30 19 02 01 01 02 01 +01 02 01 01 02 01 01 02 01 00 02 01 01 02 02 04 +20 02 01 02 30 1C 02 02 FF FF 02 02 FC 17 02 02 +FF FF 02 01 01 02 01 00 02 01 01 02 02 FF FF 02 +01 02 04 82 01 33 +*/ + uint8 gcc_CCrq[307] = "\x00\x05\x00\x14\x7C\x00\x01\x81\x2A\x00\x08\x00\x10\x00\x01\xC0" "\x00\x44\x75\x63\x61\x81\x1c\x01\xc0\xd8\x00\x04\x00\x08\x00\x00" diff --git a/libfreerdp-core/ber.c b/libfreerdp-core/ber.c index 4ec1ab756..b804fd0be 100644 --- a/libfreerdp-core/ber.c +++ b/libfreerdp-core/ber.c @@ -42,7 +42,6 @@ void ber_write_length(STREAM* s, int length) * Write BER Universal tag. * @param s stream * @param tag BER universally-defined tag - * @param length length */ void ber_write_universal_tag(STREAM* s, uint8 tag) @@ -72,6 +71,18 @@ void ber_write_application_tag(STREAM* s, uint8 tag, int length) } } +/** + * Write BER SEQUENCE OF tag. + * @param s stream + * @param length length + */ + +void ber_write_sequence_of_tag(STREAM* s, int length) +{ + stream_write_uint8(s, (BER_CLASS_UNIV | BER_CONSTRUCT) | (BER_TAG_MASK & BER_TAG_SEQUENCE_OF)); + ber_write_length(s, length); +} + /** * Write a BER OCTET_STRING * @param s stream @@ -82,6 +93,7 @@ void ber_write_application_tag(STREAM* s, uint8 tag, int length) void ber_write_octet_string(STREAM* s, uint8* oct_str, int length) { ber_write_universal_tag(s, BER_TAG_OCTET_STRING); + ber_write_length(s, length); stream_write(s, oct_str, length); } @@ -94,6 +106,7 @@ void ber_write_octet_string(STREAM* s, uint8* oct_str, int length) void ber_write_boolean(STREAM* s, boolean value) { ber_write_universal_tag(s, BER_TAG_BOOLEAN); + ber_write_length(s, 1); stream_write_uint8(s, (value == True) ? 0xFF : 0); } @@ -109,14 +122,17 @@ void ber_write_integer(STREAM* s, uint32 value) if (value <= 0xFF) { + ber_write_length(s, 1); stream_write_uint8(s, value); } else if (value <= 0xFFFF) { + ber_write_length(s, 2); stream_write_uint16_be(s, value); } else if (value <= 0xFFFFFFFF) { + ber_write_length(s, 4); stream_write_uint32_be(s, value); } } diff --git a/libfreerdp-core/ber.h b/libfreerdp-core/ber.h index 590bfea74..79c72236f 100644 --- a/libfreerdp-core/ber.h +++ b/libfreerdp-core/ber.h @@ -42,10 +42,12 @@ #define BER_TAG_BOOLEAN 0x01 #define BER_TAG_INTEGER 0x02 #define BER_TAG_OCTET_STRING 0x04 +#define BER_TAG_SEQUENCE_OF 0x10 void ber_write_length(STREAM* s, int length); void ber_write_universal_tag(STREAM* s, uint8 tag); void ber_write_application_tag(STREAM* s, uint8 tag, int length); +void ber_write_sequence_of_tag(STREAM* s, int length); void ber_write_octet_string(STREAM* s, uint8* oct_str, int length); void ber_write_boolean(STREAM* s, boolean value); void ber_write_integer(STREAM* s, uint32 value); diff --git a/libfreerdp-core/mcs.c b/libfreerdp-core/mcs.c index d8c330d14..8825a0223 100644 --- a/libfreerdp-core/mcs.c +++ b/libfreerdp-core/mcs.c @@ -71,6 +71,11 @@ static void mcs_init_domain_parameters(DOMAIN_PARAMETERS* domainParameters, domainParameters->maxUserIds = maxUserIds; domainParameters->maxTokenIds = maxTokenIds; domainParameters->maxMCSPDUsize = maxMCSPDUsize; + + domainParameters->numPriorities = 1; + domainParameters->minThroughput = 0; + domainParameters->maxHeight = 1; + domainParameters->protocolVersion = 2; } /** @@ -81,6 +86,12 @@ static void mcs_init_domain_parameters(DOMAIN_PARAMETERS* domainParameters, static void mcs_write_domain_parameters(STREAM* s, DOMAIN_PARAMETERS* domainParameters) { + int length; + uint8 *bm, *em; + + stream_get_mark(s, bm); + stream_seek(s, 2); + ber_write_integer(s, domainParameters->maxChannelIds); ber_write_integer(s, domainParameters->maxUserIds); ber_write_integer(s, domainParameters->maxTokenIds); @@ -89,6 +100,13 @@ static void mcs_write_domain_parameters(STREAM* s, DOMAIN_PARAMETERS* domainPara ber_write_integer(s, domainParameters->maxHeight); ber_write_integer(s, domainParameters->maxMCSPDUsize); ber_write_integer(s, domainParameters->protocolVersion); + + stream_get_mark(s, em); + length = (em - bm) - 2; + stream_set_mark(s, bm); + + ber_write_sequence_of_tag(s, length); + stream_set_mark(s, em); } /** @@ -103,7 +121,7 @@ void mcs_write_connect_initial(STREAM* s, rdpMcs* mcs, STREAM* user_data) int length; int gcc_CCrq_length = stream_get_length(user_data); - length = gcc_CCrq_length + 3 * 34 + 13; + length = gcc_CCrq_length + 97; /* Connect-Initial (APPLICATION 101, IMPLICIT SEQUENCE) */ ber_write_application_tag(s, MCS_TYPE_CONNECT_INITIAL, length);