diff options
author | Marcel Holtmann <marcel@holtmann.org> | 2008-06-22 21:59:42 +0000 |
---|---|---|
committer | Marcel Holtmann <marcel@holtmann.org> | 2008-06-22 21:59:42 +0000 |
commit | 0e1789b3f1897512eb30d63c8e9803f1461446c1 (patch) | |
tree | 3ad1c147a43aaba27eb12fa1af66ed149041ddb5 | |
parent | a3648e0df0ff53fef74e5437ff089aef96209db2 (diff) |
Add safe version of sdp_extract_pdu function
-rw-r--r-- | include/sdp_lib.h | 4 | ||||
-rw-r--r-- | src/sdp.c | 30 |
2 files changed, 27 insertions, 7 deletions
diff --git a/include/sdp_lib.h b/include/sdp_lib.h index 2323abfc..8df540c6 100644 --- a/include/sdp_lib.h +++ b/include/sdp_lib.h @@ -585,9 +585,11 @@ static inline int sdp_get_icon_url(const sdp_record_t *rec, char *str, int len) return sdp_get_string_attr(rec, SDP_ATTR_ICON_URL, str, len); } -sdp_record_t *sdp_extract_pdu(const uint8_t *pdata, int *scanned); sdp_data_t *sdp_extract_string(uint8_t *, int *); +sdp_record_t *sdp_extract_pdu(const uint8_t *pdata, int *scanned); +sdp_record_t *sdp_extract_pdu_safe(const uint8_t *pdata, int bufsize, int *scanned); + void sdp_data_print(sdp_data_t *data); void sdp_print_service_attr(sdp_list_t *alist); @@ -1323,7 +1323,7 @@ void sdp_print_service_attr(sdp_list_t *svcAttrList) } #endif -sdp_record_t *sdp_extract_pdu(const uint8_t *buf, int *scanned) +sdp_record_t *sdp_extract_pdu_safe(const uint8_t *buf, int bufsize, int *scanned) { int extracted = 0, seqlen = 0; uint8_t dtd; @@ -1331,21 +1331,30 @@ sdp_record_t *sdp_extract_pdu(const uint8_t *buf, int *scanned) sdp_record_t *rec = sdp_record_alloc(); const uint8_t *p = buf; - *scanned = sdp_extract_seqtype(buf, &dtd, &seqlen); + *scanned = sdp_extract_seqtype_safe(buf, bufsize, &dtd, &seqlen); p += *scanned; + bufsize -= *scanned; rec->attrlist = NULL; - while (extracted < seqlen) { + + while (extracted < seqlen && bufsize > 0) { int n = sizeof(uint8_t), attrlen = 0; sdp_data_t *data = NULL; - SDPDBG("Extract PDU, sequenceLength: %d localExtractedLength: %d", seqlen, extracted); + SDPDBG("Extract PDU, sequenceLength: %d localExtractedLength: %d", + seqlen, extracted); + + if (bufsize < n + sizeof(uint16_t)) { + SDPERR("Unexpected end of packet"); + break; + } + dtd = *(uint8_t *) p; attr = ntohs(bt_get_unaligned((uint16_t *) (p + n))); n += sizeof(uint16_t); SDPDBG("DTD of attrId : %d Attr id : 0x%x \n", dtd, attr); - data = sdp_extract_attr(p + n, &attrlen, rec); + data = sdp_extract_attr_safe(p + n, bufsize - n, &attrlen, rec); SDPDBG("Attr id : 0x%x attrValueLength : %d\n", attr, attrlen); @@ -1363,9 +1372,11 @@ sdp_record_t *sdp_extract_pdu(const uint8_t *buf, int *scanned) extracted += n; p += n; + bufsize -= n; sdp_attr_replace(rec, attr, data); + SDPDBG("Extract PDU, seqLength: %d localExtractedLength: %d", - seqlen, extracted); + seqlen, extracted); } #ifdef SDP_DEBUG SDPDBG("Successful extracting of Svc Rec attributes\n"); @@ -1375,6 +1386,13 @@ sdp_record_t *sdp_extract_pdu(const uint8_t *buf, int *scanned) return rec; } +sdp_record_t *sdp_extract_pdu(const uint8_t *buf, int *scanned) +{ + /* Assume buf points to a buffer of size at least SDP_MAX_ATTR_LEN, + because we don't have any better information */ + return sdp_extract_pdu_safe(buf, SDP_MAX_ATTR_LEN, scanned); +} + #ifdef SDP_DEBUG static void print_dataseq(sdp_data_t *p) { |