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

Commit 5fce4191 authored by Jakub Pawlowski's avatar Jakub Pawlowski
Browse files

use std::queue for keeping tGATT_CMD_Q

Test: compilation
Change-Id: I4df9a075d27a306067c48c652f5da1fb156c4a9b
parent f9883e43
Loading
Loading
Loading
Loading
+6 −5
Original line number Diff line number Diff line
@@ -434,8 +434,7 @@ tGATT_STATUS attp_cl_send_cmd(tGATT_TCB& tcb, uint16_t clcb_idx,
                              uint8_t cmd_code, BT_HDR* p_cmd) {
  cmd_code &= ~GATT_AUTH_SIGN_MASK;

  if (tcb.pending_cl_req != tcb.next_slot_inq &&
      cmd_code != GATT_HANDLE_VALUE_CONF) {
  if (!tcb.cl_cmd_q.empty() && cmd_code != GATT_HANDLE_VALUE_CONF) {
    gatt_cmd_enq(tcb, clcb_idx, true, cmd_code, p_cmd);
    return GATT_CMD_STARTED;
  }
@@ -447,10 +446,12 @@ tGATT_STATUS attp_cl_send_cmd(tGATT_TCB& tcb, uint16_t clcb_idx,
  }

  /* do not enq cmd if handle value confirmation or set request */
  if (cmd_code != GATT_HANDLE_VALUE_CONF && cmd_code != GATT_CMD_WRITE) {
  if (cmd_code == GATT_HANDLE_VALUE_CONF || cmd_code == GATT_CMD_WRITE) {
    return att_ret;
  }

  gatt_start_rsp_timer(clcb_idx);
  gatt_cmd_enq(tcb, clcb_idx, false, cmd_code, NULL);
  }
  return att_ret;
}

+28 −40
Original line number Diff line number Diff line
@@ -998,54 +998,42 @@ uint8_t gatt_cmd_to_rsp_code(uint8_t cmd_code) {
  }
  return rsp_code;
}
/*******************************************************************************
 *
 * Function         gatt_cl_send_next_cmd_inq
 *
 * Description      Find next command in queue and sent to server
 *
 * Returns          true if command sent, otherwise false.
 *
 ******************************************************************************/

