Commit 60e4246d authored by Slava Monich's avatar Slava Monich

Merge branch 'cbs' into 'master'

Allow the last CBS fragment to be truncated.

See merge request mer-core/ofono!269
parents 98b357f3 50619607
...@@ -3,6 +3,7 @@ ...@@ -3,6 +3,7 @@
* oFono - Open Source Telephony * oFono - Open Source Telephony
* *
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved. * Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2015-2020 Jolla Ltd.
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as * it under the terms of the GNU General Public License version 2 as
...@@ -1757,7 +1758,7 @@ gboolean sms_udh_iter_init_from_cbs(const struct cbs *cbs, ...@@ -1757,7 +1758,7 @@ gboolean sms_udh_iter_init_from_cbs(const struct cbs *cbs,
return FALSE; return FALSE;
hdr = cbs->ud; hdr = cbs->ud;
max_ud_len = 82; max_ud_len = cbs->udlen;
/* Must have at least one information-element if udhi is true */ /* Must have at least one information-element if udhi is true */
if (hdr[0] < 2) if (hdr[0] < 2)
...@@ -3856,8 +3857,8 @@ gboolean cbs_dcs_decode(guint8 dcs, gboolean *udhi, enum sms_class *cls, ...@@ -3856,8 +3857,8 @@ gboolean cbs_dcs_decode(guint8 dcs, gboolean *udhi, enum sms_class *cls,
gboolean cbs_decode(const unsigned char *pdu, int len, struct cbs *out) gboolean cbs_decode(const unsigned char *pdu, int len, struct cbs *out)
{ {
/* CBS is always a fixed length of 88 bytes */ /* CBS is (almost) always a fixed length of 88 bytes */
if (len != 88) if (len < 6 || len > 88)
return FALSE; return FALSE;
out->gs = (enum cbs_geo_scope) ((pdu[0] >> 6) & 0x03); out->gs = (enum cbs_geo_scope) ((pdu[0] >> 6) & 0x03);
...@@ -3868,6 +3869,10 @@ gboolean cbs_decode(const unsigned char *pdu, int len, struct cbs *out) ...@@ -3868,6 +3869,10 @@ gboolean cbs_decode(const unsigned char *pdu, int len, struct cbs *out)
out->max_pages = pdu[5] & 0xf; out->max_pages = pdu[5] & 0xf;
out->page = (pdu[5] >> 4) & 0xf; out->page = (pdu[5] >> 4) & 0xf;
/* Allow the last fragment to be truncated */
if (len != 88 && out->max_pages != out->page)
return FALSE;
/* /*
* If a mobile receives the code 0000 in either the first field or * If a mobile receives the code 0000 in either the first field or
* the second field then it shall treat the CBS message exactly the * the second field then it shall treat the CBS message exactly the
...@@ -3879,7 +3884,10 @@ gboolean cbs_decode(const unsigned char *pdu, int len, struct cbs *out) ...@@ -3879,7 +3884,10 @@ gboolean cbs_decode(const unsigned char *pdu, int len, struct cbs *out)
out->page = 1; out->page = 1;
} }
memcpy(out->ud, pdu + 6, 82); out->udlen = (guint8)(len - 6);
memcpy(out->ud, pdu + 6, out->udlen);
if (out->udlen < 82)
memset(out->ud + out->udlen, 0, 82 - out->udlen);
return TRUE; return TRUE;
} }
...@@ -4072,7 +4080,7 @@ char *cbs_decode_text(GSList *cbs_list, char *iso639_lang) ...@@ -4072,7 +4080,7 @@ char *cbs_decode_text(GSList *cbs_list, char *iso639_lang)
if (iso639) if (iso639)
bufsize -= 3; bufsize -= 3;
} else { } else {
bufsize += 82; bufsize += cbs->udlen;
if (iso639) if (iso639)
bufsize -= 2; bufsize -= 2;
...@@ -4089,7 +4097,7 @@ char *cbs_decode_text(GSList *cbs_list, char *iso639_lang) ...@@ -4089,7 +4097,7 @@ char *cbs_decode_text(GSList *cbs_list, char *iso639_lang)
if (sms_udh_iter_init_from_cbs(cbs, &iter)) if (sms_udh_iter_init_from_cbs(cbs, &iter))
taken = sms_udh_iter_get_udh_length(&iter) + 1; taken = sms_udh_iter_get_udh_length(&iter) + 1;
unpack_7bit_own_buf(cbs->ud + taken, 82 - taken, unpack_7bit_own_buf(cbs->ud + taken, cbs->udlen - taken,
taken, FALSE, 2, taken, FALSE, 2,
NULL, 0, NULL, 0,
(unsigned char *)iso639_lang); (unsigned char *)iso639_lang);
...@@ -4122,7 +4130,7 @@ char *cbs_decode_text(GSList *cbs_list, char *iso639_lang) ...@@ -4122,7 +4130,7 @@ char *cbs_decode_text(GSList *cbs_list, char *iso639_lang)
max_chars = max_chars =
sms_text_capacity_gsm(CBS_MAX_GSM_CHARS, taken); sms_text_capacity_gsm(CBS_MAX_GSM_CHARS, taken);
unpack_7bit_own_buf(ud + taken, 82 - taken, unpack_7bit_own_buf(ud + taken, cbs->udlen - taken,
taken, FALSE, max_chars, taken, FALSE, max_chars,
&written, 0, unpacked); &written, 0, unpacked);
...@@ -4156,7 +4164,7 @@ char *cbs_decode_text(GSList *cbs_list, char *iso639_lang) ...@@ -4156,7 +4164,7 @@ char *cbs_decode_text(GSList *cbs_list, char *iso639_lang)
* the check here since the specification isn't clear * the check here since the specification isn't clear
*/ */
} else { } else {
int num_ucs2_chars = (82 - taken) >> 1; int num_ucs2_chars = (cbs->udlen - taken) >> 1;
int i = taken; int i = taken;
int max_offset = taken + num_ucs2_chars * 2; int max_offset = taken + num_ucs2_chars * 2;
......
...@@ -3,6 +3,7 @@ ...@@ -3,6 +3,7 @@
* oFono - Open Source Telephony * oFono - Open Source Telephony
* *
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved. * Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2015-2020 Jolla Ltd.
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as * it under the terms of the GNU General Public License version 2 as
...@@ -398,6 +399,7 @@ struct cbs { ...@@ -398,6 +399,7 @@ struct cbs {
guint8 dcs; /* 8 bits */ guint8 dcs; /* 8 bits */
guint8 max_pages; /* 4 bits */ guint8 max_pages; /* 4 bits */
guint8 page; /* 4 bits */ guint8 page; /* 4 bits */
guint8 udlen;
guint8 ud[82]; guint8 ud[82];
}; };
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment