void gatt_verify_signature(tGATT_TCB *p_tcb, BT_HDR *p_buf) { UINT16 cmd_len; #if (GATTS_INCLUDED == TRUE) UINT8 op_code; #endif ///GATTS_INCLUDED == TRUE UINT8 *p, *p_orig = (UINT8 *)(p_buf + 1) + p_buf->offset; UINT32 counter; if (p_buf->len < GATT_AUTH_SIGN_LEN + 4) { GATT_TRACE_ERROR("%s: Data length %u less than expected %u", __func__, p_buf->len, GATT_AUTH_SIGN_LEN + 4); return; } cmd_len = p_buf->len - GATT_AUTH_SIGN_LEN + 4; p = p_orig + cmd_len - 4; STREAM_TO_UINT32(counter, p); if (BTM_BleVerifySignature(p_tcb->peer_bda, p_orig, cmd_len, counter, p)) { #if (GATTS_INCLUDED == TRUE) STREAM_TO_UINT8(op_code, p_orig); gatt_server_handle_client_req (p_tcb, op_code, (UINT16)(p_buf->len - 1), p_orig); #endif ///GATTS_INCLUDED == TRUE } else { /* if this is a bad signature, assume from attacker, ignore it */ GATT_TRACE_ERROR("Signature Verification Failed, data ignored"); } return; }
/******************************************************************************* ** ** Function gatt_le_data_ind ** ** Description This function is called when data is received from L2CAP. ** if we are the originator of the connection, we are the ATT ** client, and the received message is queued up for the client. ** ** If we are the destination of the connection, we are the ATT ** server, so the message is passed to the server processing ** function. ** ** Returns void ** *******************************************************************************/ void gatt_data_process (tGATT_TCB *p_tcb, BT_HDR *p_buf) { GATT_TRACE_DEBUG0("gatt_data_process"); UINT8 *p = (UINT8 *)(p_buf + 1) + p_buf->offset; UINT8 op_code, pseudo_op_code; UINT16 msg_len; if (p_buf->len > 0) { msg_len = p_buf->len - 1; STREAM_TO_UINT8(op_code, p); GATT_TRACE_DEBUG1("op_code = %d", op_code); /* remove the two MSBs associated with sign write and write cmd */ pseudo_op_code = op_code & (~GATT_WRITE_CMD_MASK); if (pseudo_op_code < GATT_OP_CODE_MAX) { if (op_code == GATT_SIGN_CMD_WRITE) { GATT_TRACE_DEBUG0("op_code == GATT_SIGN_CMD_WRITE"); gatt_verify_signature(p_tcb, p_buf); return; } else { /* message from client */ if ((op_code % 2) == 0) { GATT_TRACE_DEBUG0("gatt_server_handle_client_req"); gatt_server_handle_client_req (p_tcb, op_code, msg_len, p); } else { GATT_TRACE_DEBUG0("gatt_client_handle_server_rsp"); gatt_client_handle_server_rsp (p_tcb, op_code, msg_len, p); } } } else { GATT_TRACE_ERROR1 ("ATT - Rcvd L2CAP data, unknown cmd: 0x%x", op_code); } } else { GATT_TRACE_ERROR0 ("invalid data length, ignore"); } GKI_freebuf (p_buf); }
/******************************************************************************* ** ** Function gatt_verify_signature ** ** Description This function start to verify the sign data when receiving ** the data from peer device. ** ** Returns ** *******************************************************************************/ void gatt_verify_signature(tGATT_TCB *p_tcb, BT_HDR *p_buf) { UINT16 cmd_len; UINT8 op_code; UINT8 *p, *p_orig = (UINT8 *)(p_buf + 1) + p_buf->offset; UINT32 counter; cmd_len = p_buf->len - GATT_AUTH_SIGN_LEN + 4; p = p_orig + cmd_len - 4; STREAM_TO_UINT32(counter, p); if (BTM_BleVerifySignature(p_tcb->peer_bda, p_orig, cmd_len, counter, p)) { STREAM_TO_UINT8(op_code, p_orig); gatt_server_handle_client_req (p_tcb, op_code, (UINT16)(p_buf->len - 1), p_orig); } else { /* if this is a bad signature, assume from attacker, ignore it */ GATT_TRACE_ERROR("Signature Verification Failed, data ignored"); } return; }