wireless/bluetooth: Adds most of the logic to get the Tx path working. Still missing the logic to recover the Bluetooth connection structure given the destination address in the socket address.
This commit is contained in:
parent
29a4a80f8c
commit
7e05d5e9c7
@ -148,7 +148,7 @@ static FAR struct bt_buf_s *btuart_evt_recv(FAR struct btuart_upperhalf_s *upper
|
||||
|
||||
*remaining = hdr.len;
|
||||
|
||||
buf = bt_buf_alloc(BT_EVT, 0);
|
||||
buf = bt_buf_alloc(BT_EVT, NULL, 0);
|
||||
if (buf != NULL)
|
||||
{
|
||||
memcpy(bt_buf_extend(buf, sizeof(struct bt_hci_evt_hdr_s)), &hdr,
|
||||
@ -181,7 +181,7 @@ static FAR struct bt_buf_s *btuart_acl_recv(FAR struct btuart_upperhalf_s *upper
|
||||
return NULL;
|
||||
}
|
||||
|
||||
buf = bt_buf_alloc(BT_ACL_IN, 0);
|
||||
buf = bt_buf_alloc(BT_ACL_IN, NULL, 0);
|
||||
if (buf)
|
||||
{
|
||||
memcpy(bt_buf_extend(buf, sizeof(struct bt_hci_acl_hdr_s)), &hdr,
|
||||
|
@ -52,7 +52,7 @@
|
||||
|
||||
#warning REVISIT
|
||||
|
||||
#define BLUETOOTH_HDRLEN 0
|
||||
#define BLUETOOTH_HDRLEN 8 /* Size of L2CAP header */
|
||||
#define BLUETOOTH_ADDRSIZE 6
|
||||
#define BLUETOOTH_ADDRCOPY(d,s) memcpy((d),(s),BLUETOOTH_ADDRSIZE)
|
||||
#define BLUETOOTH_ADDRCMP(a,b) (memcmp((a),(b),BLUETOOTH_ADDRSIZE) == 0)
|
||||
|
@ -103,6 +103,8 @@ struct bt_buf_acl_data_s
|
||||
uint16_t handle;
|
||||
};
|
||||
|
||||
struct iob_s; /* Forward reference */
|
||||
|
||||
struct bt_buf_s
|
||||
{
|
||||
FAR struct bt_buf_s *flink;
|
||||
@ -147,6 +149,8 @@ struct bt_buf_s
|
||||
*
|
||||
* Input Parameters:
|
||||
* type - Buffer type.
|
||||
* iob - The raw I/O buffer. If NULL, then bt_buf_alloc will
|
||||
* allocate.
|
||||
* reserve_head - How much headroom to reserve.
|
||||
*
|
||||
* Returned Value:
|
||||
@ -156,7 +160,10 @@ struct bt_buf_s
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
struct iob_s; /* Forward reference */
|
||||
|
||||
FAR struct bt_buf_s *bt_buf_alloc(enum bt_buf_type_e type,
|
||||
FAR struct iob_s *iob,
|
||||
size_t reserve_head);
|
||||
|
||||
/****************************************************************************
|
||||
|
@ -120,7 +120,6 @@ config BLUETOOTH_BUFFER_PREALLOC
|
||||
config BLUETOOTH_BUFFER_IRQRESERVE
|
||||
int "Reserved pre-allocated primitive structures"
|
||||
default 0
|
||||
depends on EXPERIMENTAL
|
||||
---help---
|
||||
If buffer structures can be allocated from interrupt handlers, then
|
||||
this specifies the number of pre-allocated structures that are
|
||||
@ -139,9 +138,9 @@ config BLUETOOTH_BUFFER_IRQRESERVE
|
||||
dynamically allocate the buffer with an additional cost in
|
||||
performance.
|
||||
|
||||
NOTE: Currently marked as experimental and with a default of zero
|
||||
because there are no interrupt level allocations performed by the
|
||||
current Bluetooth stack.
|
||||
NOTE: The Bluetooth stack never allocates buffers from the
|
||||
interrupt level. This setting only needs to be non-zero if your
|
||||
low-level Bluetooth driver needs to do such allocations.
|
||||
|
||||
menu "Kernel Thread Configuration"
|
||||
|
||||
|
@ -63,11 +63,6 @@
|
||||
* Pre-processor Definitions
|
||||
****************************************************************************/
|
||||
|
||||
/* NOTE: The CONFIG_BLUETOOTH_BUFFER_IRQRESERVE options is marked as marked
|
||||
* 'experimental' and with the default 0 zero because there are no interrupt
|
||||
* level allocations performed by the current Bluetooth code.
|
||||
*/
|
||||
|
||||
#if !defined(CONFIG_BLUETOOTH_BUFFER_PREALLOC) || \
|
||||
CONFIG_BLUETOOTH_BUFFER_PREALLOC < 1
|
||||
# undef CONFIG_BLUETOOTH_BUFFER_PREALLOC
|
||||
@ -220,6 +215,8 @@ void bt_buf_initialize(void)
|
||||
*
|
||||
* Input Parameters:
|
||||
* type - Buffer type.
|
||||
* iob - The raw I/O buffer. If NULL, then bt_buf_alloc will
|
||||
* allocate.
|
||||
* reserve_head - How much headroom to reserve.
|
||||
*
|
||||
* Returned Value:
|
||||
@ -229,8 +226,9 @@ void bt_buf_initialize(void)
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
FAR struct bt_buf_s *bt_buf_alloc(enum bt_buf_type_e type, size_t
|
||||
reserve_head)
|
||||
FAR struct bt_buf_s *bt_buf_alloc(enum bt_buf_type_e type,
|
||||
FAR struct iob_s *iob,
|
||||
size_t reserve_head)
|
||||
{
|
||||
FAR struct bt_buf_s *buf;
|
||||
irqstate_t flags;
|
||||
|
@ -588,7 +588,8 @@ void bt_conn_set_state(FAR struct bt_conn_s *conn,
|
||||
|
||||
if (old_state == BT_CONN_CONNECTED || old_state == BT_CONN_DISCONNECT)
|
||||
{
|
||||
bt_queue_send(conn->tx_queue, bt_buf_alloc(BT_DUMMY, 0), BT_NORMAL_PRIO);
|
||||
bt_queue_send(conn->tx_queue, bt_buf_alloc(BT_DUMMY, NULL, 0),
|
||||
BT_NORMAL_PRIO);
|
||||
}
|
||||
|
||||
/* Release the reference we took for the very first state transition. */
|
||||
@ -618,7 +619,7 @@ void bt_conn_set_state(FAR struct bt_conn_s *conn,
|
||||
*
|
||||
* Returned Value:
|
||||
* A reference to the connection state instance is returned on success.
|
||||
* NULL is returned if the connection is not found. On succes, the
|
||||
* NULL is returned if the connection is not found. On success, the
|
||||
* caller gets a new reference to the connection object which must be
|
||||
* released with bt_conn_release() once done using the connection.
|
||||
*
|
||||
@ -658,7 +659,7 @@ FAR struct bt_conn_s *bt_conn_lookup_handle(uint16_t handle)
|
||||
*
|
||||
* Returned Value:
|
||||
* A reference to the connection state instance is returned on success.
|
||||
* NULL is returned if the connection is not found. On succes, the
|
||||
* NULL is returned if the connection is not found. On success, the
|
||||
* caller gets a new reference to the connection object which must be
|
||||
* released with bt_conn_release() once done using the connection.
|
||||
*
|
||||
@ -692,7 +693,7 @@ FAR struct bt_conn_s *bt_conn_lookup_addr_le(FAR const bt_addr_le_t * peer)
|
||||
*
|
||||
* Returned Value:
|
||||
* A reference to the connection state instance is returned on success.
|
||||
* NULL is returned if the connection is not found. On succes, the
|
||||
* NULL is returned if the connection is not found. On success, the
|
||||
* caller gets a new reference to the connection object which must be
|
||||
* released with bt_conn_release() once done using the connection.
|
||||
*
|
||||
|
@ -196,7 +196,7 @@ void bt_conn_set_state(FAR struct bt_conn_s *conn, enum bt_conn_state_e state);
|
||||
*
|
||||
* Returned Value:
|
||||
* A reference to the connection state instance is returned on success.
|
||||
* NULL is returned if the connection is not found. On succes, the
|
||||
* NULL is returned if the connection is not found. On success, the
|
||||
* caller gets a new reference to the connection object which must be
|
||||
* released with bt_conn_release() once done using the connection.
|
||||
*
|
||||
@ -215,7 +215,7 @@ FAR struct bt_conn_s *bt_conn_lookup_handle(uint16_t handle);
|
||||
*
|
||||
* Returned Value:
|
||||
* A reference to the connection state instance is returned on success.
|
||||
* NULL is returned if the connection is not found. On succes, the
|
||||
* NULL is returned if the connection is not found. On success, the
|
||||
* caller gets a new reference to the connection object which must be
|
||||
* released with bt_conn_release() once done using the connection.
|
||||
*
|
||||
@ -236,7 +236,7 @@ FAR struct bt_conn_s *bt_conn_lookup_addr_le(const bt_addr_le_t *peer);
|
||||
*
|
||||
* Returned Value:
|
||||
* A reference to the connection state instance is returned on success.
|
||||
* NULL is returned if the connection is not found. On succes, the
|
||||
* NULL is returned if the connection is not found. On success, the
|
||||
* caller gets a new reference to the connection object which must be
|
||||
* released with bt_conn_release() once done using the connection.
|
||||
*
|
||||
|
@ -1387,7 +1387,7 @@ FAR struct bt_buf_s *bt_hci_cmd_create(uint16_t opcode, uint8_t param_len)
|
||||
|
||||
wlinfo("opcode %x param_len %u\n", opcode, param_len);
|
||||
|
||||
buf = bt_buf_alloc(BT_CMD, g_btdev.dev->head_reserve);
|
||||
buf = bt_buf_alloc(BT_CMD, NULL, g_btdev.dev->head_reserve);
|
||||
if (!buf)
|
||||
{
|
||||
wlerr("ERROR: Cannot get free buffer\n");
|
||||
|
@ -182,7 +182,7 @@ struct bt_buf_s *bt_l2cap_create_pdu(FAR struct bt_conn_s *conn)
|
||||
size_t head_reserve = sizeof(struct bt_l2cap_hdr_s) +
|
||||
sizeof(struct bt_hci_acl_hdr_s) + g_btdev.dev->head_reserve;
|
||||
|
||||
return bt_buf_alloc(BT_ACL_OUT, head_reserve);
|
||||
return bt_buf_alloc(BT_ACL_OUT, NULL, head_reserve);
|
||||
}
|
||||
|
||||
void bt_l2cap_send(FAR struct bt_conn_s *conn, uint16_t cid,
|
||||
@ -413,7 +413,7 @@ void bt_l2cap_receive(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
return;
|
||||
}
|
||||
|
||||
chan->receive(conn, buf, chan->context, chan->cid);
|
||||
chan->receive(conn, buf, chan->context, cid);
|
||||
}
|
||||
|
||||
void bt_l2cap_update_conn_param(FAR struct bt_conn_s *conn)
|
||||
|
@ -861,7 +861,7 @@ static int btnet_rmmac(FAR struct net_driver_s *dev, FAR const uint8_t *mac)
|
||||
static int btnet_get_mhrlen(FAR struct radio_driver_s *netdev,
|
||||
FAR const void *meta)
|
||||
{
|
||||
return BLUETOOTH_HDRLEN;
|
||||
return sizeof(struct bt_l2cap_hdr_s);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
@ -885,16 +885,24 @@ static int btnet_get_mhrlen(FAR struct radio_driver_s *netdev,
|
||||
static int btnet_req_data(FAR struct radio_driver_s *netdev,
|
||||
FAR const void *meta, FAR struct iob_s *framelist)
|
||||
{
|
||||
FAR struct btnet_driver_s *priv =
|
||||
(FAR struct btnet_driver_s *)netdev;
|
||||
FAR const struct bluetooth_frame_meta_s *pktmeta =
|
||||
(FAR const struct bluetooth_frame_meta_s *)meta;
|
||||
FAR struct btnet_driver_s *priv;
|
||||
FAR struct bluetooth_frame_meta_s *btmeta;
|
||||
FAR struct bt_conn_s *conn;
|
||||
FAR struct bt_buf_s *buf;
|
||||
FAR struct iob_s *iob;
|
||||
int ret;
|
||||
|
||||
wlinfo("Received framelist\n");
|
||||
DEBUGASSERT(priv != NULL && meta != NULL && framelist != NULL);
|
||||
|
||||
DEBUGASSERT(priv != NULL && pktmeta != NULL && framelist != NULL);
|
||||
priv = (FAR struct btnet_driver_s *)netdev;
|
||||
btmeta = (FAR struct bluetooth_frame_meta_s *)meta;
|
||||
|
||||
/* Create a connection structure for this peer if one does not already
|
||||
* exist.
|
||||
*
|
||||
* REVISIT: Can we do a handle lookup? ... That would be faster.
|
||||
*/
|
||||
#warning Missing logic
|
||||
|
||||
/* Add the incoming list of frames to the MAC's outgoing queue */
|
||||
|
||||
@ -909,31 +917,18 @@ static int btnet_req_data(FAR struct radio_driver_s *netdev,
|
||||
framelist = iob->io_flink;
|
||||
iob->io_flink = NULL;
|
||||
|
||||
/* Transfer the frame to the MAC. */
|
||||
/* Allocate a buffer to contain the IOB */
|
||||
|
||||
do
|
||||
buf = bt_buf_alloc(BT_ACL_OUT, iob, sizeof(struct bt_l2cap_hdr_s));
|
||||
if (buf == NULL)
|
||||
{
|
||||
ret = btnet_req_data(netdev, pktmeta, iob);
|
||||
}
|
||||
while (ret == -EINTR);
|
||||
|
||||
if (ret < 0)
|
||||
{
|
||||
wlerr("ERROR: btnet_req_data failed: %d\n", ret);
|
||||
|
||||
iob_free(iob);
|
||||
for (iob = framelist; iob != NULL; iob = framelist)
|
||||
{
|
||||
/* Remove the IOB from the queue and free */
|
||||
|
||||
framelist = iob->io_flink;
|
||||
iob_free(iob);
|
||||
}
|
||||
|
||||
NETDEV_TXERRORS(&priv->bd_dev.r_dev);
|
||||
return ret;
|
||||
wlerr("ERROR: Failed to allocate buffer container\n");
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
/* Transfer the frame to the Bluetooth stack. */
|
||||
|
||||
bt_l2cap_send(conn, (uint16_t)btmeta->bm_channel, buf);
|
||||
NETDEV_TXDONE(&priv->bd_dev.r_dev);
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user