Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 4f380dbf authored by Android Build Merger (Role)'s avatar Android Build Merger (Role)
Browse files

[automerger] DO NOT MERGE: SDP: Check p_req_end before reading from p_req am:...

[automerger] DO NOT MERGE: SDP: Check p_req_end before reading from p_req am: c1347699 am: 14b050b7

Change-Id: Idde655e8a3377560317189bbc49620670c5923c8
parents 7843e90e 14b050b7
Loading
Loading
Loading
Loading
+37 −23
Original line number Original line Diff line number Diff line
@@ -124,12 +124,25 @@ void sdp_server_handle_client_req (tCONN_CB *p_ccb, BT_HDR *p_msg)


    /* Start inactivity timer */
    /* Start inactivity timer */
    btu_start_timer (&p_ccb->timer_entry, BTU_TTYPE_SDP, SDP_INACT_TIMEOUT);
    btu_start_timer (&p_ccb->timer_entry, BTU_TTYPE_SDP, SDP_INACT_TIMEOUT);
    if (p_req + sizeof(pdu_id) + sizeof(trans_num) > p_req_end) {
        android_errorWriteLog(0x534e4554, "69384124");
        trans_num = 0;
        sdpu_build_n_send_error(p_ccb, trans_num, SDP_INVALID_REQ_SYNTAX,
                                SDP_TEXT_BAD_HEADER);
    }


    /* The first byte in the message is the pdu type */
    /* The first byte in the message is the pdu type */
    pdu_id = *p_req++;
    pdu_id = *p_req++;


    /* Extract the transaction number and parameter length */
    /* Extract the transaction number and parameter length */
    BE_STREAM_TO_UINT16 (trans_num, p_req);
    BE_STREAM_TO_UINT16 (trans_num, p_req);

    if (p_req + sizeof(param_len) > p_req_end) {
        android_errorWriteLog(0x534e4554, "69384124");
        sdpu_build_n_send_error(p_ccb, trans_num, SDP_INVALID_REQ_SYNTAX,
                                SDP_TEXT_BAD_HEADER);
    }

    BE_STREAM_TO_UINT16 (param_len, p_req);
    BE_STREAM_TO_UINT16 (param_len, p_req);


    if ((p_req + param_len) != p_req_end)
    if ((p_req + param_len) != p_req_end)
@@ -195,17 +208,17 @@ static void process_service_search (tCONN_CB *p_ccb, UINT16 trans_num,
    }
    }


    /* Get the max replies we can send. Cap it at our max anyways. */
    /* Get the max replies we can send. Cap it at our max anyways. */
    if (p_req + sizeof(max_replies) + sizeof(uint8_t) > p_req_end) {
        android_errorWriteLog(0x534e4554, "69384124");
        sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_REQ_SYNTAX, SDP_TEXT_BAD_MAX_RECORDS_LIST);
        return;
    }
    BE_STREAM_TO_UINT16 (max_replies, p_req);
    BE_STREAM_TO_UINT16 (max_replies, p_req);


    if (max_replies > SDP_MAX_RECORDS)
    if (max_replies > SDP_MAX_RECORDS)
        max_replies = SDP_MAX_RECORDS;
        max_replies = SDP_MAX_RECORDS;




    if ((!p_req) || (p_req > p_req_end))
    {
        sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_REQ_SYNTAX, SDP_TEXT_BAD_MAX_RECORDS_LIST);
        return;
    }




    /* Get a list of handles that match the UUIDs given to us */
    /* Get a list of handles that match the UUIDs given to us */
