aboutsummaryrefslogtreecommitdiffstats
path: root/tests/tlv/tlv_test.c
diff options
context:
space:
mode:
Diffstat (limited to 'tests/tlv/tlv_test.c')
-rw-r--r--tests/tlv/tlv_test.c155
1 files changed, 152 insertions, 3 deletions
diff --git a/tests/tlv/tlv_test.c b/tests/tlv/tlv_test.c
index 925d7628..8e8bd603 100644
--- a/tests/tlv/tlv_test.c
+++ b/tests/tlv/tlv_test.c
@@ -188,7 +188,7 @@ static void check_lv_shift_data_len(size_t data_len,
}
}
-static void test_tlv_shift_functions()
+static void test_tlv_shift_functions(void)
{
uint8_t test_data[1024];
uint8_t buf[1024];
@@ -250,7 +250,7 @@ static void test_tlv_shift_functions()
/* Most GSM related protocols clearly indicate that in case of duplicate
* IEs, only the first occurrence shall be used, while any further occurrences
* shall be ignored. See e.g. 3GPP TS 24.008 Section 8.6.3 */
-static void test_tlv_repeated_ie()
+static void test_tlv_repeated_ie(void)
{
uint8_t test_data[768];
int i, rc;
@@ -288,7 +288,7 @@ static void test_tlv_repeated_ie()
OSMO_ASSERT(dec3[2].lv[tag].val == &test_data[2 + 3 + 3]);
}
-static void test_tlv_encoder()
+static void test_tlv_encoder(void)
{
const uint8_t enc_ies[] = {
0x17, 0x14, 0x06, 0x2b, 0x12, 0x2b, 0x0b, 0x40, 0x2b, 0xb7, 0x05, 0xd0, 0x63, 0x82, 0x95, 0x03, 0x05, 0x40,
@@ -332,6 +332,152 @@ static void test_tlv_encoder()
msgb_free(msg);
}
+static void test_tlv_parser_bounds(void)
+{
+ struct tlv_definition tdef;
+ struct tlv_parsed dec;
+ uint8_t buf[32];
+
+ memset(&tdef, 0, sizeof(tdef));
+
+ printf("Testing TLV_TYPE_T decoder for out-of-bounds\n");
+ tdef.def[0x23].type = TLV_TYPE_T;
+ buf[0] = 0x23;
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 1, 0, 0) == 1);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 0, 0, 0) == 0);
+
+ printf("Testing TLV_TYPE_TV decoder for out-of-bounds\n");
+ tdef.def[0x23].type = TLV_TYPE_TV;
+ buf[0] = 0x23;
+ buf[1] = 0x42;
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 2, 0, 0) == 1);
+ OSMO_ASSERT(*TLVP_VAL(&dec, 0x23) == buf[1]);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 1, 0, 0) == OSMO_TLVP_ERR_OFS_LEN_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+
+ printf("Testing TLV_TYPE_FIXED decoder for out-of-bounds\n");
+ tdef.def[0x23].type = TLV_TYPE_FIXED;
+ tdef.def[0x23].fixed_len = 2;
+ buf[0] = 0x23;
+ buf[1] = 0x42;
+ buf[2] = 0x55;
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 3, 0, 0) == 1);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 2, 0, 0) == OSMO_TLVP_ERR_OFS_LEN_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+
+ printf("Testing TLV_TYPE_TLV decoder for out-of-bounds\n");
+ tdef.def[0x23].type = TLV_TYPE_TLV;
+ buf[0] = 0x23;
+ buf[1] = 0x02;
+ buf[2] = 0x55;
+ buf[3] = 0xAA;
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 4, 0, 0) == 1);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == &buf[2]);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 3, 0, 0) == OSMO_TLVP_ERR_OFS_LEN_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 2, 0, 0) == OSMO_TLVP_ERR_OFS_LEN_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 1, 0, 0) == OSMO_TLVP_ERR_OFS_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+
+ printf("Testing TLV_TYPE_vTvLV_GAN decoder for out-of-bounds\n");
+ tdef.def[0x23].type = TLV_TYPE_vTvLV_GAN;
+ buf[0] = 0x23;
+ buf[1] = 0x80;
+ buf[2] = 0x01;
+ buf[3] = 0xAA;
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 4, 0, 0) == 1);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == &buf[3]);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 3, 0, 0) == OSMO_TLVP_ERR_OFS_LEN_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 2, 0, 0) == OSMO_TLVP_ERR_OFS_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 1, 0, 0) == OSMO_TLVP_ERR_OFS_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+
+ printf("Testing TLV_TYPE_TvLV decoder for out-of-bounds\n");
+ tdef.def[0x23].type = TLV_TYPE_TvLV;
+ buf[0] = 0x23;
+ buf[1] = 0x81;
+ buf[2] = 0xAA;
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 3, 0, 0) == 1);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == &buf[2]);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 2, 0, 0) == OSMO_TLVP_ERR_OFS_LEN_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 1, 0, 0) == OSMO_TLVP_ERR_OFS_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+
+ printf("Testing TLV_TYPE_TL16V decoder for out-of-bounds\n");
+ tdef.def[0x23].type = TLV_TYPE_TL16V;
+ buf[0] = 0x23;
+ buf[1] = 0x00;
+ buf[2] = 0x01;
+ buf[3] = 0xAA;
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 4, 0, 0) == 1);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == &buf[3]);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 3, 0, 0) == OSMO_TLVP_ERR_OFS_LEN_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 2, 0, 0) == OSMO_TLVP_ERR_OFS_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+ OSMO_ASSERT(tlv_parse(&dec, &tdef, buf, 1, 0, 0) == OSMO_TLVP_ERR_OFS_BEYOND_BUFFER);
+ OSMO_ASSERT(TLVP_VAL(&dec, 0x23) == NULL);
+}
+
+static void test_tlv_lens(void)
+{
+ uint16_t buf_len;
+ uint8_t buf[512];
+ uint8_t val[512] = { 0 };
+ uint16_t x;
+
+
+ for (x = 0; x < 16; x++) {
+ buf_len = lv_put(buf, x, val) - buf;
+ OSMO_ASSERT(buf_len == LV_GROSS_LEN(x));
+ buf_len = tlv_put(buf, 0x23, x, val) - buf;
+ OSMO_ASSERT(buf_len == TLV_GROSS_LEN(x));
+ buf_len = tlv16_put(buf, 0x23, x, (uint16_t *) val) - buf;
+ OSMO_ASSERT(buf_len == TLV16_GROSS_LEN(x));
+ buf_len = tl16v_put(buf, 0x23, x, val) - buf;
+ OSMO_ASSERT(buf_len == TL16V_GROSS_LEN(x));
+ buf_len = t16lv_put(buf, 0x2342, x, val) - buf;
+ OSMO_ASSERT(buf_len == T16LV_GROSS_LEN(x));
+ buf_len = tvlv_put(buf, 0x23, x, val) - buf;
+ OSMO_ASSERT(buf_len == TVLV_GROSS_LEN(x));
+ }
+
+ for (x = 250; x < 300; x++) {
+ buf_len = tl16v_put(buf, 0x23, x, val) - buf;
+ OSMO_ASSERT(buf_len == TL16V_GROSS_LEN(x));
+ buf_len = tvlv_put(buf, 0x23, x, val) - buf;
+ OSMO_ASSERT(buf_len == TVLV_GROSS_LEN(x));
+ }
+}
+
+static void test_tlv_type_single_tv(void)
+{
+ #define SAMPLE_SINGLE_TV_IE 0x08
+ const struct tlv_definition att_tlvdef = {
+ .def = {
+ [SAMPLE_SINGLE_TV_IE] = { TLV_TYPE_SINGLE_TV, 0 },
+ },
+ };
+ struct tlv_parsed tp;
+ int rc;
+ uint8_t exp_val = 0x03;
+ uint8_t buf[] = { (SAMPLE_SINGLE_TV_IE << 4) | (exp_val & 0x0f) };
+ const uint8_t *val;
+
+ rc = tlv_parse(&tp, &att_tlvdef, buf, sizeof(buf), 0, 0);
+ OSMO_ASSERT(rc == 1);
+ OSMO_ASSERT(TLVP_PRESENT(&tp, SAMPLE_SINGLE_TV_IE));
+ val = TLVP_VAL(&tp, SAMPLE_SINGLE_TV_IE);
+ OSMO_ASSERT(val);
+ OSMO_ASSERT(val == &buf[0]);
+ OSMO_ASSERT(*val == buf[0]);
+ OSMO_ASSERT((*val & 0x0f) == exp_val);
+}
+
int main(int argc, char **argv)
{
//osmo_init_logging2(ctx, &info);
@@ -339,6 +485,9 @@ int main(int argc, char **argv)
test_tlv_shift_functions();
test_tlv_repeated_ie();
test_tlv_encoder();
+ test_tlv_parser_bounds();
+ test_tlv_lens();
+ test_tlv_type_single_tv();
printf("Done.\n");
return EXIT_SUCCESS;