libfreerdp-core: encoding of GCC create conference request + unit tests
This commit is contained in:
parent
2a13a7bc16
commit
dd18348436
@ -27,6 +27,8 @@ add_executable(test_freerdp
|
||||
test_per.h
|
||||
test_ber.c
|
||||
test_ber.h
|
||||
test_gcc.c
|
||||
test_gcc.h
|
||||
test_color.c
|
||||
test_color.h
|
||||
test_libgdi.c
|
||||
|
@ -21,6 +21,7 @@
|
||||
|
||||
#include "test_per.h"
|
||||
#include "test_ber.h"
|
||||
#include "test_gcc.h"
|
||||
#include "test_color.h"
|
||||
#include "test_libgdi.h"
|
||||
#include "test_stream.h"
|
||||
@ -60,16 +61,23 @@ void assert_stream(STREAM* s, uint8* data, int length, const char* func, int lin
|
||||
int actual_length;
|
||||
uint8* actual_data;
|
||||
|
||||
actual_data = s->buffer;
|
||||
actual_length = stream_get_length(s);
|
||||
|
||||
if (actual_length != length)
|
||||
{
|
||||
printf("\n %s (%d): length mismatch, actual:%d, expected:%d", func, line, actual_length, length);
|
||||
printf("\n %s (%d): length mismatch, actual:%d, expected:%d\n", func, line, actual_length, length);
|
||||
|
||||
printf("\nActual:\n");
|
||||
freerdp_hexdump(actual_data, actual_length);
|
||||
|
||||
printf("Expected:\n");
|
||||
freerdp_hexdump(data, length);
|
||||
|
||||
CU_FAIL("assert_stream, length mismatch");
|
||||
return;
|
||||
}
|
||||
|
||||
actual_data = s->buffer;
|
||||
for (i = 0; i < length; i++)
|
||||
{
|
||||
if (actual_data[i] != data[i])
|
||||
@ -133,6 +141,10 @@ int main(int argc, char* argv[])
|
||||
{
|
||||
add_ber_suite();
|
||||
}
|
||||
else if (strcmp("gcc", argv[*pindex]) == 0)
|
||||
{
|
||||
add_gcc_suite();
|
||||
}
|
||||
|
||||
*pindex = *pindex + 1;
|
||||
}
|
||||
|
102
cunit/test_gcc.c
Normal file
102
cunit/test_gcc.c
Normal file
@ -0,0 +1,102 @@
|
||||
/**
|
||||
* FreeRDP: A Remote Desktop Protocol Client
|
||||
* T.124 Generic Conference Control (GCC) Unit Tests
|
||||
*
|
||||
* Copyright 2011 Marc-Andre Moreau <marcandre.moreau@gmail.com>
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "gcc.h"
|
||||
|
||||
#include <freerdp/freerdp.h>
|
||||
#include <freerdp/utils/hexdump.h>
|
||||
#include <freerdp/utils/stream.h>
|
||||
|
||||
#include "test_gcc.h"
|
||||
|
||||
int init_gcc_suite(void)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int clean_gcc_suite(void)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int add_gcc_suite(void)
|
||||
{
|
||||
add_test_suite(gcc);
|
||||
|
||||
add_test_function(gcc_write_create_conference_request);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint8 gcc_user_data[284] =
|
||||
"\x01\xc0\xd8\x00\x04\x00\x08\x00\x00\x05\x00\x04\x01\xCA\x03\xAA"
|
||||
"\x09\x04\x00\x00\xCE\x0E\x00\x00\x45\x00\x4c\x00\x54\x00\x4f\x00"
|
||||
"\x4e\x00\x53\x00\x2d\x00\x44\x00\x45\x00\x56\x00\x32\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x04\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x0c\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x01\xCA\x01\x00\x00\x00\x00\x00\x18\x00\x07\x00"
|
||||
"\x01\x00\x36\x00\x39\x00\x37\x00\x31\x00\x32\x00\x2d\x00\x37\x00"
|
||||
"\x38\x00\x33\x00\x2d\x00\x30\x00\x33\x00\x35\x00\x37\x00\x39\x00"
|
||||
"\x37\x00\x34\x00\x2d\x00\x34\x00\x32\x00\x37\x00\x31\x00\x34\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x04\xC0\x0C\x00\x0D\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x02\xC0\x0C\x00\x1B\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x03\xC0\x2C\x00\x03\x00\x00\x00\x72\x64\x70\x64\x72\x00\x00\x00"
|
||||
"\x00\x00\x80\x80\x63\x6c\x69\x70\x72\x64\x72\x00\x00\x00\xA0\xC0"
|
||||
"\x72\x64\x70\x73\x6e\x64\x00\x00\x00\x00\x00\xc0";
|
||||
|
||||
uint8 gcc_create_conference_request_expected[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"
|
||||
"\x05\x00\x04\x01\xCA\x03\xAA\x09\x04\x00\x00\xCE\x0E\x00\x00\x45"
|
||||
"\x00\x4c\x00\x54\x00\x4f\x00\x4e\x00\x53\x00\x2d\x00\x44\x00\x45"
|
||||
"\x00\x56\x00\x32\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x04"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x0c\x00\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01\xCA\x01\x00\x00"
|
||||
"\x00\x00\x00\x18\x00\x07\x00\x01\x00\x36\x00\x39\x00\x37\x00\x31"
|
||||
"\x00\x32\x00\x2d\x00\x37\x00\x38\x00\x33\x00\x2d\x00\x30\x00\x33"
|
||||
"\x00\x35\x00\x37\x00\x39\x00\x37\x00\x34\x00\x2d\x00\x34\x00\x32"
|
||||
"\x00\x37\x00\x31\x00\x34\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x04"
|
||||
"\xC0\x0C\x00\x0D\x00\x00\x00\x00\x00\x00\x00\x02\xC0\x0C\x00\x1B"
|
||||
"\x00\x00\x00\x00\x00\x00\x00\x03\xC0\x2C\x00\x03\x00\x00\x00\x72"
|
||||
"\x64\x70\x64\x72\x00\x00\x00\x00\x00\x80\x80\x63\x6c\x69\x70\x72"
|
||||
"\x64\x72\x00\x00\x00\xA0\xC0\x72\x64\x70\x73\x6e\x64\x00\x00\x00"
|
||||
"\x00\x00\xc0";
|
||||
|
||||
void test_gcc_write_create_conference_request(void)
|
||||
{
|
||||
STREAM* s;
|
||||
STREAM user_data;
|
||||
|
||||
user_data.buffer = gcc_user_data;
|
||||
user_data.capacity = sizeof(gcc_user_data);
|
||||
user_data.ptr = user_data.buffer + user_data.capacity;
|
||||
|
||||
s = stream_new(sizeof(gcc_create_conference_request_expected));
|
||||
|
||||
gcc_write_create_conference_request(s, &user_data);
|
||||
ASSERT_STREAM(s, (uint8*) gcc_create_conference_request_expected, sizeof(gcc_create_conference_request_expected));
|
||||
}
|
26
cunit/test_gcc.h
Normal file
26
cunit/test_gcc.h
Normal file
@ -0,0 +1,26 @@
|
||||
/**
|
||||
* FreeRDP: A Remote Desktop Protocol Client
|
||||
* T.124 Generic Conference Control (GCC) Unit Tests
|
||||
*
|
||||
* Copyright 2011 Marc-Andre Moreau <marcandre.moreau@gmail.com>
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include "test_freerdp.h"
|
||||
|
||||
int init_gcc_suite(void);
|
||||
int clean_gcc_suite(void);
|
||||
int add_gcc_suite(void);
|
||||
|
||||
void test_gcc_write_create_conference_request(void);
|
@ -33,6 +33,12 @@
|
||||
* connectPDU OCTET_STRING
|
||||
* }
|
||||
*
|
||||
* Key ::= CHOICE
|
||||
* {
|
||||
* object OBJECT_IDENTIFIER,
|
||||
* h221NonStandard H221NonStandardIdentifier
|
||||
* }
|
||||
*
|
||||
* ConnectGCCPDU ::= CHOICE
|
||||
* {
|
||||
* conferenceCreateRequest ConferenceCreateRequest,
|
||||
@ -45,10 +51,80 @@
|
||||
* conferenceInviteResponse ConferenceInviteResponse,
|
||||
* ...
|
||||
* }
|
||||
*
|
||||
* ConferenceCreateRequest ::= SEQUENCE
|
||||
* {
|
||||
* conferenceName ConferenceName,
|
||||
* convenerPassword Password OPTIONAL,
|
||||
* password Password OPTIONAL,
|
||||
* lockedConference BOOLEAN,
|
||||
* listedConference BOOLEAN,
|
||||
* conductibleConference BOOLEAN,
|
||||
* terminationMethod TerminationMethod,
|
||||
* conductorPrivileges SET OF Privilege OPTIONAL,
|
||||
* conductedPrivileges SET OF Privilege OPTIONAL,
|
||||
* nonConductedPrivileges SET OF Privilege OPTIONAL,
|
||||
* conferenceDescription TextString OPTIONAL,
|
||||
* callerIdentifier TextString OPTIONAL,
|
||||
* userData UserData OPTIONAL,
|
||||
* ...,
|
||||
* conferencePriority ConferencePriority OPTIONAL,
|
||||
* conferenceMode ConferenceMode OPTIONAL
|
||||
* }
|
||||
*
|
||||
* ConferenceName ::= SEQUENCE
|
||||
* {
|
||||
* numeric SimpleNumericString
|
||||
* text SimpleTextString OPTIONAL,
|
||||
* ...
|
||||
* }
|
||||
*
|
||||
* SimpleNumericString ::= NumericString (SIZE (1..255)) (FROM ("0123456789"))
|
||||
*
|
||||
* UserData ::= SET OF SEQUENCE
|
||||
* {
|
||||
* key Key,
|
||||
* value OCTET_STRING OPTIONAL
|
||||
* }
|
||||
*
|
||||
* H221NonStandardIdentifier ::= OCTET STRING (SIZE (4..255))
|
||||
*
|
||||
*/
|
||||
|
||||
/* http://msdn.microsoft.com/en-us/library/cc240836/ */
|
||||
|
||||
uint8 t124_oid[6] = { 0, 0, 20, 124, 0, 1 };
|
||||
/*
|
||||
* OID = 0.0.20.124.0.1
|
||||
* { itu-t(0) recommendation(0) t(20) t124(124) version(0) 1 }
|
||||
* v.1 of ITU-T Recommendation T.124 (Feb 1998): "Generic Conference Control"
|
||||
*/
|
||||
uint8 t124_02_98_oid[6] = { 0, 0, 20, 124, 0, 1 };
|
||||
|
||||
void
|
||||
gcc_write_create_conference_request(STREAM* s, STREAM* user_data)
|
||||
{
|
||||
/* ConnectData */
|
||||
per_write_choice(s, 0); /* From Key select object (0) of type OBJECT_IDENTIFIER */
|
||||
per_write_object_identifier(s, t124_02_98_oid); /* ITU-T T.124 (02/98) OBJECT_IDENTIFIER */
|
||||
|
||||
/* ConnectData::connectPDU (OCTET_STRING) */
|
||||
per_write_length(s, stream_get_length(user_data) + 14); /* connectPDU length */
|
||||
|
||||
/* ConnectGCCPDU */
|
||||
per_write_choice(s, 0); /* From ConnectGCCPDU select conferenceCreateRequest (0) of type ConferenceCreateRequest */
|
||||
per_write_selection(s, 0x08); /* select optional userData from ConferenceCreateRequest */
|
||||
|
||||
/* ConferenceCreateRequest::conferenceName */
|
||||
per_write_numeric_string(s, "1", 1, 1); /* ConferenceName::numeric */
|
||||
per_write_padding(s, 1); /* padding */
|
||||
|
||||
/* UserData (SET OF SEQUENCE) */
|
||||
per_write_number_of_sets(s, 1); /* one set of UserData */
|
||||
per_write_choice(s, 0xC0); /* UserData::value present + select h221NonStandard (1) */
|
||||
|
||||
/* h221NonStandard */
|
||||
per_write_octet_string(s, "Duca", 4, 4); /* h221NonStandard, client-to-server H.221 key, "Duca" */
|
||||
|
||||
/* userData::value (OCTET_STRING) */
|
||||
per_write_octet_string(s, user_data->buffer, stream_get_length(user_data), 0); /* array of client data blocks */
|
||||
}
|
||||
|
@ -24,6 +24,7 @@
|
||||
|
||||
#include <freerdp/utils/stream.h>
|
||||
|
||||
|
||||
void
|
||||
gcc_write_create_conference_request(STREAM* s, STREAM* user_data);
|
||||
|
||||
#endif /* __GCC_H */
|
||||
|
@ -28,6 +28,33 @@ per_write_length(STREAM* s, int length)
|
||||
stream_write_uint8(s, length);
|
||||
}
|
||||
|
||||
void
|
||||
per_write_choice(STREAM* s, uint8 choice)
|
||||
{
|
||||
stream_write_uint8(s, choice);
|
||||
}
|
||||
|
||||
void
|
||||
per_write_selection(STREAM* s, uint8 selection)
|
||||
{
|
||||
stream_write_uint8(s, selection);
|
||||
}
|
||||
|
||||
void
|
||||
per_write_number_of_sets(STREAM* s, uint8 number)
|
||||
{
|
||||
stream_write_uint8(s, number);
|
||||
}
|
||||
|
||||
void
|
||||
per_write_padding(STREAM* s, int length)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < length; i++)
|
||||
stream_write_uint8(s, 0);
|
||||
}
|
||||
|
||||
void
|
||||
per_write_object_identifier(STREAM* s, uint8 oid[6])
|
||||
{
|
||||
@ -39,3 +66,50 @@ per_write_object_identifier(STREAM* s, uint8 oid[6])
|
||||
stream_write_uint8(s, oid[4]); /* tuple 5 */
|
||||
stream_write_uint8(s, oid[5]); /* tuple 6 */
|
||||
}
|
||||
|
||||
void
|
||||
per_write_string(STREAM* s, uint8* str, int length)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < length; i++)
|
||||
stream_write_uint8(s, str[i]);
|
||||
}
|
||||
|
||||
void
|
||||
per_write_octet_string(STREAM* s, uint8* oct_str, int length, int min)
|
||||
{
|
||||
int i;
|
||||
int mlength;
|
||||
|
||||
mlength = (length - min >= 0) ? length - min : min;
|
||||
|
||||
per_write_length(s, mlength);
|
||||
|
||||
for (i = 0; i < length; i++)
|
||||
stream_write_uint8(s, oct_str[i]);
|
||||
}
|
||||
|
||||
void
|
||||
per_write_numeric_string(STREAM* s, uint8* num_str, int length, int min)
|
||||
{
|
||||
int i;
|
||||
int mlength;
|
||||
uint8 num, c1, c2;
|
||||
|
||||
mlength = (length - min >= 0) ? length - min : min;
|
||||
|
||||
per_write_length(s, mlength);
|
||||
|
||||
for (i = 0; i < length; i += 2)
|
||||
{
|
||||
c1 = num_str[i];
|
||||
c2 = ((i + 1) < length) ? num_str[i + 1] : 0x30;
|
||||
|
||||
c1 = (c1 - 0x30) % 10;
|
||||
c2 = (c2 - 0x30) % 10;
|
||||
num = (c1 << 4) | c2;
|
||||
|
||||
stream_write_uint8(s, num); /* string */
|
||||
}
|
||||
}
|
||||
|
@ -25,6 +25,18 @@
|
||||
void
|
||||
per_write_length(STREAM* s, int length);
|
||||
void
|
||||
per_write_choice(STREAM* s, uint8 choice);
|
||||
void
|
||||
per_write_selection(STREAM* s, uint8 selection);
|
||||
void
|
||||
per_write_number_of_sets(STREAM* s, uint8 number);
|
||||
void
|
||||
per_write_padding(STREAM* s, int length);
|
||||
void
|
||||
per_write_object_identifier(STREAM* s, uint8 oid[6]);
|
||||
void
|
||||
per_write_octet_string(STREAM* s, uint8* oct_str, int length, int min);
|
||||
void
|
||||
per_write_numeric_string(STREAM* s, uint8* num_str, int length, int min);
|
||||
|
||||
#endif /* __PER_H */
|
||||
|
Loading…
Reference in New Issue
Block a user