@@ -222,8 +235,8 @@ static void process_service_search (tCONN_CB *p_ccb, UINT16 trans_num,
    /* Check if this is a continuation request */
    /* Check if this is a continuation request */
    if (*p_req)
    if (*p_req)
    {
    {
        if (*p_req++ != SDP_CONTINUATION_LEN || (p_req >= p_req_end))
        if (*p_req++ != SDP_CONTINUATION_LEN ||
        {
            (p_req + sizeof(cont_offset) > p_req_end)) {
            sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_CONT_STATE,
            sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_CONT_STATE,
                                     SDP_TEXT_BAD_CONT_LEN);
                                     SDP_TEXT_BAD_CONT_LEN);
            return;
            return;
@@ -332,15 +345,16 @@ static void process_service_attr_req (tCONN_CB *p_ccb, UINT16 trans_num,
    BOOLEAN         is_cont = FALSE;
    BOOLEAN         is_cont = FALSE;
    UINT16          attr_len;
    UINT16          attr_len;


    /* Extract the record handle */
    if (p_req + sizeof(rec_handle) + sizeof(max_list_len) > p_req_end) {
    BE_STREAM_TO_UINT32 (rec_handle, p_req);
        android_errorWriteLog(0x534e4554, "69384124");

        sdpu_build_n_send_error(p_ccb, trans_num, SDP_INVALID_SERV_REC_HDL,
    if (p_req > p_req_end)
                                SDP_TEXT_BAD_HANDLE);
    {
        sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_SERV_REC_HDL, SDP_TEXT_BAD_HANDLE);
        return;
        return;
    }
    }


    /* Extract the record handle */
    BE_STREAM_TO_UINT32 (rec_handle, p_req);

    /* Get the max list length we can send. Cap it at MTU size minus overhead */
    /* Get the max list length we can send. Cap it at MTU size minus overhead */
    BE_STREAM_TO_UINT16 (max_list_len, p_req);
    BE_STREAM_TO_UINT16 (max_list_len, p_req);


@@ -349,8 +363,8 @@ static void process_service_attr_req (tCONN_CB *p_ccb, UINT16 trans_num,


    p_req = sdpu_extract_attr_seq (p_req, param_len, &attr_seq);
    p_req = sdpu_extract_attr_seq (p_req, param_len, &attr_seq);


    if ((!p_req) || (!attr_seq.num_attr) || (p_req > p_req_end))
    if ((!p_req) || (!attr_seq.num_attr) ||
    {
        (p_req + sizeof(uint8_t) > p_req_end)) {
        sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_REQ_SYNTAX, SDP_TEXT_BAD_ATTR_LIST);
        sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_REQ_SYNTAX, SDP_TEXT_BAD_ATTR_LIST);
        return;
        return;
    }
    }
@@ -385,8 +399,8 @@ static void process_service_attr_req (tCONN_CB *p_ccb, UINT16 trans_num,
            return;
            return;
        }
        }


        if (*p_req++ != SDP_CONTINUATION_LEN)
        if (*p_req++ != SDP_CONTINUATION_LEN ||
        {
            (p_req + sizeof(cont_offset) > p_req_end)) {
            sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_CONT_STATE, SDP_TEXT_BAD_CONT_LEN);
            sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_CONT_STATE, SDP_TEXT_BAD_CONT_LEN);
            return;
            return;
        }
        }
@@ -610,8 +624,8 @@ static void process_service_search_attr_req (tCONN_CB *p_ccb, UINT16 trans_num,
    /* Extract the UUID sequence to search for */
    /* Extract the UUID sequence to search for */
    p_req = sdpu_extract_uid_seq (p_req, param_len, &uid_seq);
    p_req = sdpu_extract_uid_seq (p_req, param_len, &uid_seq);


    if ((!p_req) || (!uid_seq.num_uids))
    if ((!p_req) || (!uid_seq.num_uids) ||
    {
        (p_req + sizeof(uint16_t) > p_req_end)) {
        sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_REQ_SYNTAX, SDP_TEXT_BAD_UUID_LIST);
        sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_REQ_SYNTAX, SDP_TEXT_BAD_UUID_LIST);
        return;
        return;
    }
    }
@@ -624,8 +638,8 @@ static void process_service_search_attr_req (tCONN_CB *p_ccb, UINT16 trans_num,


    p_req = sdpu_extract_attr_seq (p_req, param_len, &attr_seq);
    p_req = sdpu_extract_attr_seq (p_req, param_len, &attr_seq);


    if ((!p_req) || (!attr_seq.num_attr))
    if ((!p_req) || (!attr_seq.num_attr) ||
    {
        (p_req + sizeof(uint8_t) > p_req_end)) {
        sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_REQ_SYNTAX, SDP_TEXT_BAD_ATTR_LIST);
        sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_REQ_SYNTAX, SDP_TEXT_BAD_ATTR_LIST);
        return;
        return;
    }
    }
@@ -654,8 +668,8 @@ static void process_service_search_attr_req (tCONN_CB *p_ccb, UINT16 trans_num,
            return;
            return;
        }
        }


        if (*p_req++ != SDP_CONTINUATION_LEN)
        if (*p_req++ != SDP_CONTINUATION_LEN ||
        {
            (p_req + sizeof(uint16_t) > p_req_end)) {
            sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_CONT_STATE, SDP_TEXT_BAD_CONT_LEN);
            sdpu_build_n_send_error (p_ccb, trans_num, SDP_INVALID_CONT_STATE, SDP_TEXT_BAD_CONT_LEN);
            return;
            return;
        }
        }
