diff options
author | Anderson Lizardo <anderson.lizardo@openbossa.org> | 2013-02-15 11:07:48 -0400 |
---|---|---|
committer | Johan Hedberg <johan.hedberg@intel.com> | 2013-02-18 09:59:35 +0200 |
commit | fcb9ece0f9ef5b141634be945690757c425aa45a (patch) | |
tree | 57ff8f7fd00d15f4e99835649e16af320477a3dd /lib | |
parent | 9e2d91bc75ce093f3a8ff40288c3da0f19fae38d (diff) |
lib: Fix missing DTD validation while accessing SDP data elements
It is necessary to validate the sdp_data_t "dtd" field before accessing
the "val" union members, specially when handling SDP_SEQ*, SDP_ALT* and
SDP_STR* elements, otherwise remote devices can trigger memory
corruption by passing invalid data elements where others are expected.
Diffstat (limited to 'lib')
-rw-r--r-- | lib/sdp.c | 26 |
1 files changed, 24 insertions, 2 deletions
@@ -1874,19 +1874,41 @@ static int sdp_get_proto_descs(uint16_t attr_id, const sdp_record_t *rec, SDPDBG("Attribute value type: 0x%02x\n", pdlist->dtd); - if (attr_id == SDP_ATTR_ADD_PROTO_DESC_LIST) + if (attr_id == SDP_ATTR_ADD_PROTO_DESC_LIST) { + if (!SDP_IS_SEQ(pdlist->dtd)) { + errno = EINVAL; + return -1; + } pdlist = pdlist->val.dataseq; + } for (; pdlist; pdlist = pdlist->next) { sdp_list_t *pds = NULL; - for (curr = pdlist->val.dataseq; curr; curr = curr->next) + + if (!SDP_IS_SEQ(pdlist->dtd) && !SDP_IS_ALT(pdlist->dtd)) + goto failed; + + for (curr = pdlist->val.dataseq; curr; curr = curr->next) { + if (!SDP_IS_SEQ(curr->dtd)) { + sdp_list_free(pds, NULL); + goto failed; + } pds = sdp_list_append(pds, curr->val.dataseq); + } + ap = sdp_list_append(ap, pds); } *pap = ap; return 0; + +failed: + sdp_list_foreach(ap, (sdp_list_func_t) sdp_list_free, NULL); + sdp_list_free(ap, NULL); + errno = EINVAL; + + return -1; } int sdp_get_access_protos(const sdp_record_t *rec, sdp_list_t **pap) |