laforge has submitted this change and it was merged. ( https://gerrit.osmocom.org/c/osmo-msc/+/13470 )
Change subject: libmsc/db.c: fix potential integer overflow ...................................................................... libmsc/db.c: fix potential integer overflow The value of 'sms->user_data_len' is fetched from the database: sms->user_data_len = dbi_result_get_field_length(result, "user_data"); and this is where the problem is. As per the libdbi's documentation (see 3.5.3), dbi_result_get_field_length() returns the length in bytes of the value stored in the specified field: unsigned int dbi_result_get_field_length(dbi_result Result, const char *fieldname) so 'unsigned int' is assigned to 'uint8_t', what could lead to an integer overflow if the value is grather than 0xff. As a result, if the database for some reason does contain such odd TP-UD, the truncation of 'user_data' would be done incorrectly. Let's avoid such direct assignment, and use a separate variable. Also, let's warn user if TP-UDL value is grether than 140, as per 3GPP TS 03.40. Change-Id: Ibbd588545e1a4817504c806a3d02cf59d5938ee2 Related: OS#3684 --- M src/libmsc/db.c 1 file changed, 27 insertions(+), 9 deletions(-) Approvals: laforge: Looks good to me, approved Jenkins Builder: Verified diff --git a/src/libmsc/db.c b/src/libmsc/db.c index e3995a6..1fe8e6b 100644 --- a/src/libmsc/db.c +++ b/src/libmsc/db.c @@ -236,6 +236,7 @@ long long unsigned int sender_id; const char *text, *daddr; const unsigned char *user_data; + unsigned int user_data_len; char buf[32]; char *quoted; dbi_result result2; @@ -273,10 +274,15 @@ if (daddr) OSMO_STRLCPY_ARRAY(sms->dst.addr, daddr); - sms->user_data_len = dbi_result_get_field_length(result, "user_data"); + user_data_len = dbi_result_get_field_length(result, "user_data"); user_data = dbi_result_get_binary(result, "user_data"); - if (sms->user_data_len > sizeof(sms->user_data)) - sms->user_data_len = (uint8_t) sizeof(sms->user_data); + if (user_data_len > sizeof(sms->user_data)) { + LOGP(DDB, LOGL_ERROR, + "SMS TP-UD length %u is too big, truncating to %zu\n", + user_data_len, sizeof(sms->user_data)); + user_data_len = (uint8_t) sizeof(sms->user_data); + } + sms->user_data_len = user_data_len; memcpy(sms->user_data, user_data, sms->user_data_len); text = dbi_result_get_string(result, "text"); @@ -395,6 +401,7 @@ { struct gsm_sms *sms = sms_alloc(); const unsigned char *user_data; + unsigned int user_data_len; const char *text, *addr; if (!sms) @@ -419,10 +426,15 @@ sms->dst.ton = dbi_result_get_ulonglong(result, "dest_ton"); sms->dst.npi = dbi_result_get_ulonglong(result, "dest_npi"); - sms->user_data_len = dbi_result_get_field_length(result, "user_data"); + user_data_len = dbi_result_get_field_length(result, "user_data"); user_data = dbi_result_get_binary(result, "user_data"); - if (sms->user_data_len > sizeof(sms->user_data)) - sms->user_data_len = (uint8_t) sizeof(sms->user_data); + if (user_data_len > sizeof(sms->user_data)) { + LOGP(DDB, LOGL_ERROR, + "SMS TP-UD length %u is too big, truncating to %zu\n", + user_data_len, sizeof(sms->user_data)); + user_data_len = (uint8_t) sizeof(sms->user_data); + } + sms->user_data_len = user_data_len; memcpy(sms->user_data, user_data, sms->user_data_len); text = dbi_result_get_string(result, "text"); @@ -753,6 +765,7 @@ struct gsm_sms *sms = sms_alloc(); const char *text, *daddr, *saddr; const unsigned char *user_data; + unsigned int user_data_len; time_t validity_timestamp; if (!sms) @@ -789,10 +802,15 @@ if (saddr) OSMO_STRLCPY_ARRAY(sms->src.addr, saddr); - sms->user_data_len = dbi_result_get_field_length(result, "user_data"); + user_data_len = dbi_result_get_field_length(result, "user_data"); user_data = dbi_result_get_binary(result, "user_data"); - if (sms->user_data_len > sizeof(sms->user_data)) - sms->user_data_len = (uint8_t) sizeof(sms->user_data); + if (user_data_len > sizeof(sms->user_data)) { + LOGP(DDB, LOGL_ERROR, + "SMS TP-UD length %u is too big, truncating to %zu\n", + user_data_len, sizeof(sms->user_data)); + user_data_len = (uint8_t) sizeof(sms->user_data); + } + sms->user_data_len = user_data_len; if (user_data) memcpy(sms->user_data, user_data, sms->user_data_len); -- To view, visit https://gerrit.osmocom.org/c/osmo-msc/+/13470 To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings Gerrit-Project: osmo-msc Gerrit-Branch: master Gerrit-Change-Id: Ibbd588545e1a4817504c806a3d02cf59d5938ee2 Gerrit-Change-Number: 13470 Gerrit-PatchSet: 10 Gerrit-Owner: fixeria <axilira...@gmail.com> Gerrit-Reviewer: Jenkins Builder Gerrit-Reviewer: Neels Hofmeyr <nhofm...@sysmocom.de> Gerrit-Reviewer: fixeria <axilira...@gmail.com> Gerrit-Reviewer: laforge <lafo...@gnumonks.org> Gerrit-Reviewer: pespin <pes...@sysmocom.de> Gerrit-MessageType: merged