+32 −11
Original line number Original line Diff line number Diff line
@@ -381,6 +381,9 @@ UINT8 *sdpu_extract_uid_seq (UINT8 *p, UINT16 param_len, tSDP_UUID_SEQ *p_seq)


    /* A UID sequence is composed of a bunch of UIDs. */
    /* A UID sequence is composed of a bunch of UIDs. */


    if (sizeof(descr) > param_len) return (NULL);
    param_len -= sizeof(descr);

    BE_STREAM_TO_UINT8 (descr, p);
    BE_STREAM_TO_UINT8 (descr, p);
    type = descr >> 3;
    type = descr >> 3;
    size = descr & 7;
    size = descr & 7;
@@ -400,19 +403,25 @@ UINT8 *sdpu_extract_uid_seq (UINT8 *p, UINT16 param_len, tSDP_UUID_SEQ *p_seq)
        seq_len = 16;
        seq_len = 16;
        break;
        break;
    case SIZE_IN_NEXT_BYTE:
    case SIZE_IN_NEXT_BYTE:
        if (sizeof(uint8_t) > param_len) return (NULL);
        param_len -= sizeof(uint8_t);
        BE_STREAM_TO_UINT8 (seq_len, p);
        BE_STREAM_TO_UINT8 (seq_len, p);
        break;
        break;
    case SIZE_IN_NEXT_WORD:
    case SIZE_IN_NEXT_WORD:
        if (sizeof(uint16_t) > param_len) return (NULL);
        param_len -= sizeof(uint16_t);
        BE_STREAM_TO_UINT16 (seq_len, p);
        BE_STREAM_TO_UINT16 (seq_len, p);
        break;
        break;
    case SIZE_IN_NEXT_LONG:
    case SIZE_IN_NEXT_LONG:
        if (sizeof(uint32_t) > param_len) return (NULL);
        param_len -= sizeof(uint32_t);
        BE_STREAM_TO_UINT32 (seq_len, p);
        BE_STREAM_TO_UINT32 (seq_len, p);
        break;
        break;
    default:
    default:
        return (NULL);
        return (NULL);
    }
    }


    if (seq_len >= param_len)
    if (seq_len > param_len)
        return (NULL);
        return (NULL);


    p_seq_end = p + seq_len;
    p_seq_end = p + seq_len;
@@ -439,12 +448,15 @@ UINT8 *sdpu_extract_uid_seq (UINT8 *p, UINT16 param_len, tSDP_UUID_SEQ *p_seq)
            uuid_len = 16;
            uuid_len = 16;
            break;
            break;
        case SIZE_IN_NEXT_BYTE:
        case SIZE_IN_NEXT_BYTE:
            if (p + sizeof(uint8_t) > p_seq_end) return NULL;
            BE_STREAM_TO_UINT8 (uuid_len, p);
            BE_STREAM_TO_UINT8 (uuid_len, p);
            break;
            break;
        case SIZE_IN_NEXT_WORD:
        case SIZE_IN_NEXT_WORD:
            if (p + sizeof(uint16_t) > p_seq_end) return NULL;
            BE_STREAM_TO_UINT16 (uuid_len, p);
            BE_STREAM_TO_UINT16 (uuid_len, p);
            break;
            break;
        case SIZE_IN_NEXT_LONG:
        case SIZE_IN_NEXT_LONG:
            if (p + sizeof(uint32_t) > p_seq_end) return NULL;
            BE_STREAM_TO_UINT32 (uuid_len, p);
            BE_STREAM_TO_UINT32 (uuid_len, p);
            break;
            break;
        default:
        default:
@@ -452,8 +464,8 @@ UINT8 *sdpu_extract_uid_seq (UINT8 *p, UINT16 param_len, tSDP_UUID_SEQ *p_seq)
        }
        }


        /* If UUID length is valid, copy it across */
        /* If UUID length is valid, copy it across */
        if ((uuid_len == 2) || (uuid_len == 4) || (uuid_len == 16))
        if (((uuid_len == 2) || (uuid_len == 4) || (uuid_len == 16)) &&
        {
            (p + uuid_len <= p_seq_end)) {
            p_seq->uuid_entry[p_seq->num_uids].len = (UINT16) uuid_len;
            p_seq->uuid_entry[p_seq->num_uids].len = (UINT16) uuid_len;
            BE_STREAM_TO_ARRAY (p, p_seq->uuid_entry[p_seq->num_uids].value, (int)uuid_len);
            BE_STREAM_TO_ARRAY (p, p_seq->uuid_entry[p_seq->num_uids].value, (int)uuid_len);
            p_seq->num_uids++;
            p_seq->num_uids++;
@@ -494,33 +506,39 @@ UINT8 *sdpu_extract_attr_seq (UINT8 *p, UINT16 param_len, tSDP_ATTR_SEQ *p_seq)
    p_seq->num_attr = 0;
    p_seq->num_attr = 0;


    /* Get attribute sequence info */
    /* Get attribute sequence info */
    if (param_len < sizeof(descr)) return NULL;
    param_len -= sizeof(descr);
    BE_STREAM_TO_UINT8 (descr, p);
    BE_STREAM_TO_UINT8 (descr, p);
    type = descr >> 3;
    type = descr >> 3;
    size = descr & 7;
    size = descr & 7;


    if (type != DATA_ELE_SEQ_DESC_TYPE)
    if (type != DATA_ELE_SEQ_DESC_TYPE) return NULL;
        return (p);


    switch (size)
    switch (size)
    {
    {
    case SIZE_IN_NEXT_BYTE:
    case SIZE_IN_NEXT_BYTE:
        if (param_len < sizeof(uint8_t)) return NULL;
        param_len -= sizeof(uint8_t);
        BE_STREAM_TO_UINT8 (list_len, p);
        BE_STREAM_TO_UINT8 (list_len, p);
        break;
        break;


    case SIZE_IN_NEXT_WORD:
    case SIZE_IN_NEXT_WORD:
        if (param_len < sizeof(uint16_t)) return NULL;
        param_len -= sizeof(uint16_t);
        BE_STREAM_TO_UINT16 (list_len, p);
        BE_STREAM_TO_UINT16 (list_len, p);
        break;
        break;


    case SIZE_IN_NEXT_LONG:
    case SIZE_IN_NEXT_LONG:
        if (param_len < sizeof(uint32_t)) return NULL;
        param_len -= sizeof(uint32_t);
        BE_STREAM_TO_UINT32 (list_len, p);
        BE_STREAM_TO_UINT32 (list_len, p);
        break;
        break;


    default:
    default:
        return (p);
        return NULL;
    }
    }


    if (list_len > param_len)
    if (list_len > param_len) return NULL;
        return (p);


    p_end_list = p + list_len;
    p_end_list = p + list_len;


@@ -531,8 +549,7 @@ UINT8 *sdpu_extract_attr_seq (UINT8 *p, UINT16 param_len, tSDP_ATTR_SEQ *p_seq)
        type = descr >> 3;
        type = descr >> 3;
        size = descr & 7;
        size = descr & 7;


        if (type != UINT_DESC_TYPE)
        if (type != UINT_DESC_TYPE) return NULL;
            return (p);


        switch (size)
        switch (size)
        {
        {
@@ -543,20 +560,24 @@ UINT8 *sdpu_extract_attr_seq (UINT8 *p, UINT16 param_len, tSDP_ATTR_SEQ *p_seq)
            attr_len = 4;
            attr_len = 4;
            break;
            break;
        case SIZE_IN_NEXT_BYTE:
        case SIZE_IN_NEXT_BYTE:
            if (p + sizeof(uint8_t) > p_end_list) return NULL;
            BE_STREAM_TO_UINT8 (attr_len, p);
            BE_STREAM_TO_UINT8 (attr_len, p);
            break;
            break;
        case SIZE_IN_NEXT_WORD:
        case SIZE_IN_NEXT_WORD:
            if (p + sizeof(uint16_t) > p_end_list) return NULL;
            BE_STREAM_TO_UINT16 (attr_len, p);
            BE_STREAM_TO_UINT16 (attr_len, p);
            break;
            break;
        case SIZE_IN_NEXT_LONG:
        case SIZE_IN_NEXT_LONG:
            if (p + sizeof(uint32_t) > p_end_list) return NULL;
            BE_STREAM_TO_UINT32 (attr_len, p);
            BE_STREAM_TO_UINT32 (attr_len, p);
            break;
            break;
        default:
        default:
            return (NULL);
            return NULL;
            break;
            break;
        }
        }


        /* Attribute length must be 2-bytes or 4-bytes for a paired entry. */
        /* Attribute length must be 2-bytes or 4-bytes for a paired entry. */
        if (p + attr_len > p_end_list) return NULL;
        if (attr_len == 2)
        if (attr_len == 2)
        {
        {
            BE_STREAM_TO_UINT16 (p_seq->attr_entry[p_seq->num_attr].start, p);
            BE_STREAM_TO_UINT16 (p_seq->attr_entry[p_seq->num_attr].start, p);