/** Find next command in queue and sent to server */
bool gatt_cl_send_next_cmd_inq(tGATT_TCB& tcb) {
  tGATT_CMD_Q* p_cmd = &tcb.cl_cmd_q[tcb.pending_cl_req];
  bool sent = false;
  uint8_t rsp_code;
  tGATT_CLCB* p_clcb = NULL;
  tGATT_STATUS att_ret = GATT_SUCCESS;
  while (!tcb.cl_cmd_q.empty()) {
    tGATT_CMD_Q& cmd = tcb.cl_cmd_q.front();
    if (!cmd.to_send || cmd.p_cmd == NULL) return false;

  while (!sent && tcb.pending_cl_req != tcb.next_slot_inq && p_cmd->to_send &&
         p_cmd->p_cmd != NULL) {
    att_ret = attp_send_msg_to_l2cap(tcb, p_cmd->p_cmd);
    tGATT_STATUS att_ret = attp_send_msg_to_l2cap(tcb, cmd.p_cmd);
    if (att_ret != GATT_SUCCESS && att_ret != GATT_CONGESTED) {
      GATT_TRACE_ERROR("%s: L2CAP sent error", __func__);
      tcb.cl_cmd_q.pop();
      continue;
    }

    if (att_ret == GATT_SUCCESS || att_ret == GATT_CONGESTED) {
      sent = true;
      p_cmd->to_send = false;
      p_cmd->p_cmd = NULL;
    cmd.to_send = false;
    cmd.p_cmd = NULL;

    if (cmd.op_code == GATT_CMD_WRITE || cmd.op_code == GATT_SIGN_CMD_WRITE) {
      /* dequeue the request if is write command or sign write */
      if (p_cmd->op_code != GATT_CMD_WRITE &&
          p_cmd->op_code != GATT_SIGN_CMD_WRITE) {
        gatt_start_rsp_timer(p_cmd->clcb_idx);
      } else {
        p_clcb = gatt_cmd_dequeue(tcb, &rsp_code);

        /* if no ack needed, keep sending */
        if (att_ret == GATT_SUCCESS) sent = false;
      uint8_t rsp_code;
      tGATT_CLCB* p_clcb = gatt_cmd_dequeue(tcb, &rsp_code);

        p_cmd = &tcb.cl_cmd_q[tcb.pending_cl_req];
      /* send command complete callback here */
      gatt_end_operation(p_clcb, att_ret, NULL);
      }
    } else {
      GATT_TRACE_ERROR("gatt_cl_send_next_cmd_inq: L2CAP sent error");

      memset(p_cmd, 0, sizeof(tGATT_CMD_Q));
      tcb.pending_cl_req++;
      p_cmd = &tcb.cl_cmd_q[tcb.pending_cl_req];
      /* if no ack needed, keep sending */
      if (att_ret == GATT_SUCCESS) continue;

      return true;
    }

    gatt_start_rsp_timer(cmd.clcb_idx);
    return true;
  }
  return sent;

  return false;
}

/*******************************************************************************
@@ -1062,9 +1050,9 @@ bool gatt_cl_send_next_cmd_inq(tGATT_TCB& tcb) {
void gatt_client_handle_server_rsp(tGATT_TCB& tcb, uint8_t op_code,
                                   uint16_t len, uint8_t* p_data) {
  tGATT_CLCB* p_clcb = NULL;
  uint8_t rsp_code;

  if (op_code != GATT_HANDLE_VALUE_IND && op_code != GATT_HANDLE_VALUE_NOTIF) {
    uint8_t rsp_code;
    p_clcb = gatt_cmd_dequeue(tcb, &rsp_code);

    rsp_code = gatt_cmd_to_rsp_code(rsp_code);
+3 −5
Original line number Diff line number Diff line
@@ -289,10 +289,8 @@ typedef struct {
  uint8_t prep_cnt[GATT_MAX_APPS];
  uint8_t ind_count;

  tGATT_CMD_Q cl_cmd_q[GATT_CL_MAX_LCB];
  std::queue<tGATT_CMD_Q> cl_cmd_q;
  alarm_t* ind_ack_timer; /* local app confirm to indication timer */
  uint8_t pending_cl_req;
  uint8_t next_slot_inq; /* index of next available slot in queue */

  bool in_use;
  uint8_t tcb_idx;
@@ -546,9 +544,9 @@ extern void gatt_end_operation(tGATT_CLCB* p_clcb, tGATT_STATUS status,
extern void gatt_act_discovery(tGATT_CLCB* p_clcb);
extern void gatt_act_read(tGATT_CLCB* p_clcb, uint16_t offset);
extern void gatt_act_write(tGATT_CLCB* p_clcb, uint8_t sec_act);
extern bool gatt_cmd_enq(tGATT_TCB& tcb, uint16_t clcb_idx, bool to_send,
                         uint8_t op_code, BT_HDR* p_buf);
extern tGATT_CLCB* gatt_cmd_dequeue(tGATT_TCB& tcb, uint8_t* p_opcode);
extern void gatt_cmd_enq(tGATT_TCB& tcb, uint16_t clcb_idx, bool to_send,
                         uint8_t op_code, BT_HDR* p_buf);
extern void gatt_client_handle_server_rsp(tGATT_TCB& tcb, uint8_t op_code,
                                          uint16_t len, uint8_t* p_data);
extern void gatt_send_queue_write_cancel(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
+16 −40
Original line number Diff line number Diff line
@@ -1307,55 +1307,31 @@ bool gatt_find_app_hold_link(tGATT_TCB* p_tcb, uint8_t start_idx,
  return found;
}

/*******************************************************************************
 *
 * Function         gatt_cmd_enq
 *
 * Description      Enqueue this command.
 *
 * Returns          None.
 *
 ******************************************************************************/
bool gatt_cmd_enq(tGATT_TCB& tcb, uint16_t clcb_idx, bool to_send,
/** Enqueue this command */
void gatt_cmd_enq(tGATT_TCB& tcb, uint16_t clcb_idx, bool to_send,
                  uint8_t op_code, BT_HDR* p_buf) {
  tGATT_CMD_Q* p_cmd = &tcb.cl_cmd_q[tcb.next_slot_inq];

  p_cmd->to_send = to_send; /* waiting to be sent */
  p_cmd->op_code = op_code;
  p_cmd->p_cmd = p_buf;
  p_cmd->clcb_idx = clcb_idx;
  tGATT_CMD_Q cmd;
  cmd.to_send = to_send; /* waiting to be sent */
  cmd.op_code = op_code;
  cmd.p_cmd = p_buf;
  cmd.clcb_idx = clcb_idx;

  if (!to_send) {
    tcb.pending_cl_req = tcb.next_slot_inq;
    // TODO: WTF why do we clear the queue here ?!
    tcb.cl_cmd_q = std::queue<tGATT_CMD_Q>();
  }

  tcb.next_slot_inq++;
  tcb.next_slot_inq %= GATT_CL_MAX_LCB;

  return true;
  tcb.cl_cmd_q.push(cmd);
}

/*******************************************************************************
 *
 * Function         gatt_cmd_dequeue
 *
 * Description      dequeue the command in the client CCB command queue.
 *
 * Returns          total number of clcb found.
 *
 ******************************************************************************/
/** dequeue the command in the client CCB command queue */
tGATT_CLCB* gatt_cmd_dequeue(tGATT_TCB& tcb, uint8_t* p_op_code) {
  tGATT_CMD_Q* p_cmd = &tcb.cl_cmd_q[tcb.pending_cl_req];
  tGATT_CLCB* p_clcb = NULL;

  if (tcb.pending_cl_req != tcb.next_slot_inq) {
    p_clcb = &gatt_cb.clcb[p_cmd->clcb_idx];
  if (tcb.cl_cmd_q.empty()) return nullptr;

    *p_op_code = p_cmd->op_code;

    tcb.pending_cl_req++;
    tcb.pending_cl_req %= GATT_CL_MAX_LCB;
  }
  tGATT_CMD_Q cmd = tcb.cl_cmd_q.front();
  tGATT_CLCB* p_clcb = &gatt_cb.clcb[cmd.clcb_idx];
  *p_op_code = cmd.op_code;
  tcb.cl_cmd_q.pop();

  return p_clcb;
}