blob: 6529d4de91d058db37c540870cf6379c1e3d8ad0 [file] [log] [blame]
Ivan Kluchnikov487a1412011-12-21 13:17:53 +03001/* RLCMACTest.cpp
2 *
3 * Copyright (C) 2011 Ivan Klyuchnikov
4 *
5 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU General Public License
7 * as published by the Free Software Foundation; either version 2
8 * of the License, or (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18 */
19
20
21
22//#include <BitVector.h>
23#include <iostream>
24#include <cstdlib>
Ivan Kluchnikov835f91e2012-04-30 18:00:36 +040025#include <cstring>
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +010026#include <assert.h>
Ivan Kluchnikov487a1412011-12-21 13:17:53 +030027#include "gsm_rlcmac.h"
Max7426c5f2019-02-18 20:42:42 +010028#include "gprs_rlcmac.h"
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +010029#include "decoding.h"
Max7426c5f2019-02-18 20:42:42 +010030
Andreas Eversberg138f4e62013-01-14 12:31:11 +010031extern "C" {
32extern const struct log_info gprs_log_info;
33#include "pcu_vty.h"
34#include <osmocom/vty/telnet_interface.h>
35#include <osmocom/vty/logging.h>
Aravind Sirsikar9f5f0082016-08-30 13:20:23 +053036#include <osmocom/core/utils.h>
Maxd3a0d912019-03-05 16:15:01 +010037#include <osmocom/core/msgb.h>
Andreas Eversberg138f4e62013-01-14 12:31:11 +010038#include <osmocom/core/application.h>
Vadim Yanitskiy39a65052020-01-25 01:24:59 +070039
40#include "csn1.h"
Andreas Eversberg138f4e62013-01-14 12:31:11 +010041}
Ivan Kluchnikov487a1412011-12-21 13:17:53 +030042using namespace std;
43
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +010044void *tall_pcu_ctx;
45
Ivan Kluchnikov487a1412011-12-21 13:17:53 +030046void printSizeofRLCMAC()
47{
Pau Espin Pedrol54681c32020-01-23 21:59:23 +010048 printf("*** %s ***\n", __func__);
Ivan Kluchnikov487a1412011-12-21 13:17:53 +030049 cout << "sizeof RlcMacUplink_t " << sizeof(RlcMacUplink_t) << endl;
50 cout << "sizeof Packet_Cell_Change_Failure_t " << sizeof(Packet_Cell_Change_Failure_t) << endl;
51 cout << "sizeof Packet_Control_Acknowledgement_t " << sizeof(Packet_Control_Acknowledgement_t) << endl;
52 cout << "sizeof Packet_Downlink_Ack_Nack_t " << sizeof(Packet_Downlink_Ack_Nack_t) << endl;
53 cout << "sizeof EGPRS_PD_AckNack_t " << sizeof(EGPRS_PD_AckNack_t) << endl;
54 cout << "sizeof Packet_Uplink_Dummy_Control_Block_t " << sizeof(Packet_Uplink_Dummy_Control_Block_t) << endl;
55 cout << "sizeof Packet_Measurement_Report_t " << sizeof(Packet_Measurement_Report_t) << endl;
56 cout << "sizeof Packet_Resource_Request_t " << sizeof(Packet_Resource_Request_t) << endl;
57 cout << "sizeof Packet_Mobile_TBF_Status_t " << sizeof(Packet_Mobile_TBF_Status_t) << endl;
58 cout << "sizeof Packet_PSI_Status_t " << sizeof(Packet_PSI_Status_t) << endl;
59 cout << "sizeof Packet_Enh_Measurement_Report_t " << sizeof(Packet_Enh_Measurement_Report_t) << endl;
60 cout << "sizeof Packet_Cell_Change_Notification_t " << sizeof(Packet_Cell_Change_Notification_t) << endl;
61 cout << "sizeof Packet_SI_Status_t " << sizeof(Packet_SI_Status_t) << endl;
62 cout << "sizeof Additional_MS_Rad_Access_Cap_t " << sizeof(Additional_MS_Rad_Access_Cap_t) << endl;
63 cout << "sizeof Packet_Pause_t " << sizeof(Packet_Pause_t) << endl;
64
65 cout << "sizeof RlcMacDownlink_t " << sizeof(RlcMacDownlink_t) << endl;
66 cout << "sizeof Packet_Access_Reject_t " << sizeof(Packet_Access_Reject_t) << endl;
Holger Hans Peter Freythere13298d2013-07-28 16:45:54 +020067 cout << "sizeof Packet_Cell_Change_Order_t " << sizeof(Packet_Cell_Change_Order_t) << endl;
68 cout << "sizeof Packet_Downlink_Assignment_t " << sizeof(Packet_Downlink_Assignment_t) << endl;
Ivan Kluchnikov487a1412011-12-21 13:17:53 +030069 cout << "sizeof Packet_Neighbour_Cell_Data_t " << sizeof(Packet_Neighbour_Cell_Data_t) << endl;
70 cout << "sizeof Packet_Serving_Cell_Data_t " << sizeof(Packet_Serving_Cell_Data_t) << endl;
71 cout << "sizeof Packet_Paging_Request_t " << sizeof(Packet_Paging_Request_t) << endl;
72 cout << "sizeof Packet_PDCH_Release_t " << sizeof(Packet_PDCH_Release_t) << endl;
73 cout << "sizeof Packet_Polling_Request_t " << sizeof(Packet_Polling_Request_t) << endl;
74 cout << "sizeof Packet_Power_Control_Timing_Advance_t " << sizeof(Packet_Power_Control_Timing_Advance_t) << endl;
75 cout << "sizeof Packet_PRACH_Parameters_t " << sizeof(Packet_PRACH_Parameters_t) << endl;
76 cout << "sizeof Packet_Queueing_Notification_t " << sizeof(Packet_Queueing_Notification_t) << endl;
77 cout << "sizeof Packet_Timeslot_Reconfigure_t " << sizeof(Packet_Timeslot_Reconfigure_t) << endl;
78 cout << "sizeof Packet_TBF_Release_t " << sizeof(Packet_TBF_Release_t) << endl;
79 cout << "sizeof Packet_Uplink_Ack_Nack_t " << sizeof(Packet_Uplink_Ack_Nack_t) << endl;
80 cout << "sizeof Packet_Uplink_Assignment_t " << sizeof(Packet_Uplink_Assignment_t) << endl;
81 cout << "sizeof Packet_Cell_Change_Continue_t " << sizeof(Packet_Cell_Change_Continue_t) << endl;
82 cout << "sizeof Packet_Handover_Command_t " << sizeof(Packet_Handover_Command_t) << endl;
83 cout << "sizeof Packet_PhysicalInformation_t " << sizeof(Packet_PhysicalInformation_t) << endl;
84 cout << "sizeof Packet_Downlink_Dummy_Control_Block_t " << sizeof(Packet_Downlink_Dummy_Control_Block_t) << endl;
85 cout << "sizeof PSI1_t " << sizeof(PSI1_t) << endl;
86 cout << "sizeof PSI2_t " << sizeof(PSI2_t) << endl;
87 cout << "sizeof PSI3_t " << sizeof(PSI3_t) << endl;
88 cout << "sizeof PSI3_BIS_t " << sizeof(PSI3_BIS_t) << endl;
89 cout << "sizeof PSI4_t " << sizeof(PSI4_t) << endl;
90 cout << "sizeof PSI13_t " << sizeof(PSI13_t) << endl;
91 cout << "sizeof PSI5_t " << sizeof(PSI5_t) << endl;
92}
93
Alexander Couzensccde5c92017-02-04 03:10:08 +010094void testRlcMacDownlink(void *test_ctx)
Ivan Kluchnikov487a1412011-12-21 13:17:53 +030095{
Pau Espin Pedrol54681c32020-01-23 21:59:23 +010096 printf("*** %s ***\n", __func__);
Pau Espin Pedrol5e300ce2020-02-03 17:18:03 +010097
98 int rc;
Alexander Couzensccde5c92017-02-04 03:10:08 +010099 struct bitvec *resultVector = bitvec_alloc(23, test_ctx);
Max7426c5f2019-02-18 20:42:42 +0100100 bitvec_unhex(resultVector, DUMMY_VEC);
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300101
102 std::string testData[] = {
103 "4e082500e3f1a81d080820800b2b2b2b2b2b2b2b2b2b2b", // Packet Downlink Assignment
Saurabh Sharan656eed52016-03-10 14:15:29 +0530104 "48282407a6a07422720100032b2b2b2b2b2b2b2b2b2b2b", // Packet Uplink Assignment
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300105 "47240c00400000000000000079eb2ac9402b2b2b2b2b2b", // Packet Uplink Ack Nack
Saurabh Sharanbacb65b2016-03-10 17:24:49 +0530106 "47283c367513ba333004242b2b2b2b2b2b2b2b2b2b2b2b", // Packet Uplink Assignment
107 "400820001a3904df0680efb3300b2b2b2b2b2b2b2b2b2b", // Packet Downlink Assignment (EGPRS)
Saurabh Sharan2b09c392016-03-16 19:17:32 +0530108 "40284f0000001009810c826f4406809dcecb2b2b2b2b2b", // Packet Uplink Assignment (EGPRS)
Pau Espin Pedrol5cb002f2020-01-23 23:45:17 +0100109 "4024030f2f0000000087b0042b2b2b2b2b2b2b2b2b2b2b", // Packet Uplink Ack Nack (EGPRS)
Vadim Yanitskiy9b2f7c42020-02-11 21:45:19 +0700110 "4913e00850884013a8048b2b2b2b2b2b2b2b2b2b2b2b2b", // Polling Request (malformed)
Pau Espin Pedrol5cb002f2020-01-23 23:45:17 +0100111 "412430007fffffffffffffffefd19c7ba12b2b2b2b2b2b", // Packet Uplink Ack Nack?
112 "41942b2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b", // System Info 13?
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300113 };
114
115 int testDataSize = sizeof(testData)/sizeof(testData[0]);
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300116
117 cout << " DOWNLINK " << endl;
118 for (int i = 0; i < testDataSize; i++)
119 {
Pau Espin Pedrol87bfbe42020-01-23 23:51:34 +0100120 cout << "vector1 = " << testData[i] << endl;
Alexander Couzensccde5c92017-02-04 03:10:08 +0100121 bitvec *vector = bitvec_alloc(23, test_ctx);
Ivan Kluchnikov835f91e2012-04-30 18:00:36 +0400122 bitvec_unhex(vector, testData[i].c_str());
Pau Espin Pedrol87bfbe42020-01-23 23:51:34 +0100123
Pau Espin Pedrol99c437b2020-01-24 12:34:50 +0100124 RlcMacDownlink_t data;
125 memset(&data, 0, sizeof(data));
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300126 cout << "=========Start DECODE===========" << endl;
Pau Espin Pedrol5e300ce2020-02-03 17:18:03 +0100127 rc = decode_gsm_rlcmac_downlink(vector, &data);
128 cout << "+++++++++Finish DECODE ("<< rc <<")++++++++++" << endl;
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300129 cout << "=========Start ENCODE=============" << endl;
Pau Espin Pedrol5e300ce2020-02-03 17:18:03 +0100130 rc = encode_gsm_rlcmac_downlink(resultVector, &data);
131 cout << "+++++++++Finish ENCODE ("<< rc <<")+++++++++++" << endl;
Pau Espin Pedrol87bfbe42020-01-23 23:51:34 +0100132 cout << "vector1 = " << osmo_hexdump(vector->data, 23) << endl;
133 cout << "vector2 = " << osmo_hexdump(resultVector->data, 23) << endl;
Ivan Kluchnikov835f91e2012-04-30 18:00:36 +0400134 if (memcmp(vector->data, resultVector->data, 23) == 0)
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300135 cout << "vector1 == vector2 : TRUE" << endl;
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300136 else
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300137 cout << "vector1 == vector2 : FALSE" << endl;
Max7426c5f2019-02-18 20:42:42 +0100138 bitvec_unhex(resultVector, DUMMY_VEC);
Ivan Kluchnikov835f91e2012-04-30 18:00:36 +0400139 bitvec_free(vector);
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300140 }
Andreas Eversberg273a2222013-01-16 08:56:33 +0100141
142 bitvec_free(resultVector);
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300143}
144
145
Alexander Couzensccde5c92017-02-04 03:10:08 +0100146void testRlcMacUplink(void *test_ctx)
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300147{
Pau Espin Pedrol54681c32020-01-23 21:59:23 +0100148 printf("*** %s ***\n", __func__);
Pau Espin Pedrol5e300ce2020-02-03 17:18:03 +0100149
150 int rc;
Alexander Couzensccde5c92017-02-04 03:10:08 +0100151 struct bitvec *resultVector = bitvec_alloc(23, test_ctx);
Max7426c5f2019-02-18 20:42:42 +0100152 bitvec_unhex(resultVector, DUMMY_VEC);
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300153
154 std::string testData[] = {
Saurabh Sharan656eed52016-03-10 14:15:29 +0530155 "400e1e61d11d2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b", // Packet Uplink Dummy Control Block
156 "400b8020000000000000002480e0032b2b2b2b2b2b2b2b", // Packet Downlink Ack/Nack
Saurabh Sharanbacb65b2016-03-10 17:24:49 +0530157 "4016713dc094270ca2ae57ef909006aa0fc0001f80222b", // Packet Resource Request
Vadim Yanitskiyf22163b2020-03-06 06:51:48 +0700158 "401673c87f24af2632b25964200600000091000b780080", // Packet Resource Request (from keith)
Saurabh Sharanbacb65b2016-03-10 17:24:49 +0530159 "40200ffc0021ec010b2b2b2b2b2b2b2b2b2b2b2b2b2b2b", // EPDAN
Pau Espin Pedrol5cb002f2020-01-23 23:45:17 +0100160 "400a9020000000000000003010012a0800132b2b2b2b2b", // Packet Downlink Ack/Nack ?
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300161 };
162
163 int testDataSize = sizeof(testData)/sizeof(testData[0]);
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300164
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300165
166 cout << " UPLINK " << endl;
167 for (int i = 0; i < testDataSize; i++)
168 {
Pau Espin Pedrol87bfbe42020-01-23 23:51:34 +0100169 cout << "vector1 = " << testData[i] << endl;
Alexander Couzensccde5c92017-02-04 03:10:08 +0100170 bitvec *vector = bitvec_alloc(23, test_ctx);
Ivan Kluchnikov835f91e2012-04-30 18:00:36 +0400171 bitvec_unhex(vector, testData[i].c_str());
Pau Espin Pedrol87bfbe42020-01-23 23:51:34 +0100172
Pau Espin Pedrol99c437b2020-01-24 12:34:50 +0100173 RlcMacUplink_t data;
174 memset(&data, 0, sizeof(data));
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300175 cout << "=========Start DECODE===========" << endl;
Pau Espin Pedrol5e300ce2020-02-03 17:18:03 +0100176 rc = decode_gsm_rlcmac_uplink(vector, &data);
177 cout << "+++++++++Finish DECODE ("<< rc << ")++++++++++" << endl;
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300178 cout << "=========Start ENCODE=============" << endl;
Pau Espin Pedrol5e300ce2020-02-03 17:18:03 +0100179 rc = encode_gsm_rlcmac_uplink(resultVector, &data);
180 cout << "+++++++++Finish ENCODE ("<< rc <<")+++++++++++" << endl;
Pau Espin Pedrol87bfbe42020-01-23 23:51:34 +0100181 cout << "vector1 = " << osmo_hexdump(vector->data, 23) << endl;
182 cout << "vector2 = " << osmo_hexdump(resultVector->data, 23) << endl;
Ivan Kluchnikov835f91e2012-04-30 18:00:36 +0400183 if (memcmp(vector->data, resultVector->data, 23) == 0)
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300184 cout << "vector1 == vector2 : TRUE" << endl;
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300185 else
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300186 cout << "vector1 == vector2 : FALSE" << endl;
Max7426c5f2019-02-18 20:42:42 +0100187 bitvec_unhex(resultVector, DUMMY_VEC);
Ivan Kluchnikov835f91e2012-04-30 18:00:36 +0400188 bitvec_free(vector);
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300189 }
Andreas Eversberg273a2222013-01-16 08:56:33 +0100190
191 bitvec_free(resultVector);
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300192}
193
Alexander Couzensccde5c92017-02-04 03:10:08 +0100194void testCsnLeftAlignedVarBmpBounds(void *test_ctx)
Aravind Sirsikar9f5f0082016-08-30 13:20:23 +0530195{
Pau Espin Pedrol54681c32020-01-23 21:59:23 +0100196 printf("*** %s ***\n", __func__);
Pau Espin Pedrol5e300ce2020-02-03 17:18:03 +0100197
Maxd3a0d912019-03-05 16:15:01 +0100198 struct msgb *m = msgb_alloc(80, "test");
199 static uint8_t exp[] = { 0x7f, 0xff, 0xff, 0xee, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
Alexander Couzensccde5c92017-02-04 03:10:08 +0100200 bitvec *vector = bitvec_alloc(23, test_ctx);
Pau Espin Pedrol5e300ce2020-02-03 17:18:03 +0100201 int rc;
Aravind Sirsikar9f5f0082016-08-30 13:20:23 +0530202
203 bitvec_unhex(vector, "40200bffd161003e0e519ffffffb800000000000000000");
204 RlcMacUplink_t data;
Pau Espin Pedrol99c437b2020-01-24 12:34:50 +0100205 memset(&data, 0, sizeof(data));
Aravind Sirsikar9f5f0082016-08-30 13:20:23 +0530206
207 EGPRS_AckNack_Desc_t *urbb =
208 &data.u.Egprs_Packet_Downlink_Ack_Nack.EGPRS_AckNack.Desc;
Pau Espin Pedrol5e300ce2020-02-03 17:18:03 +0100209 rc = decode_gsm_rlcmac_uplink(vector, &data);
210 OSMO_ASSERT(rc == 0);
Aravind Sirsikar9f5f0082016-08-30 13:20:23 +0530211
Maxd3a0d912019-03-05 16:15:01 +0100212 memcpy(msgb_put(m, 13), urbb->URBB, 13);
213 if (!msgb_eq_data_print(m, exp, 13))
214 printf("%s failed!\n", __func__);
215 msgb_free(m);
Aravind Sirsikar9f5f0082016-08-30 13:20:23 +0530216}
217
Vadim Yanitskiyb47e53b2020-02-20 04:33:50 +0700218int encode_gsm_ra_cap(bitvec * vector, MS_Radio_Access_capability_t * data);
219
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +0100220void testRAcap(void *test_ctx)
221{
Pau Espin Pedrol866bece2020-03-21 01:20:52 +0100222 printf("*** %s ***\n", __func__);
223 MS_Radio_Access_capability_t data;
224 memset(&data, 0, sizeof(data));
225 bitvec *bv_dec = bitvec_alloc(23, test_ctx);
226 bitvec *bv_enc = bitvec_alloc(23, test_ctx);
227 unsigned int len_dec, len_enc;
228 int rc;
229/*
230MS RA capability 1
231 0001 .... = Access Technology Type: GSM E --note that GSM E covers GSM P (1)
232 .... 0011 011. .... = Length in bits: 0x1b (27)
233 ...0 01.. RF Power Capability, GMSK Power Class: Not specified (1)
234 A5 Bits: Same values apply for parameters as in the immediately preceding Access capabilities field within this IE (0)
235 .... ...1 = Controlled early Classmark Sending: Implemented
236 0... .... = Pseudo Synchronisation: Not Present
237 .0.. .... = Voice Group Call Service: no VGCS capability or no notifications wanted
238 ..0. .... = Voice Broadcast Service: no VBS capability or no notifications wanted
239 ...1 .... = Multislot capability struct: Present
240 HSCSD multislot class: Bits are not available (0)
241 SMS_VALUE (Switch-Measure-Switch): Bits are not available (0)
242 ECSD multislot class: Bits are not available (0)
243 DTM GPRS Multi Slot Class: Bits are not available (0)
244 .... ..00 011. .... = GPRS multislot class: Max Rx-Slot/TDMA:2 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:3 Tta:3 Ttb:2 Tra:3 Trb:1 Type:1 (3)
245 ...0 .... = GPRS Extended Dynamic Allocation Capability: Not Implemented
246 .... ...0 0011 .... = EGPRS multislot class: Max Rx-Slot/TDMA:2 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:3 Tta:3 Ttb:2 Tra:3 Trb:1 Type:1 (3)
247 .... 0... = EGPRS Extended Dynamic Allocation Capability: Not Implemented
248*/
249 bitvec_unhex(bv_dec, "1365146230");
250
251 printf("=== Test decoding of MS RA Capability ===\n");
252 rc = decode_gsm_ra_cap(bv_dec, &data);
253 OSMO_ASSERT(rc == 0);
254
255 /* Make sure there's 1 value (currently fails due to failed decoding) */
256 OSMO_ASSERT(data.Count_MS_RA_capability_value == 1);
257
258 /* Make sure GPRS / EGPRS multislot class is parsed correctly */
259 printf("GPRS multislot class = %u\n", Decoding::get_ms_class_by_capability(&data));
260 printf("EGPRS multislot class = %u\n", Decoding::get_egprs_ms_class_by_capability(&data));
261
262 /* Test encoding of decoded MS RA Capability */
263 printf("=== Test encoding of MS RA Capability ===\n");
264 rc = encode_gsm_ra_cap(bv_enc, &data);
265 printf("encode_gsm_ra_cap() returns %d\n", rc);
266
267 bv_dec->cur_bit = 4;
268 len_dec = bitvec_get_uint(bv_dec, 7);
269 bv_enc->cur_bit = 4;
270 len_enc = bitvec_get_uint(bv_enc, 7);
271
272 /* NOTE: vector2 is expected to be different because there is actually no
273 * way to distinguish between NULL and 0 in MS_Radio_Access_capability_t.
274 * The difference is in length indicator: 27 bits vs 65 bits. */
275 printf("vector1 (len_ind=%u) = %s\n", len_dec, osmo_hexdump(bv_dec->data, bv_dec->data_len));
276 printf("vector2 (len_ind=%u) = %s\n", len_enc, osmo_hexdump(bv_enc->data, bv_enc->data_len));
277
278 /* Mangle the length indicator (set it to 21) */
279 unsigned int writeIndex = 4;
280 rc = bitvec_write_field(bv_dec, &writeIndex, 21, 7);
281 OSMO_ASSERT(rc == 0);
282
283 /* Make sure decoding attempt fails */
284 printf("=== Test decoding of a malformed vector (short length indicator) ===\n");
285 rc = decode_gsm_ra_cap(bv_dec, &data);
286 printf("decode_gsm_ra_cap() returns %d\n", rc);
287}
288
289void testMalformedRAcap(void *test_ctx)
290{
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +0100291 printf("*** %s ***\n", __func__);
292 MS_Radio_Access_capability_t data;
293 memset(&data, 0, sizeof(data));
Vadim Yanitskiyb47e53b2020-02-20 04:33:50 +0700294 bitvec *bv_dec = bitvec_alloc(23, test_ctx);
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +0100295 int rc;
296/*
297 MS RA capability 1
298 0001 .... = Access Technology Type: GSM E --note that GSM E covers GSM P (1)
Vadim Yanitskiy55f06c32020-02-18 05:45:15 +0700299 .... 0011 101. .... = Length in bits: 0x1d (29)
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +0100300 ...0 01.. RF Power Capability, GMSK Power Class: Not specified (1)
301 A5 Bits: Same values apply for parameters as in the immediately preceding Access capabilities field within this IE (0)
302 .... ...1 = Controlled early Classmark Sending: Implemented
303 0... .... = Pseudo Synchronisation: Not Present
304 .0.. .... = Voice Group Call Service: no VGCS capability or no notifications wanted
305 ..0. .... = Voice Broadcast Service: no VBS capability or no notifications wanted
306 ...1 .... = Multislot capability struct: Present
307 .... ..00 011. .... = GPRS multislot class: Max Rx-Slot/TDMA:2 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:3 Tta:3 Ttb:2 Tra:3 Trb:1 Type:1 (3)
308 ...0 .... = GPRS Extended Dynamic Allocation Capability: Not Implemented
Pau Espin Pedrol866bece2020-03-21 01:20:52 +0100309
310 It doesn't show up in wireshark's tree above because specific parser is
311 used, but this RA Cap bitstream has Exist_EGPRS_multislot_class = 1 but
312 it provides no struct with the expected data (malformed, generated
313 erroneusly through TTCN3). The CSN.1 dceoder should ideally return an
314 error here, but it doesn't (it returns a >0 value which we convert to 0
315 in decode_gsm_ra_cap()).
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +0100316*/
Vadim Yanitskiyb47e53b2020-02-20 04:33:50 +0700317 bitvec_unhex(bv_dec, "13a5146200");
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +0100318
Vadim Yanitskiyb47e53b2020-02-20 04:33:50 +0700319 printf("=== Test decoding of MS RA Capability ===\n");
320 rc = decode_gsm_ra_cap(bv_dec, &data);
Pau Espin Pedrol866bece2020-03-21 01:20:52 +0100321 printf("decode_gsm_ra_cap() returns %d\n", rc);
Vadim Yanitskiy55f06c32020-02-18 05:45:15 +0700322 OSMO_ASSERT(rc == 0);
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +0100323
Pau Espin Pedrol866bece2020-03-21 01:20:52 +0100324 /* For sake of completeness, check if the decoder could find 1 value
325 before failing to decode it */
Vadim Yanitskiy55f06c32020-02-18 05:45:15 +0700326 OSMO_ASSERT(data.Count_MS_RA_capability_value == 1);
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +0100327
Pau Espin Pedrol2f169242020-03-20 23:59:44 +0100328 bitvec_free(bv_dec);
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +0100329}
330
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300331int main(int argc, char *argv[])
332{
Alexander Couzensccde5c92017-02-04 03:10:08 +0100333 void *ctx = talloc_named_const(NULL, 1, "RLCMACTest");
Neels Hofmeyr42f2d612018-04-01 16:54:40 +0200334 osmo_init_logging2(ctx, &gprs_log_info);
Harald Welte570f9132020-03-19 15:03:01 +0100335 log_parse_category_mask(osmo_stderr_target, "DPCU,3:DLGLOBAL,1:DRLCMACDATA,2:DCSN1,1:");
Vadim Yanitskiy8a87f912020-02-17 01:19:10 +0700336
337 log_set_print_filename2(osmo_stderr_target, LOG_FILENAME_NONE);
338 log_set_print_category_hex(osmo_stderr_target, 0);
339 log_set_print_category(osmo_stderr_target, 1);
340 log_set_print_level(osmo_stderr_target, 1);
341 log_set_use_color(osmo_stderr_target, 0);
Andreas Eversberg138f4e62013-01-14 12:31:11 +0100342
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300343 //printSizeofRLCMAC();
Alexander Couzensccde5c92017-02-04 03:10:08 +0100344 testRlcMacDownlink(ctx);
345 testRlcMacUplink(ctx);
346 testCsnLeftAlignedVarBmpBounds(ctx);
Pau Espin Pedrolcdbc5db2020-01-23 21:00:19 +0100347 testRAcap(ctx);
Pau Espin Pedrol866bece2020-03-21 01:20:52 +0100348 testMalformedRAcap(ctx);
Alexander Couzensccde5c92017-02-04 03:10:08 +0100349 talloc_free(ctx);
Ivan Kluchnikov487a1412011-12-21 13:17:53 +0300350}