mirror of
https://github.com/apache/nuttx.git
synced 2026-05-23 06:39:01 +08:00
Squashed commit of the following:
wireless/bluetooth: This completes the basic logic path that gets frames from the Bluetooth stack and into the network layer.
wireless/bluetooth: Fleshes out some of the network packet receive logic.
wireless/bluetooth: Replace buffer allocated with primitive allocator from ieee 802.15.4.
wireless/ieee802154: Fix a few typos.
wireless/bluetooth: More renaming in preparation for some real work.
wireless/bluetooth: Some trivial renaming; update comments
This commit is contained in:
@@ -148,10 +148,10 @@ static FAR struct bt_buf_s *btuart_evt_recv(FAR struct btuart_upperhalf_s *upper
|
||||
|
||||
*remaining = hdr.len;
|
||||
|
||||
buf = bt_buf_get(BT_EVT, 0);
|
||||
buf = bt_buf_alloc(BT_EVT, 0);
|
||||
if (buf != NULL)
|
||||
{
|
||||
memcpy(bt_buf_add(buf, sizeof(struct bt_hci_evt_hdr_s)), &hdr,
|
||||
memcpy(bt_buf_extend(buf, sizeof(struct bt_hci_evt_hdr_s)), &hdr,
|
||||
sizeof(struct bt_hci_evt_hdr_s));
|
||||
}
|
||||
else
|
||||
@@ -181,10 +181,10 @@ static FAR struct bt_buf_s *btuart_acl_recv(FAR struct btuart_upperhalf_s *upper
|
||||
return NULL;
|
||||
}
|
||||
|
||||
buf = bt_buf_get(BT_ACL_IN, 0);
|
||||
buf = bt_buf_alloc(BT_ACL_IN, 0);
|
||||
if (buf)
|
||||
{
|
||||
memcpy(bt_buf_add(buf, sizeof(struct bt_hci_acl_hdr_s)), &hdr,
|
||||
memcpy(bt_buf_extend(buf, sizeof(struct bt_hci_acl_hdr_s)), &hdr,
|
||||
sizeof(struct bt_hci_acl_hdr_s));
|
||||
}
|
||||
else
|
||||
@@ -268,14 +268,14 @@ static void btuart_interrupt(FAR const struct btuart_lowerhalf_s *lower,
|
||||
|
||||
/* Pass buffer to the stack */
|
||||
|
||||
bt_input(buf);
|
||||
bt_hci_receive(buf);
|
||||
buf = NULL;
|
||||
}
|
||||
|
||||
return;
|
||||
|
||||
failed:
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
remaining = 0;
|
||||
buf = NULL;
|
||||
return;
|
||||
@@ -299,7 +299,7 @@ static int btuart_send(FAR const struct bt_driver_s *dev,
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
type = bt_buf_push(buf, 1);
|
||||
type = bt_buf_provide(buf, 1);
|
||||
|
||||
switch (buf->type)
|
||||
{
|
||||
|
||||
@@ -99,7 +99,7 @@
|
||||
#define BTPROTO_HIDP 6
|
||||
#define BTPROTO_AVDTP 7
|
||||
|
||||
/* HCI socket options:
|
||||
/* HCI socket options (SOL_HCI, see include/sys/socket.h):
|
||||
*
|
||||
* SO_HCI_EVT_FILTER
|
||||
* Controls which events will be received at the socket. By default,
|
||||
@@ -116,7 +116,7 @@
|
||||
#define SO_HCI_PKT_FILTER (__SO_PROTOCOL + 1)
|
||||
#define SO_HCI_DIRECTION (__SO_PROTOCOL + 2)
|
||||
|
||||
/* L2CAP socket options:
|
||||
/* L2CAP socket options (SOL_L2CAP, see include/sys/socket.h):
|
||||
|
||||
* SO_L2CAP_IMTU [uint16_t]
|
||||
* Incoming MTU
|
||||
@@ -145,7 +145,7 @@
|
||||
# define L2CAP_LM_ENCRYPT (1 << 1)
|
||||
# define L2CAP_LM_SECURE (1 << 2)
|
||||
|
||||
/* RFCOMM socket options:
|
||||
/* RFCOMM socket options (SOL_RFCOMM, see include/sys/socket.h):
|
||||
*
|
||||
* SO_RFCOMM_MTU [uint16_t]
|
||||
* Maximum Frame Size to use for this link.
|
||||
@@ -171,7 +171,7 @@
|
||||
# define RFCOMM_LM_ENCRYPT (1 << 1)
|
||||
# define RFCOMM_LM_SECURE (1 << 2)
|
||||
|
||||
/* SCO socket options:
|
||||
/* SCO socket options (SOL_SCO, see include/sys/socket.h):
|
||||
*
|
||||
* SO_SCO_MTU [uint16_t]
|
||||
* Maximum packet size for use on this link. This is read-only and will
|
||||
@@ -184,6 +184,78 @@
|
||||
#define SO_SCO_MTU (__SO_PROTOCOL + 8)
|
||||
#define SO_SCO_HANDLE (__SO_PROTOCOL + 9)
|
||||
|
||||
/* The CID name space for the ACL-U, ASB-C, and AMP-U logical links is as
|
||||
* follows:
|
||||
*/
|
||||
|
||||
#define BT_CID_NULL 0x0000 /* Null identifier */
|
||||
#define BT_CID_L2CAP 0x0001 /* L2CAP Signaling channel */
|
||||
#define BT_CID_CONNECTIONLESS 0x0002 /* Connectionless channel */
|
||||
#define BT_CID_AMP 0x0003 /* AMP Manager Protocol */
|
||||
/* 0x0004-0x0006 Reserved for future
|
||||
* use */
|
||||
#define BT_CID_BREDR 0x0007 /* BR/EDR Security Manager */
|
||||
/* 0x0008-0x003e Reserved for future
|
||||
* use */
|
||||
#define BT_CID_AMPTEST 0x003f /* AMP Test Manager */
|
||||
/* 0x0040-0xffff Dynamically
|
||||
* allocated */
|
||||
|
||||
/* The CID name space for the LE-U logical link is as follows:
|
||||
*
|
||||
* NOTE: 0x0004, 0x0005, and 0x0006 are used internally by ATT, L2CAP, and
|
||||
* and SMP. These are unavailable for use use in socket connection.
|
||||
*/
|
||||
|
||||
#define BT_LE_CID_NULL 0x0000 /* Null identifier */
|
||||
/* 0x0001-0x0003 Reserved for future
|
||||
* use */
|
||||
#define BT_LE_CID_ATT 0x0004 /* Attribute Protocol */
|
||||
#define BT_LE_CID_L2CAP 0x0005 /* Low Energy L2CAP Signaling channel */
|
||||
#define BT_LE_CID_SMP 0x0006 /* Security Manager Protocol
|
||||
/* 0x0007-0x001f Reserved for future
|
||||
/* 0x0020-0x003e Assigned Numbers
|
||||
/* 0x003f Reserved for future use */
|
||||
/* 0x0040-0x007f Dynamically allocated
|
||||
* using the L2CAP LE credit based
|
||||
* connection mechanism
|
||||
/* Others reserved for future use */
|
||||
|
||||
/* Protocol and Service Multiplexers (PSMs) */
|
||||
|
||||
#define BT_PSM_SDP 0x0001 /* Bluetooth Service Discovery
|
||||
* Protocol (SDP), Bluetooth SIG */
|
||||
#define BT_PSM_RFCOMM 0x0003 /* RFCOMM with TS 07.10, Bluetooth
|
||||
* SIG */
|
||||
#define BT_PSM_TCS_BIN 0x0005 /* Bluetooth Telephony Control
|
||||
* Specification / TCS Binary,
|
||||
* Bluetooth SIG */
|
||||
#define BT_PSM_TCS_BIN_CORDLESS 0x0007 /* Bluetooth Telephony Control
|
||||
* Specification / TCS Binary,
|
||||
* Bluetooth SIG */
|
||||
#define BT_PSM_BNEP 0x000f /* Bluetooth Network Encapsulation
|
||||
* Protocol, Bluetooth SIG */
|
||||
#define BT_PSM_HID_CTRL 0x0011 /* Human Interface Device, Bluetooth
|
||||
* SIG */
|
||||
#define BT_PSM_HID_INT 0x0013 /* Human Interface Device, Bluetooth
|
||||
* SIG */
|
||||
#define BT_PSM_UPnP 0x0015 /* [ESDP] , Bluetooth SIG */
|
||||
#define BT_PSM_AVCTP 0x0017 /* Audio/Video Control Transport
|
||||
* Protocol, Bluetooth SIG */
|
||||
#define BT_PSM_AVDTP 0x0019 /* Audio/Video Distribution Transport
|
||||
* Protocol, Bluetooth SIG */
|
||||
#define BT_PSM_AVCTP_BROWSING 0x001b /* Audio/Video Remote Control
|
||||
* Profile, Bluetooth SIG */
|
||||
#define BT_PSM_UDI_CPLANE 0x001d /* Unrestricted Digital Information
|
||||
* Profile [UDI], Bluetooth SIG */
|
||||
#define BT_PSM_ATT 0x001f /* Bluetooth Core Specification */
|
||||
#define BT_PSM_3DSP 0x0021 /* 3D Synchronization Profile,
|
||||
* Bluetooth SIG. */
|
||||
#define BT_PSM_LE_PSM_IPSP 0x0023 /* Internet Protocol Support Profile
|
||||
* (IPSP), Bluetooth SIG */
|
||||
#define BT_PSM_OTS 0x0025 /* Object Transfer Service (OTS),
|
||||
* Bluetooth SIG */
|
||||
|
||||
/****************************************************************************
|
||||
* Public Type Definitions
|
||||
****************************************************************************/
|
||||
@@ -204,9 +276,9 @@
|
||||
|
||||
struct sockaddr_bt_s
|
||||
{
|
||||
sa_family_t bt_family;
|
||||
bt_addr_t bt_bdaddr;
|
||||
uint8_t bt_channel;
|
||||
sa_family_t bt_family; /* Must be AF_BLUETOOTH */
|
||||
bt_addr_t bt_bdaddr; /* 6-byte Bluetooth address */
|
||||
uint8_t bt_channel; /* Channel identifier (CID) */
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/****************************************************************************
|
||||
* wireless/bluetooth/bt_att.h
|
||||
* include/nuttx/wireless/bt_buf.h
|
||||
* Bluetooth buffer management.
|
||||
*
|
||||
* Copyright (C) 2018 Gregory Nutt. All rights reserved.
|
||||
@@ -105,7 +105,8 @@ struct bt_buf_acl_data_s
|
||||
|
||||
struct bt_buf_s
|
||||
{
|
||||
FAR struct iob_s *iob; /* IOB container of the buffer */
|
||||
FAR struct bt_buf_s *flink;
|
||||
|
||||
union
|
||||
{
|
||||
struct bt_buf_hci_data_s hci;
|
||||
@@ -114,12 +115,13 @@ struct bt_buf_s
|
||||
|
||||
FAR uint8_t *data; /* Start of data in the buffer */
|
||||
uint8_t len; /* Length of data in the buffer */
|
||||
uint8_t ref : 5; /* Reference count */
|
||||
uint8_t type : 3; /* Type of data contained in the buffer */
|
||||
uint8_t pool; /* Memory pool */
|
||||
uint8_t ref; /* Reference count */
|
||||
uint8_t type; /* Type of data contained in the buffer */
|
||||
|
||||
/* The full available buffer. */
|
||||
|
||||
uint8_t buf[BT_BUF_MAX_DATA];
|
||||
FAR struct iob_s *frame;
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
@@ -127,43 +129,55 @@ struct bt_buf_s
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_get
|
||||
* Name: bt_buf_alloc
|
||||
*
|
||||
* Description:
|
||||
* Get buffer from the available buffers pool with specified type and
|
||||
* reserved headroom.
|
||||
* The bt_buf_alloc function will get a free buffer for use by the
|
||||
* Bluetooth stack with specified type and reserved headroom. The
|
||||
* reference count is initially set to one.
|
||||
*
|
||||
* Interrupt handling logic will first attempt to allocate from the
|
||||
* g_buf_free list. If that list is empty, it will attempt to allocate
|
||||
* from its reserve, g_buf_free_irq. If that list is empty, then the
|
||||
* allocation fails (NULL is returned).
|
||||
*
|
||||
* Non-interrupt handler logic will attempt to allocate from g_buf_free
|
||||
* list. If that the list is empty, then the buffer structure will be
|
||||
* allocated from the dynamic memory pool with some performance hit.
|
||||
*
|
||||
* Input Parameters:
|
||||
* type - Buffer type.
|
||||
* reserve_head - How much headroom to reserve.
|
||||
*
|
||||
* Returned Value:
|
||||
* New buffer or NULL if out of buffers.
|
||||
*
|
||||
* WARNING: If there are no available buffers and the function is
|
||||
* called from a task or thread the call will block until a buffer
|
||||
* becomes available in the pool.
|
||||
* A reference to the allocated buffer structure. All user fields in this
|
||||
* structure have been zeroed. On a failure to allocate, NULL is
|
||||
* returned.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
FAR struct bt_buf_s *bt_buf_get(enum bt_buf_type_e type, size_t reserve_head);
|
||||
FAR struct bt_buf_s *bt_buf_alloc(enum bt_buf_type_e type,
|
||||
size_t reserve_head);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_put
|
||||
* Name: bt_buf_release
|
||||
*
|
||||
* Description:
|
||||
* Decrements the reference count of a buffer and puts it back into the
|
||||
* pool if the count reaches zero.
|
||||
* Decrements the reference count of a buffer and returns the buffer to the
|
||||
* memory pool if the count decrements zero.
|
||||
*
|
||||
* Input Parameters:
|
||||
* buf - Buffer.
|
||||
*
|
||||
* Returned Value:
|
||||
* None
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void bt_buf_put(FAR struct bt_buf_s *buf);
|
||||
void bt_buf_release(FAR struct bt_buf_s *buf);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_hold
|
||||
* Name: bt_buf_addref
|
||||
*
|
||||
* Description:
|
||||
* Increment the reference count of a buffer.
|
||||
@@ -173,14 +187,14 @@ void bt_buf_put(FAR struct bt_buf_s *buf);
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
FAR struct bt_buf_s *bt_buf_hold(FAR struct bt_buf_s *buf);
|
||||
FAR struct bt_buf_s *bt_buf_addref(FAR struct bt_buf_s *buf);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_add
|
||||
* Name: bt_buf_extend
|
||||
*
|
||||
* Description:
|
||||
* Increments the data length of a buffer to account for more data
|
||||
* at the end.
|
||||
* at the end of the buffer.
|
||||
*
|
||||
* Input Parameters:
|
||||
* buf - Buffer to update.
|
||||
@@ -191,10 +205,10 @@ FAR struct bt_buf_s *bt_buf_hold(FAR struct bt_buf_s *buf);
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
FAR void *bt_buf_add(FAR struct bt_buf_s *buf, size_t len);
|
||||
FAR void *bt_buf_extend(FAR struct bt_buf_s *buf, size_t len);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_add_le16
|
||||
* Name: bt_buf_put_le16
|
||||
*
|
||||
* Description:
|
||||
* Adds 16-bit value in little endian format at the end of buffer.
|
||||
@@ -210,10 +224,10 @@ FAR void *bt_buf_add(FAR struct bt_buf_s *buf, size_t len);
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void bt_buf_add_le16(FAR struct bt_buf_s *buf, uint16_t value);
|
||||
void bt_buf_put_le16(FAR struct bt_buf_s *buf, uint16_t value);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_push
|
||||
* Name: bt_buf_provide
|
||||
*
|
||||
* Description:
|
||||
* Modifies the data pointer and buffer length to account for more data
|
||||
@@ -228,10 +242,10 @@ void bt_buf_add_le16(FAR struct bt_buf_s *buf, uint16_t value);
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
FAR void *bt_buf_push(FAR struct bt_buf_s *buf, size_t len);
|
||||
FAR void *bt_buf_provide(FAR struct bt_buf_s *buf, size_t len);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_pull
|
||||
* Name: bt_buf_consume
|
||||
*
|
||||
* Description:
|
||||
* Removes data from the beginning of the buffer by modifying the data
|
||||
@@ -245,10 +259,10 @@ FAR void *bt_buf_push(FAR struct bt_buf_s *buf, size_t len);
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
FAR void *bt_buf_pull(FAR struct bt_buf_s *buf, size_t len);
|
||||
FAR void *bt_buf_consume(FAR struct bt_buf_s *buf, size_t len);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_pull_le16
|
||||
* Name: bt_buf_get_le16
|
||||
*
|
||||
* Description:
|
||||
* Same idea as with bt_buf_pull(), but a helper for operating on
|
||||
@@ -262,7 +276,7 @@ FAR void *bt_buf_pull(FAR struct bt_buf_s *buf, size_t len);
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
uint16_t bt_buf_pull_le16(FAR struct bt_buf_s *buf);
|
||||
uint16_t bt_buf_get_le16(FAR struct bt_buf_s *buf);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_tailroom
|
||||
@@ -306,22 +320,4 @@ size_t bt_buf_headroom(FAR struct bt_buf_s *buf);
|
||||
|
||||
#define bt_buf_tail(buf) ((buf)->data + (buf)->len)
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_init
|
||||
*
|
||||
* Description:
|
||||
* Initialize the buffers with specified amount of incoming and outgoing
|
||||
* ACL buffers. The HCI command and event buffers will be allocated from
|
||||
* whatever is left over.
|
||||
*
|
||||
* Input Parameters:
|
||||
* None.
|
||||
*
|
||||
* Returned Value:
|
||||
* Zero on success or (negative) error code on failure.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int bt_buf_init(void);
|
||||
|
||||
#endif /* __INCLUDE_NUTTX_WIRELESS_BT_BUF_H */
|
||||
|
||||
@@ -111,7 +111,7 @@ int bt_driver_register(FAR const struct bt_driver_s *dev);
|
||||
void bt_driver_unregister(FAR const struct bt_driver_s *dev);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_input
|
||||
* Name: bt_hci_receive
|
||||
*
|
||||
* Description:
|
||||
* Called by the Bluetooth low-level driver when new data is received from
|
||||
@@ -126,6 +126,6 @@ void bt_driver_unregister(FAR const struct bt_driver_s *dev);
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void bt_input(FAR struct bt_buf_s *buf);
|
||||
void bt_hci_receive(FAR struct bt_buf_s *buf);
|
||||
|
||||
#endif /* __INCLUDE_NUTTX_WIRELESS_BT_DRIVER_H */
|
||||
|
||||
@@ -96,6 +96,53 @@ config BLUETOOTH_MAXSCANRESULT
|
||||
This contributes to a static memory allocation that will be greater
|
||||
than CONFIG_BLUETOOTH_MAXSCANDATA * CONFIG_BLUETOOTH_MAXSCANRESULT
|
||||
|
||||
#if !defined(CONFIG_BLUETOOTH_BUFFER_PREALLOC) || \
|
||||
CONFIG_BLUETOOTH_BUFFER_PREALLOC < 0
|
||||
# undef CONFIG_BLUETOOTH_BUFFER_PREALLOC
|
||||
# define CONFIG_BLUETOOTH_BUFFER_PREALLOC 20
|
||||
#endif
|
||||
|
||||
#if !defined(CONFIG_) || \
|
||||
CONFIG_BLUETOOTH_BUFFER_IRQRESERVE < 0
|
||||
# undef CONFIG_BLUETOOTH_BUFFER_IRQRESERVE
|
||||
# define CONFIG_BLUETOOTH_BUFFER_IRQRESERVE 0
|
||||
#endif
|
||||
|
||||
config BLUETOOTH_BUFFER_PREALLOC
|
||||
int "Number of pre-allocated buffer structures"
|
||||
default 20
|
||||
---help---
|
||||
This specifies the total number of preallocated buffer structures.
|
||||
This is for performance optimization. If additional buffer structures
|
||||
are needed, they will be allocated dynamically at some loss of
|
||||
performance.
|
||||
|
||||
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
|
||||
reserved for for use only by interrupt handlers. This may be set
|
||||
zero to reserve no buffers for interrupt handlers. In that case,
|
||||
the allocation will fail if tasking logic has allocated them all.
|
||||
|
||||
Interrupt logic will first attempt to allocate from the general,
|
||||
pre-allocated buffer pool that will contain up to (size
|
||||
CONFIG_BLUETOOTH_BUFFER_PREALLOC - BLUETOOTH_BUFFER_IRQRESERVE)
|
||||
entries. If that fails, then it will try to take a buffer from
|
||||
the reserve (size CONFIG_BLUETOOTH_BUFFER_IRQRESERVE).
|
||||
|
||||
Non-interrupt logic will also first attempt to allocate from the
|
||||
general, pre-allocated buffer pool. If that fails, it will
|
||||
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.
|
||||
|
||||
menu "Kernel Thread Configuration"
|
||||
|
||||
config BLUETOOTH_RXTHREAD_STACKSIZE
|
||||
|
||||
+50
-44
@@ -276,10 +276,12 @@ static uint8_t att_handle_read_mult_rsp(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf);
|
||||
static uint8_t att_handle_write_rsp(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf);
|
||||
static void bt_att_recv(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf);
|
||||
static void bt_att_connected(FAR struct bt_conn_s *conn);
|
||||
static void bt_att_disconnected(FAR struct bt_conn_s *conn);
|
||||
static void bt_att_receive(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf, FAR void *context, uint16_t cid);
|
||||
static void bt_att_connected(FAR struct bt_conn_s *conn, FAR void *context,
|
||||
uint16_t cid);
|
||||
static void bt_att_disconnected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid);
|
||||
|
||||
/****************************************************************************
|
||||
* Private Data
|
||||
@@ -451,7 +453,7 @@ static void send_err_rsp(struct bt_conn_s *conn, uint8_t req, uint16_t handle,
|
||||
return;
|
||||
}
|
||||
|
||||
rsp = bt_buf_add(buf, sizeof(*rsp));
|
||||
rsp = bt_buf_extend(buf, sizeof(*rsp));
|
||||
rsp->request = req;
|
||||
rsp->handle = BT_HOST2LE16(handle);
|
||||
rsp->error = err;
|
||||
@@ -499,7 +501,7 @@ static uint8_t att_mtu_req(struct bt_conn_s *conn, struct bt_buf_s *data)
|
||||
|
||||
att->mtu = mtu;
|
||||
|
||||
rsp = bt_buf_add(buf, sizeof(*rsp));
|
||||
rsp = bt_buf_extend(buf, sizeof(*rsp));
|
||||
rsp->mtu = BT_HOST2LE16(mtu);
|
||||
|
||||
bt_l2cap_send(conn, BT_L2CAP_CID_ATT, buf);
|
||||
@@ -610,7 +612,7 @@ static uint8_t find_info_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
|
||||
if (!data->rsp)
|
||||
{
|
||||
data->rsp = bt_buf_add(data->buf, sizeof(*data->rsp));
|
||||
data->rsp = bt_buf_extend(data->buf, sizeof(*data->rsp));
|
||||
data->rsp->format = (attr->uuid->type == BT_UUID_16) ?
|
||||
BT_ATT_INFO_16 : BT_ATT_INFO_128;
|
||||
}
|
||||
@@ -625,7 +627,7 @@ static uint8_t find_info_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
|
||||
/* Fast foward to next item position */
|
||||
|
||||
data->u.info16 = bt_buf_add(data->buf, sizeof(*data->u.info16));
|
||||
data->u.info16 = bt_buf_extend(data->buf, sizeof(*data->u.info16));
|
||||
data->u.info16->handle = BT_HOST2LE16(attr->handle);
|
||||
data->u.info16->uuid = BT_HOST2LE16(attr->uuid->u.u16);
|
||||
|
||||
@@ -640,7 +642,7 @@ static uint8_t find_info_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
|
||||
/* Fast foward to next item position */
|
||||
|
||||
data->u.info128 = bt_buf_add(data->buf, sizeof(*data->u.info128));
|
||||
data->u.info128 = bt_buf_extend(data->buf, sizeof(*data->u.info128));
|
||||
data->u.info128->handle = BT_HOST2LE16(attr->handle);
|
||||
memcpy(data->u.info128->uuid, attr->uuid->u.u128,
|
||||
sizeof(data->u.info128->uuid));
|
||||
@@ -670,7 +672,7 @@ static uint8_t att_find_info_rsp(FAR struct bt_conn_s *conn,
|
||||
|
||||
if (!data.rsp)
|
||||
{
|
||||
bt_buf_put(data.buf);
|
||||
bt_buf_release(data.buf);
|
||||
|
||||
/* Respond since handle is set */
|
||||
|
||||
@@ -759,7 +761,7 @@ static uint8_t find_type_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
|
||||
/* Fast foward to next item position */
|
||||
|
||||
data->group = bt_buf_add(data->buf, sizeof(*data->group));
|
||||
data->group = bt_buf_extend(data->buf, sizeof(*data->group));
|
||||
data->group->start_handle = BT_HOST2LE16(attr->handle);
|
||||
data->group->end_handle = BT_HOST2LE16(attr->handle);
|
||||
|
||||
@@ -791,7 +793,7 @@ static uint8_t att_find_type_rsp(FAR struct bt_conn_s *conn,
|
||||
|
||||
if (!data.group)
|
||||
{
|
||||
bt_buf_put(data.buf);
|
||||
bt_buf_release(data.buf);
|
||||
|
||||
/* Respond since handle is set */
|
||||
|
||||
@@ -819,7 +821,7 @@ static uint8_t att_find_type_req(FAR struct bt_conn_s *conn,
|
||||
start_handle = BT_LE162HOST(req->start_handle);
|
||||
end_handle = BT_LE162HOST(req->end_handle);
|
||||
type = BT_LE162HOST(req->type);
|
||||
value = bt_buf_pull(data, sizeof(*req));
|
||||
value = bt_buf_consume(data, sizeof(*req));
|
||||
|
||||
wlinfo("start_handle 0x%04x end_handle 0x%04x type %u\n", start_handle,
|
||||
end_handle, type);
|
||||
@@ -858,7 +860,7 @@ static bool uuid_create(FAR struct bt_uuid_s *uuid, FAR struct bt_buf_s *data)
|
||||
{
|
||||
case 2:
|
||||
uuid->type = BT_UUID_16;
|
||||
uuid->u.u16 = bt_buf_pull_le16(data);
|
||||
uuid->u.u16 = bt_buf_get_le16(data);
|
||||
return true;
|
||||
|
||||
case 16:
|
||||
@@ -888,7 +890,7 @@ static uint8_t read_type_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
|
||||
/* Fast foward to next item position */
|
||||
|
||||
data->item = bt_buf_add(data->buf, sizeof(*data->item));
|
||||
data->item = bt_buf_extend(data->buf, sizeof(*data->item));
|
||||
data->item->handle = BT_HOST2LE16(attr->handle);
|
||||
|
||||
/* Read attribute value and store in the buffer */
|
||||
@@ -916,7 +918,7 @@ static uint8_t read_type_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
return BT_GATT_ITER_STOP;
|
||||
}
|
||||
|
||||
bt_buf_add(data->buf, read);
|
||||
bt_buf_extend(data->buf, read);
|
||||
|
||||
/* Return true only if there are still space for more items */
|
||||
|
||||
@@ -941,14 +943,14 @@ static uint8_t att_read_type_rsp(FAR struct bt_conn_s *conn,
|
||||
}
|
||||
|
||||
data.uuid = uuid;
|
||||
data.rsp = bt_buf_add(data.buf, sizeof(*data.rsp));
|
||||
data.rsp = bt_buf_extend(data.buf, sizeof(*data.rsp));
|
||||
data.rsp->len = 0;
|
||||
|
||||
bt_gatt_foreach_attr(start_handle, end_handle, read_type_cb, &data);
|
||||
|
||||
if (!data.rsp->len)
|
||||
{
|
||||
bt_buf_put(data.buf);
|
||||
bt_buf_release(data.buf);
|
||||
|
||||
/* Response here since handle is set */
|
||||
|
||||
@@ -981,7 +983,7 @@ static uint8_t att_read_type_req(FAR struct bt_conn_s *conn,
|
||||
req = (FAR void *)data->data;
|
||||
start_handle = BT_LE162HOST(req->start_handle);
|
||||
end_handle = BT_LE162HOST(req->end_handle);
|
||||
bt_buf_pull(data, sizeof(*req));
|
||||
bt_buf_consume(data, sizeof(*req));
|
||||
|
||||
if (!uuid_create(&uuid, data))
|
||||
{
|
||||
@@ -1062,7 +1064,7 @@ static uint8_t read_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
|
||||
wlinfo("handle 0x%04x\n", attr->handle);
|
||||
|
||||
data->rsp = bt_buf_add(data->buf, sizeof(*data->rsp));
|
||||
data->rsp = bt_buf_extend(data->buf, sizeof(*data->rsp));
|
||||
|
||||
if (!attr->read)
|
||||
{
|
||||
@@ -1088,7 +1090,7 @@ static uint8_t read_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
return BT_GATT_ITER_STOP;
|
||||
}
|
||||
|
||||
bt_buf_add(data->buf, read);
|
||||
bt_buf_extend(data->buf, read);
|
||||
return BT_GATT_ITER_CONTINUE;
|
||||
}
|
||||
|
||||
@@ -1119,7 +1121,7 @@ static uint8_t att_read_rsp(FAR struct bt_conn_s *conn, uint8_t op,
|
||||
|
||||
if (data.err)
|
||||
{
|
||||
bt_buf_put(data.buf);
|
||||
bt_buf_release(data.buf);
|
||||
|
||||
/* Respond here since handle is set */
|
||||
|
||||
@@ -1181,7 +1183,7 @@ static uint8_t att_read_mult_req(FAR struct bt_conn_s *conn,
|
||||
|
||||
while (buf->len >= sizeof(uint16_t))
|
||||
{
|
||||
handle = bt_buf_pull_le16(buf);
|
||||
handle = bt_buf_get_le16(buf);
|
||||
|
||||
wlinfo("handle 0x%04x \n", handle);
|
||||
|
||||
@@ -1191,7 +1193,7 @@ static uint8_t att_read_mult_req(FAR struct bt_conn_s *conn,
|
||||
|
||||
if (data.err)
|
||||
{
|
||||
bt_buf_put(data.buf);
|
||||
bt_buf_release(data.buf);
|
||||
|
||||
/* Respond here since handle is set */
|
||||
|
||||
@@ -1235,7 +1237,7 @@ static uint8_t read_group_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
|
||||
/* Fast forward to next group position */
|
||||
|
||||
data->group = bt_buf_add(data->buf, sizeof(*data->group));
|
||||
data->group = bt_buf_extend(data->buf, sizeof(*data->group));
|
||||
|
||||
/* Initialize group handle range */
|
||||
|
||||
@@ -1267,7 +1269,7 @@ static uint8_t read_group_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
return false;
|
||||
}
|
||||
|
||||
bt_buf_add(data->buf, read);
|
||||
bt_buf_extend(data->buf, read);
|
||||
|
||||
/* Continue to find the end handle */
|
||||
|
||||
@@ -1292,14 +1294,14 @@ static uint8_t att_read_group_rsp(FAR struct bt_conn_s *conn,
|
||||
|
||||
data.conn = conn;
|
||||
data.uuid = uuid;
|
||||
data.rsp = bt_buf_add(data.buf, sizeof(*data.rsp));
|
||||
data.rsp = bt_buf_extend(data.buf, sizeof(*data.rsp));
|
||||
data.rsp->len = 0;
|
||||
|
||||
bt_gatt_foreach_attr(start_handle, end_handle, read_group_cb, &data);
|
||||
|
||||
if (!data.rsp->len)
|
||||
{
|
||||
bt_buf_put(data.buf);
|
||||
bt_buf_release(data.buf);
|
||||
|
||||
/* Respond here since handle is set */
|
||||
|
||||
@@ -1332,7 +1334,7 @@ static uint8_t att_read_group_req(FAR struct bt_conn_s *conn,
|
||||
req = (FAR void *)data->data;
|
||||
start_handle = BT_LE162HOST(req->start_handle);
|
||||
end_handle = BT_LE162HOST(req->end_handle);
|
||||
bt_buf_pull(data, sizeof(*req));
|
||||
bt_buf_consume(data, sizeof(*req));
|
||||
|
||||
if (!uuid_create(&uuid, data))
|
||||
{
|
||||
@@ -1456,7 +1458,7 @@ static uint8_t att_write_rsp(FAR struct bt_conn_s *conn, uint8_t op,
|
||||
{
|
||||
if (rsp)
|
||||
{
|
||||
bt_buf_put(data.buf);
|
||||
bt_buf_release(data.buf);
|
||||
|
||||
/* Respond here since handle is set */
|
||||
|
||||
@@ -1474,10 +1476,10 @@ static uint8_t att_write_rsp(FAR struct bt_conn_s *conn, uint8_t op,
|
||||
{
|
||||
FAR struct bt_att_prepare_write_rsp_s *wrrsp;
|
||||
|
||||
wrrsp = bt_buf_add(data.buf, sizeof(*wrrsp));
|
||||
wrrsp = bt_buf_extend(data.buf, sizeof(*wrrsp));
|
||||
wrrsp->handle = BT_HOST2LE16(handle);
|
||||
wrrsp->offset = BT_HOST2LE16(offset);
|
||||
bt_buf_add(data.buf, len);
|
||||
bt_buf_extend(data.buf, len);
|
||||
memcpy(wrrsp->value, value, len);
|
||||
}
|
||||
|
||||
@@ -1496,7 +1498,7 @@ static uint8_t att_write_req(FAR struct bt_conn_s *conn,
|
||||
req = (FAR void *)data->data;
|
||||
|
||||
handle = BT_LE162HOST(req->handle);
|
||||
bt_buf_pull(data, sizeof(*req));
|
||||
bt_buf_consume(data, sizeof(*req));
|
||||
|
||||
wlinfo("handle 0x%04x\n", handle);
|
||||
|
||||
@@ -1514,7 +1516,7 @@ static uint8_t att_prepare_write_req(FAR struct bt_conn_s *conn,
|
||||
req = (FAR void *)data->data;
|
||||
handle = BT_LE162HOST(req->handle);
|
||||
offset = BT_LE162HOST(req->offset);
|
||||
bt_buf_pull(data, sizeof(*req));
|
||||
bt_buf_consume(data, sizeof(*req));
|
||||
|
||||
wlinfo("handle 0x%04x offset %u\n", handle, offset);
|
||||
|
||||
@@ -1577,7 +1579,7 @@ static uint8_t att_exec_write_rsp(FAR struct bt_conn_s *conn, uint8_t flags)
|
||||
|
||||
if (data.err)
|
||||
{
|
||||
bt_buf_put(data.buf);
|
||||
bt_buf_release(data.buf);
|
||||
return data.err;
|
||||
}
|
||||
|
||||
@@ -1628,7 +1630,7 @@ static uint8_t att_signed_write_cmd(FAR struct bt_conn_s *conn,
|
||||
req = (FAR void *)data->data;
|
||||
|
||||
handle = BT_LE162HOST(req->handle);
|
||||
bt_buf_pull(data, sizeof(*req));
|
||||
bt_buf_consume(data, sizeof(*req));
|
||||
|
||||
wlinfo("handle 0x%04x\n", handle);
|
||||
|
||||
@@ -1712,7 +1714,9 @@ static uint8_t att_handle_write_rsp(FAR struct bt_conn_s *conn,
|
||||
return att_handle_rsp(conn, buf->data, buf->len, 0);
|
||||
}
|
||||
|
||||
static void bt_att_recv(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
static void bt_att_receive(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf, FAR void *context,
|
||||
uint16_t cid)
|
||||
{
|
||||
FAR struct bt_att_hdr_s *hdr = (FAR void *)buf->data;
|
||||
uint8_t err = BT_ATT_ERR_NOT_SUPPORTED;
|
||||
@@ -1728,7 +1732,7 @@ static void bt_att_recv(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
|
||||
wlinfo("Received ATT code 0x%02x len %u\n", hdr->code, buf->len);
|
||||
|
||||
bt_buf_pull(buf, sizeof(*hdr));
|
||||
bt_buf_consume(buf, sizeof(*hdr));
|
||||
|
||||
for (i = 0; i < NHANDLERS; i++)
|
||||
{
|
||||
@@ -1763,10 +1767,11 @@ static void bt_att_recv(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
}
|
||||
|
||||
done:
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
}
|
||||
|
||||
static void bt_att_connected(FAR struct bt_conn_s *conn)
|
||||
static void bt_att_connected(FAR struct bt_conn_s *conn, FAR void *context,
|
||||
uint16_t cid)
|
||||
{
|
||||
int i;
|
||||
|
||||
@@ -1789,7 +1794,8 @@ static void bt_att_connected(FAR struct bt_conn_s *conn)
|
||||
wlerr("ERROR: No available ATT context for conn %p\n", conn);
|
||||
}
|
||||
|
||||
static void bt_att_disconnected(FAR struct bt_conn_s *conn)
|
||||
static void bt_att_disconnected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid)
|
||||
{
|
||||
FAR struct bt_att_s *att = conn->att;
|
||||
|
||||
@@ -1809,12 +1815,12 @@ static void bt_att_disconnected(FAR struct bt_conn_s *conn)
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
|
||||
void bt_att_init(void)
|
||||
void bt_att_initialize(void)
|
||||
{
|
||||
static struct bt_l2cap_chan_s chan =
|
||||
{
|
||||
.cid = BT_L2CAP_CID_ATT,
|
||||
.recv = bt_att_recv,
|
||||
.receive = bt_att_receive,
|
||||
.connected = bt_att_connected,
|
||||
.disconnected = bt_att_disconnected,
|
||||
};
|
||||
@@ -1841,7 +1847,7 @@ FAR struct bt_buf_s *bt_att_create_pdu(FAR struct bt_conn_s *conn, uint8_t op,
|
||||
return NULL;
|
||||
}
|
||||
|
||||
hdr = bt_buf_add(buf, sizeof(*hdr));
|
||||
hdr = bt_buf_extend(buf, sizeof(*hdr));
|
||||
hdr->code = op;
|
||||
|
||||
return buf;
|
||||
|
||||
@@ -434,7 +434,7 @@ typedef void (*bt_att_destroy_t)(FAR void *user_data);
|
||||
* Public Function Prototypes
|
||||
****************************************************************************/
|
||||
|
||||
void bt_att_init(void);
|
||||
void bt_att_initialize(void);
|
||||
struct bt_buf_s *bt_att_create_pdu(FAR struct bt_conn_s *conn, uint8_t op,
|
||||
size_t len);
|
||||
|
||||
|
||||
+490
-64
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,74 @@
|
||||
/****************************************************************************
|
||||
* wireless/bluetooth/bt_buf.h
|
||||
* Bluetooth buffer management.
|
||||
*
|
||||
* Copyright (C) 2018 Gregory Nutt. All rights reserved.
|
||||
* Author: Gregory Nutt <gnutt@nuttx.org>
|
||||
*
|
||||
* Ported from the Intel/Zephyr arduino101_firmware_source-v1.tar package
|
||||
* where the code was released with a compatible 3-clause BSD license:
|
||||
*
|
||||
* Copyright (c) 2016, Intel Corporation
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice,
|
||||
* this list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* 3. Neither the name of the copyright holder nor the names of its
|
||||
* contributors may be used to endorse or promote products derived from this
|
||||
* software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
|
||||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef __WIRELESS_BLUETOOTH_BT_BUF_H
|
||||
#define __WIRELESS_BLUETOOTH_BT_BUF_H 1
|
||||
|
||||
/****************************************************************************
|
||||
* Included Files
|
||||
****************************************************************************/
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
|
||||
/****************************************************************************
|
||||
* Public Function Prototypes
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_buf_initialize
|
||||
*
|
||||
* Description:
|
||||
* This function initializes the buffer allocator. This function must
|
||||
* be called early in the initialization sequence before any radios
|
||||
* begin operation.
|
||||
*
|
||||
* Input Parameters:
|
||||
* None
|
||||
*
|
||||
* Returned Value:
|
||||
* None
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void bt_buf_initialize(void);
|
||||
|
||||
#endif /* __WIRELESS_BLUETOOTH_BT_BUF_H */
|
||||
@@ -123,7 +123,7 @@ static void bt_conn_reset_rx_state(FAR struct bt_conn_s *conn)
|
||||
return;
|
||||
}
|
||||
|
||||
bt_buf_put(conn->rx);
|
||||
bt_buf_release(conn->rx);
|
||||
conn->rx = NULL;
|
||||
conn->rx_len = 0;
|
||||
}
|
||||
@@ -166,20 +166,20 @@ static int conn_tx_kthread(int argc, FAR char *argv[])
|
||||
|
||||
/* Get next ACL packet for connection */
|
||||
|
||||
ret = bt_queue_recv(conn->tx_queue, &buf);
|
||||
ret = bt_queue_receive(conn->tx_queue, &buf);
|
||||
DEBUGASSERT(ret >= 0 && buf != NULL);
|
||||
UNUSED(ret);
|
||||
|
||||
if (conn->state != BT_CONN_CONNECTED)
|
||||
{
|
||||
nxsem_post(&g_btdev.le_pkts_sem);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
break;
|
||||
}
|
||||
|
||||
wlinfo("passing buf %p len %u to driver\n", buf, buf->len);
|
||||
g_btdev.dev->send(g_btdev.dev, buf);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
}
|
||||
|
||||
wlinfo("handle %u disconnected - cleaning up\n", conn->handle);
|
||||
@@ -189,11 +189,11 @@ static int conn_tx_kthread(int argc, FAR char *argv[])
|
||||
do
|
||||
{
|
||||
buf = NULL;
|
||||
ret = bt_queue_recv(conn->tx_queue, &buf);
|
||||
ret = bt_queue_receive(conn->tx_queue, &buf);
|
||||
if (ret >= 0)
|
||||
{
|
||||
DEBUGASSERT(buf != NULL);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
}
|
||||
}
|
||||
while (ret >= OK);
|
||||
@@ -217,7 +217,7 @@ static int bt_hci_disconnect(FAR struct bt_conn_s *conn, uint8_t reason)
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
disconn = bt_buf_add(buf, sizeof(*disconn));
|
||||
disconn = bt_buf_extend(buf, sizeof(*disconn));
|
||||
disconn->handle = BT_HOST2LE16(conn->handle);
|
||||
disconn->reason = reason;
|
||||
|
||||
@@ -249,7 +249,7 @@ static int bt_hci_connect_le_cancel(FAR struct bt_conn_s *conn)
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_conn_input
|
||||
* Name: bt_conn_receive
|
||||
*
|
||||
* Description:
|
||||
* Receive packets from the HCI core on a registered connection.
|
||||
@@ -264,8 +264,8 @@ static int bt_hci_connect_le_cancel(FAR struct bt_conn_s *conn)
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void bt_conn_input(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
uint8_t flags)
|
||||
void bt_conn_receive(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
uint8_t flags)
|
||||
{
|
||||
FAR struct bt_l2cap_hdr_s *hdr;
|
||||
uint16_t len;
|
||||
@@ -307,7 +307,7 @@ void bt_conn_input(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
{
|
||||
wlerr("ERROR: Unexpected L2CAP continuation\n");
|
||||
bt_conn_reset_rx_state(conn);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -315,7 +315,7 @@ void bt_conn_input(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
{
|
||||
wlerr("ERROR: L2CAP data overflow\n");
|
||||
bt_conn_reset_rx_state(conn);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -325,13 +325,13 @@ void bt_conn_input(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
{
|
||||
wlerr("ERROR: Not enough buffer space for L2CAP data\n");
|
||||
bt_conn_reset_rx_state(conn);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return;
|
||||
}
|
||||
|
||||
memcpy(bt_buf_add(conn->rx, buf->len), buf->data, buf->len);
|
||||
memcpy(bt_buf_extend(conn->rx, buf->len), buf->data, buf->len);
|
||||
conn->rx_len -= buf->len;
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
|
||||
if (conn->rx_len)
|
||||
{
|
||||
@@ -347,7 +347,7 @@ void bt_conn_input(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
default:
|
||||
wlerr("ERROR: Unexpected ACL flags (0x%02x)\n", flags);
|
||||
bt_conn_reset_rx_state(conn);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -357,13 +357,13 @@ void bt_conn_input(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
if (sizeof(*hdr) + len != buf->len)
|
||||
{
|
||||
wlerr("ERROR: ACL len mismatch (%u != %u)\n", len, buf->len);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return;
|
||||
}
|
||||
|
||||
wlinfo("Successfully parsed %u byte L2CAP packet\n", buf->len);
|
||||
|
||||
bt_l2cap_recv(conn, buf);
|
||||
bt_l2cap_receive(conn, buf);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
@@ -385,7 +385,6 @@ void bt_conn_send(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
{
|
||||
FAR struct bt_hci_acl_hdr_s *hdr;
|
||||
sq_queue_t fraglist;
|
||||
sq_entry_t *fragment;
|
||||
uint16_t len;
|
||||
uint16_t remaining = buf->len;
|
||||
FAR uint8_t *ptr;
|
||||
@@ -405,7 +404,7 @@ void bt_conn_send(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
len = g_btdev.le_mtu;
|
||||
}
|
||||
|
||||
hdr = bt_buf_push(buf, sizeof(*hdr));
|
||||
hdr = bt_buf_provide(buf, sizeof(*hdr));
|
||||
hdr->handle = BT_HOST2LE16(conn->handle);
|
||||
hdr->len = BT_HOST2LE16(len);
|
||||
|
||||
@@ -414,10 +413,7 @@ void bt_conn_send(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
|
||||
/* Add the fragment to the end of the list */
|
||||
|
||||
fragment = (FAR sq_entry_t *)buf->iob;
|
||||
DEBUGASSERT(fragment != NULL);
|
||||
sq_addlast(fragment, &fraglist);
|
||||
|
||||
sq_addlast((FAR sq_entry_t *)buf, &fraglist);
|
||||
remaining -= len;
|
||||
|
||||
while (remaining)
|
||||
@@ -432,27 +428,23 @@ void bt_conn_send(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
|
||||
/* Copy from original buffer */
|
||||
|
||||
memcpy(bt_buf_add(buf, len), ptr, len);
|
||||
memcpy(bt_buf_extend(buf, len), ptr, len);
|
||||
ptr += len;
|
||||
|
||||
hdr = bt_buf_push(buf, sizeof(*hdr));
|
||||
hdr = bt_buf_provide(buf, sizeof(*hdr));
|
||||
hdr->handle = BT_HOST2LE16(conn->handle | (1 << 12));
|
||||
hdr->len = BT_HOST2LE16(len);
|
||||
|
||||
/* Add the fragment to the end of the list */
|
||||
|
||||
fragment = (FAR sq_entry_t *)buf->iob;
|
||||
DEBUGASSERT(fragment != NULL);
|
||||
sq_addlast(fragment, &fraglist);
|
||||
|
||||
sq_addlast((FAR sq_entry_t *)buf, &fraglist);
|
||||
remaining -= len;
|
||||
}
|
||||
|
||||
/* Then send each fragment in the correct order */
|
||||
|
||||
while ((fragment = sq_remfirst(&fraglist)) != NULL)
|
||||
while ((buf = (FAR struct bt_buf_s *)sq_remfirst(&fraglist)) != NULL)
|
||||
{
|
||||
buf = (FAR struct bt_buf_s *)(((FAR struct iob_s *)fragment)->io_data);
|
||||
bt_queue_send(conn->tx_queue, buf, BT_NORMAL_PRIO);
|
||||
}
|
||||
}
|
||||
@@ -596,7 +588,7 @@ 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_get(BT_DUMMY, 0), BT_NORMAL_PRIO);
|
||||
bt_queue_send(conn->tx_queue, bt_buf_alloc(BT_DUMMY, 0), BT_NORMAL_PRIO);
|
||||
}
|
||||
|
||||
/* Release the reference we took for the very first state transition. */
|
||||
@@ -1009,7 +1001,7 @@ FAR struct bt_conn_s *bt_conn_create_le(FAR const bt_addr_le_t *peer)
|
||||
* Input Parameters:
|
||||
* conn - The connection to send the command on.
|
||||
* rand, ediv - Values to use for the encryption key
|
||||
* ltk -
|
||||
* ltk -
|
||||
*
|
||||
* Returned Value:
|
||||
* Zero is returned on success; a negated errno value is returned on any
|
||||
@@ -1029,7 +1021,7 @@ int bt_conn_le_start_encryption(FAR struct bt_conn_s *conn, uint64_t rand,
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
cp = bt_buf_add(buf, sizeof(*cp));
|
||||
cp = bt_buf_extend(buf, sizeof(*cp));
|
||||
cp->handle = BT_HOST2LE16(conn->handle);
|
||||
cp->rand = rand;
|
||||
cp->ediv = ediv;
|
||||
@@ -1050,7 +1042,7 @@ int bt_conn_le_conn_update(FAR struct bt_conn_s *conn, uint16_t min,
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
conn_update = bt_buf_add(buf, sizeof(*conn_update));
|
||||
conn_update = bt_buf_extend(buf, sizeof(*conn_update));
|
||||
memset(conn_update, 0, sizeof(*conn_update));
|
||||
conn_update->handle = BT_HOST2LE16(conn->handle);
|
||||
conn_update->conn_interval_min = BT_HOST2LE16(min);
|
||||
|
||||
@@ -111,11 +111,11 @@ struct bt_conn_s
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
* Public Data
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_conn_input
|
||||
* Name: bt_conn_receive
|
||||
*
|
||||
* Description:
|
||||
* Receive packets from the HCI core on a registered connection.
|
||||
@@ -130,8 +130,8 @@ struct bt_conn_s
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void bt_conn_input(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
uint8_t flags);
|
||||
void bt_conn_receive(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
uint8_t flags);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_conn_send
|
||||
|
||||
@@ -442,10 +442,10 @@ static uint8_t notify_cb(FAR const struct bt_gatt_attr_s *attr,
|
||||
|
||||
wlinfo("conn %p handle 0x%04x\n", conn, data->handle);
|
||||
|
||||
nfy = bt_buf_add(buf, sizeof(*nfy));
|
||||
nfy = bt_buf_extend(buf, sizeof(*nfy));
|
||||
nfy->handle = BT_HOST2LE16(data->handle);
|
||||
|
||||
bt_buf_add(buf, data->len);
|
||||
bt_buf_extend(buf, data->len);
|
||||
memcpy(nfy->value, data->data, data->len);
|
||||
|
||||
bt_l2cap_send(conn, BT_L2CAP_CID_ATT, buf);
|
||||
@@ -595,7 +595,7 @@ static int gatt_send(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
if (err)
|
||||
{
|
||||
wlerr("ERROR: Error sending ATT PDU: %d\n", err);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
}
|
||||
|
||||
return err;
|
||||
@@ -627,7 +627,7 @@ int bt_gatt_exchange_mtu(FAR struct bt_conn_s *conn,
|
||||
|
||||
wlinfo("Client MTU %u\n", mtu);
|
||||
|
||||
req = bt_buf_add(buf, sizeof(*req));
|
||||
req = bt_buf_extend(buf, sizeof(*req));
|
||||
req->mtu = BT_HOST2LE16(mtu);
|
||||
|
||||
return gatt_send(conn, buf, gatt_mtu_rsp, func, NULL);
|
||||
@@ -721,7 +721,7 @@ int bt_gatt_discover(FAR struct bt_conn_s *conn,
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
req = bt_buf_add(buf, sizeof(*req));
|
||||
req = bt_buf_extend(buf, sizeof(*req));
|
||||
req->start_handle = BT_HOST2LE16(params->start_handle);
|
||||
req->end_handle = BT_HOST2LE16(params->end_handle);
|
||||
req->type = BT_HOST2LE16(BT_UUID_GATT_PRIMARY);
|
||||
@@ -732,18 +732,18 @@ int bt_gatt_discover(FAR struct bt_conn_s *conn,
|
||||
switch (params->uuid->type)
|
||||
{
|
||||
case BT_UUID_16:
|
||||
value = bt_buf_add(buf, sizeof(*value));
|
||||
value = bt_buf_extend(buf, sizeof(*value));
|
||||
*value = BT_HOST2LE16(params->uuid->u.u16);
|
||||
break;
|
||||
|
||||
case BT_UUID_128:
|
||||
bt_buf_add(buf, sizeof(params->uuid->u.u128));
|
||||
bt_buf_extend(buf, sizeof(params->uuid->u.u128));
|
||||
memcpy(req->value, params->uuid->u.u128, sizeof(params->uuid->u.u128));
|
||||
break;
|
||||
|
||||
default:
|
||||
wlerr("ERROR: Unkown UUID type %u\n", params->uuid->type);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
@@ -885,11 +885,11 @@ int bt_gatt_discover_characteristic(FAR struct bt_conn_s *conn,
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
req = bt_buf_add(buf, sizeof(*req));
|
||||
req = bt_buf_extend(buf, sizeof(*req));
|
||||
req->start_handle = BT_HOST2LE16(params->start_handle);
|
||||
req->end_handle = BT_HOST2LE16(params->end_handle);
|
||||
|
||||
value = bt_buf_add(buf, sizeof(*value));
|
||||
value = bt_buf_extend(buf, sizeof(*value));
|
||||
*value = BT_HOST2LE16(BT_UUID_GATT_CHRC);
|
||||
|
||||
wlinfo("start_handle 0x%04x end_handle 0x%04x\n", params->start_handle,
|
||||
@@ -1031,7 +1031,7 @@ int bt_gatt_discover_descriptor(FAR struct bt_conn_s *conn,
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
req = bt_buf_add(buf, sizeof(*req));
|
||||
req = bt_buf_extend(buf, sizeof(*req));
|
||||
req->start_handle = BT_HOST2LE16(params->start_handle);
|
||||
req->end_handle = BT_HOST2LE16(params->end_handle);
|
||||
|
||||
@@ -1070,7 +1070,7 @@ static int gatt_read_blob(FAR struct bt_conn_s *conn, uint16_t handle,
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
req = bt_buf_add(buf, sizeof(*req));
|
||||
req = bt_buf_extend(buf, sizeof(*req));
|
||||
req->handle = BT_HOST2LE16(handle);
|
||||
req->offset = BT_HOST2LE16(offset);
|
||||
|
||||
@@ -1101,7 +1101,7 @@ int bt_gatt_read(FAR struct bt_conn_s *conn, uint16_t handle,
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
req = bt_buf_add(buf, sizeof(*req));
|
||||
req = bt_buf_extend(buf, sizeof(*req));
|
||||
req->handle = BT_HOST2LE16(handle);
|
||||
|
||||
wlinfo("handle 0x%04x\n", handle);
|
||||
@@ -1132,10 +1132,10 @@ static int gatt_write_cmd(FAR struct bt_conn_s *conn, uint16_t handle,
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
cmd = bt_buf_add(buf, sizeof(*cmd));
|
||||
cmd = bt_buf_extend(buf, sizeof(*cmd));
|
||||
cmd->handle = BT_HOST2LE16(handle);
|
||||
memcpy(cmd->value, data, length);
|
||||
bt_buf_add(buf, length);
|
||||
bt_buf_extend(buf, length);
|
||||
|
||||
wlinfo("handle 0x%04x length %u\n", handle, length);
|
||||
|
||||
@@ -1165,10 +1165,10 @@ int bt_gatt_write(FAR struct bt_conn_s *conn, uint16_t handle,
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
req = bt_buf_add(buf, sizeof(*req));
|
||||
req = bt_buf_extend(buf, sizeof(*req));
|
||||
req->handle = BT_HOST2LE16(handle);
|
||||
memcpy(req->value, data, length);
|
||||
bt_buf_add(buf, length);
|
||||
bt_buf_extend(buf, length);
|
||||
|
||||
wlinfo("handle 0x%04x length %u\n", handle, length);
|
||||
|
||||
@@ -1206,7 +1206,7 @@ int bt_gatt_read_multiple(FAR struct bt_conn_s *conn,
|
||||
|
||||
for (i = 0; i < count; i++)
|
||||
{
|
||||
bt_buf_add_le16(buf, handles[i]);
|
||||
bt_buf_put_le16(buf, handles[i]);
|
||||
}
|
||||
|
||||
return gatt_send(conn, buf, att_read_rsp, func, NULL);
|
||||
|
||||
@@ -58,10 +58,11 @@
|
||||
#include <nuttx/wireless/bt_hci.h>
|
||||
|
||||
#include "bt_queue.h"
|
||||
#include "bt_hcicore.h"
|
||||
#include "bt_buf.h"
|
||||
#include "bt_keys.h"
|
||||
#include "bt_conn.h"
|
||||
#include "bt_l2cap.h"
|
||||
#include "bt_hcicore.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
@@ -95,11 +96,11 @@ static void bt_connected(FAR struct bt_conn_s *conn)
|
||||
{
|
||||
FAR struct bt_conn_cb_s *cb;
|
||||
|
||||
for (cb = g_callback_list; cb; cb = cb->next)
|
||||
for (cb = g_callback_list; cb; cb = cb->flink)
|
||||
{
|
||||
if (cb->connected)
|
||||
{
|
||||
cb->connected(conn);
|
||||
cb->connected(conn, cb->context);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -108,11 +109,11 @@ static void bt_disconnected(FAR struct bt_conn_s *conn)
|
||||
{
|
||||
FAR struct bt_conn_cb_s *cb;
|
||||
|
||||
for (cb = g_callback_list; cb; cb = cb->next)
|
||||
for (cb = g_callback_list; cb; cb = cb->flink)
|
||||
{
|
||||
if (cb->disconnected)
|
||||
{
|
||||
cb->disconnected(conn);
|
||||
cb->disconnected(conn, cb->context);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -131,14 +132,14 @@ static void hci_acl(FAR struct bt_buf_s *buf)
|
||||
flags = (handle >> 12);
|
||||
buf->u.acl.handle = bt_acl_handle(handle);
|
||||
|
||||
bt_buf_pull(buf, sizeof(*hdr));
|
||||
bt_buf_consume(buf, sizeof(*hdr));
|
||||
|
||||
wlinfo("handle %u len %u flags %u\n", buf->u.acl.handle, len, flags);
|
||||
|
||||
if (buf->len != len)
|
||||
{
|
||||
wlerr("ERROR: ACL data length mismatch (%u != %u)\n", buf->len, len);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -146,11 +147,11 @@ static void hci_acl(FAR struct bt_buf_s *buf)
|
||||
if (!conn)
|
||||
{
|
||||
wlerr("ERROR: Unable to find conn for handle %u\n", buf->u.acl.handle);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return;
|
||||
}
|
||||
|
||||
bt_conn_input(conn, buf, flags);
|
||||
bt_conn_receive(conn, buf, flags);
|
||||
bt_conn_release(conn);
|
||||
}
|
||||
|
||||
@@ -229,14 +230,14 @@ static void hci_cmd_done(uint16_t opcode, uint8_t status,
|
||||
}
|
||||
else
|
||||
{
|
||||
sent->u.hci.sync = bt_buf_hold(buf);
|
||||
sent->u.hci.sync = bt_buf_addref(buf);
|
||||
}
|
||||
|
||||
nxsem_post(sem);
|
||||
}
|
||||
else
|
||||
{
|
||||
bt_buf_put(sent);
|
||||
bt_buf_release(sent);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -248,7 +249,7 @@ static void hci_cmd_complete(FAR struct bt_buf_s *buf)
|
||||
|
||||
wlinfo("opcode %x\n", opcode);
|
||||
|
||||
bt_buf_pull(buf, sizeof(*evt));
|
||||
bt_buf_consume(buf, sizeof(*evt));
|
||||
|
||||
/* All command return parameters have a 1-byte status in the beginning, so we
|
||||
* can safely make this generalization.
|
||||
@@ -285,7 +286,7 @@ static void hci_cmd_status(FAR struct bt_buf_s *buf)
|
||||
|
||||
wlinfo("opcode %x\n", opcode);
|
||||
|
||||
bt_buf_pull(buf, sizeof(*evt));
|
||||
bt_buf_consume(buf, sizeof(*evt));
|
||||
|
||||
switch (opcode)
|
||||
{
|
||||
@@ -392,7 +393,7 @@ static int bt_hci_start_scanning(uint8_t scan_type, uint8_t scan_filter)
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
set_param = bt_buf_add(buf, sizeof(*set_param));
|
||||
set_param = bt_buf_extend(buf, sizeof(*set_param));
|
||||
memset(set_param, 0, sizeof(*set_param));
|
||||
set_param->scan_type = scan_type;
|
||||
|
||||
@@ -412,7 +413,7 @@ static int bt_hci_start_scanning(uint8_t scan_type, uint8_t scan_filter)
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
scan_enable = bt_buf_add(buf, sizeof(*scan_enable));
|
||||
scan_enable = bt_buf_extend(buf, sizeof(*scan_enable));
|
||||
memset(scan_enable, 0, sizeof(*scan_enable));
|
||||
scan_enable->filter_dup = scan_filter;
|
||||
scan_enable->enable = BT_LE_SCAN_ENABLE;
|
||||
@@ -431,7 +432,7 @@ static int bt_hci_start_scanning(uint8_t scan_type, uint8_t scan_filter)
|
||||
g_btdev.scan_enable = BT_LE_SCAN_ENABLE;
|
||||
}
|
||||
|
||||
bt_buf_put(rsp);
|
||||
bt_buf_release(rsp);
|
||||
return err;
|
||||
}
|
||||
|
||||
@@ -453,7 +454,7 @@ static int bt_hci_stop_scanning(void)
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
scan_enable = bt_buf_add(buf, sizeof(*scan_enable));
|
||||
scan_enable = bt_buf_extend(buf, sizeof(*scan_enable));
|
||||
memset(scan_enable, 0x0, sizeof(*scan_enable));
|
||||
scan_enable->filter_dup = 0x00;
|
||||
scan_enable->enable = BT_LE_SCAN_DISABLE;
|
||||
@@ -472,7 +473,7 @@ static int bt_hci_stop_scanning(void)
|
||||
g_btdev.scan_enable = BT_LE_SCAN_DISABLE;
|
||||
}
|
||||
|
||||
bt_buf_put(rsp);
|
||||
bt_buf_release(rsp);
|
||||
return err;
|
||||
}
|
||||
|
||||
@@ -487,7 +488,7 @@ static int hci_le_create_conn(FAR const bt_addr_le_t *addr)
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
cp = bt_buf_add(buf, sizeof(*cp));
|
||||
cp = bt_buf_extend(buf, sizeof(*cp));
|
||||
memset(cp, 0x0, sizeof(*cp));
|
||||
bt_addr_le_copy(&cp->peer_addr, addr);
|
||||
cp->conn_interval_max = BT_HOST2LE16(0x0028);
|
||||
@@ -538,7 +539,7 @@ static void hci_disconn_complete(FAR struct bt_buf_s *buf)
|
||||
buf = bt_hci_cmd_create(BT_HCI_OP_LE_SET_ADV_ENABLE, 1);
|
||||
if (buf)
|
||||
{
|
||||
memcpy(bt_buf_add(buf, 1), &g_btdev.adv_enable, 1);
|
||||
memcpy(bt_buf_extend(buf, 1), &g_btdev.adv_enable, 1);
|
||||
bt_hci_cmd_send(BT_HCI_OP_LE_SET_ADV_ENABLE, buf);
|
||||
}
|
||||
}
|
||||
@@ -665,7 +666,7 @@ static void le_adv_report(FAR struct bt_buf_s *buf)
|
||||
|
||||
wlinfo("Adv number of reports %u\n", num_reports);
|
||||
|
||||
info = bt_buf_pull(buf, sizeof(num_reports));
|
||||
info = bt_buf_consume(buf, sizeof(num_reports));
|
||||
|
||||
while (num_reports--)
|
||||
{
|
||||
@@ -701,7 +702,7 @@ static void le_adv_report(FAR struct bt_buf_s *buf)
|
||||
* according to spec 4.2, Vol 2, Part E, 7.7.65.2.
|
||||
*/
|
||||
|
||||
info = bt_buf_pull(buf, sizeof(*info) + info->length + sizeof(rssi));
|
||||
info = bt_buf_consume(buf, sizeof(*info) + info->length + sizeof(rssi));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -740,7 +741,7 @@ static void le_ltk_request(FAR struct bt_buf_s *buf)
|
||||
goto done;
|
||||
}
|
||||
|
||||
cp = bt_buf_add(buf, sizeof(*cp));
|
||||
cp = bt_buf_extend(buf, sizeof(*cp));
|
||||
cp->handle = evt->handle;
|
||||
memcpy(cp->ltk, conn->keys->slave_ltk.val, 16);
|
||||
|
||||
@@ -757,7 +758,7 @@ static void le_ltk_request(FAR struct bt_buf_s *buf)
|
||||
goto done;
|
||||
}
|
||||
|
||||
cp = bt_buf_add(buf, sizeof(*cp));
|
||||
cp = bt_buf_extend(buf, sizeof(*cp));
|
||||
cp->handle = evt->handle;
|
||||
|
||||
bt_hci_cmd_send(BT_HCI_OP_LE_LTK_REQ_NEG_REPLY, buf);
|
||||
@@ -771,7 +772,7 @@ static void hci_le_meta_event(FAR struct bt_buf_s *buf)
|
||||
{
|
||||
FAR struct bt_hci_evt_le_meta_event_s *evt = (FAR void *)buf->data;
|
||||
|
||||
bt_buf_pull(buf, sizeof(*evt));
|
||||
bt_buf_consume(buf, sizeof(*evt));
|
||||
|
||||
switch (evt->subevent)
|
||||
{
|
||||
@@ -799,7 +800,7 @@ static void hci_event(FAR struct bt_buf_s *buf)
|
||||
|
||||
wlinfo("event %u\n", hdr->evt);
|
||||
|
||||
bt_buf_pull(buf, sizeof(*hdr));
|
||||
bt_buf_consume(buf, sizeof(*hdr));
|
||||
|
||||
switch (hdr->evt)
|
||||
{
|
||||
@@ -836,7 +837,7 @@ static void hci_event(FAR struct bt_buf_s *buf)
|
||||
break;
|
||||
}
|
||||
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
}
|
||||
|
||||
static int hci_tx_kthread(int argc, FAR char *argv[])
|
||||
@@ -863,7 +864,7 @@ static int hci_tx_kthread(int argc, FAR char *argv[])
|
||||
/* Get next command - wait if necessary */
|
||||
|
||||
buf = NULL;
|
||||
ret = bt_queue_recv(g_btdev.tx_queue, &buf);
|
||||
ret = bt_queue_receive(g_btdev.tx_queue, &buf);
|
||||
DEBUGASSERT(ret >= 0 && buf != NULL);
|
||||
UNUSED(ret);
|
||||
|
||||
@@ -879,7 +880,7 @@ static int hci_tx_kthread(int argc, FAR char *argv[])
|
||||
if (g_btdev.sent_cmd)
|
||||
{
|
||||
wlerr("ERROR: Uncleared pending sent_cmd\n");
|
||||
bt_buf_put(g_btdev.sent_cmd);
|
||||
bt_buf_release(g_btdev.sent_cmd);
|
||||
g_btdev.sent_cmd = NULL;
|
||||
}
|
||||
|
||||
@@ -898,10 +899,10 @@ static int hci_rx_kthread(int argc, FAR char *argv[])
|
||||
|
||||
while (1)
|
||||
{
|
||||
ret = bt_queue_recv(g_btdev.rx_queue, &buf);
|
||||
ret = bt_queue_receive(g_btdev.rx_queue, &buf);
|
||||
if (ret < 0)
|
||||
{
|
||||
wlerr("ERROR: bt_queue_recv() failed: %d\n", ret);
|
||||
wlerr("ERROR: bt_queue_receive() failed: %d\n", ret);
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -919,7 +920,7 @@ static int hci_rx_kthread(int argc, FAR char *argv[])
|
||||
|
||||
default:
|
||||
wlerr("ERROR: Unknown buf type %u\n", buf->type);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -1014,7 +1015,7 @@ static int hci_init(void)
|
||||
}
|
||||
|
||||
read_local_features_complete(rsp);
|
||||
bt_buf_put(rsp);
|
||||
bt_buf_release(rsp);
|
||||
|
||||
/* Read Local Version Information */
|
||||
|
||||
@@ -1025,7 +1026,7 @@ static int hci_init(void)
|
||||
}
|
||||
|
||||
read_local_ver_complete(rsp);
|
||||
bt_buf_put(rsp);
|
||||
bt_buf_release(rsp);
|
||||
|
||||
/* Read Bluetooth Address */
|
||||
|
||||
@@ -1036,7 +1037,7 @@ static int hci_init(void)
|
||||
}
|
||||
|
||||
read_bdaddr_complete(rsp);
|
||||
bt_buf_put(rsp);
|
||||
bt_buf_release(rsp);
|
||||
|
||||
/* For now we only support LE capable controllers */
|
||||
|
||||
@@ -1055,7 +1056,7 @@ static int hci_init(void)
|
||||
}
|
||||
|
||||
read_le_features_complete(rsp);
|
||||
bt_buf_put(rsp);
|
||||
bt_buf_release(rsp);
|
||||
|
||||
/* Read LE Buffer Size */
|
||||
|
||||
@@ -1066,7 +1067,7 @@ static int hci_init(void)
|
||||
}
|
||||
|
||||
le_read_buffer_size_complete(rsp);
|
||||
bt_buf_put(rsp);
|
||||
bt_buf_release(rsp);
|
||||
|
||||
buf = bt_hci_cmd_create(BT_HCI_OP_SET_EVENT_MASK, sizeof(*ev));
|
||||
if (!buf)
|
||||
@@ -1074,7 +1075,7 @@ static int hci_init(void)
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
ev = bt_buf_add(buf, sizeof(*ev));
|
||||
ev = bt_buf_extend(buf, sizeof(*ev));
|
||||
memset(ev, 0, sizeof(*ev));
|
||||
ev->events[0] |= 0x10; /* Disconnection Complete */
|
||||
ev->events[1] |= 0x08; /* Read Remote Version Information Complete */
|
||||
@@ -1099,7 +1100,7 @@ static int hci_init(void)
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
hbs = bt_buf_add(buf, sizeof(*hbs));
|
||||
hbs = bt_buf_extend(buf, sizeof(*hbs));
|
||||
memset(hbs, 0, sizeof(*hbs));
|
||||
hbs->acl_mtu = BT_HOST2LE16(BT_BUF_MAX_DATA -
|
||||
sizeof(struct bt_hci_acl_hdr_s) -
|
||||
@@ -1118,7 +1119,7 @@ static int hci_init(void)
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
enable = bt_buf_add(buf, sizeof(*enable));
|
||||
enable = bt_buf_extend(buf, sizeof(*enable));
|
||||
*enable = 0x01;
|
||||
|
||||
err = bt_hci_cmd_send_sync(BT_HCI_OP_SET_CTL_TO_HOST_FLOW, buf, NULL);
|
||||
@@ -1142,7 +1143,7 @@ static int hci_init(void)
|
||||
}
|
||||
|
||||
read_buffer_size_complete(rsp);
|
||||
bt_buf_put(rsp);
|
||||
bt_buf_release(rsp);
|
||||
}
|
||||
|
||||
buf = bt_hci_cmd_create(BT_HCI_OP_LE_WRITE_LE_HOST_SUPP, sizeof(*cp));
|
||||
@@ -1153,7 +1154,7 @@ static int hci_init(void)
|
||||
|
||||
/* Explicitly enable LE for dual-mode controllers */
|
||||
|
||||
cp = bt_buf_add(buf, sizeof *cp);
|
||||
cp = bt_buf_extend(buf, sizeof *cp);
|
||||
cp->le = 0x01;
|
||||
cp->simul = 0x00;
|
||||
|
||||
@@ -1205,8 +1206,8 @@ static void rx_queue_init(void)
|
||||
pid_t pid;
|
||||
int ret;
|
||||
|
||||
/* When a buffer is received from the Bluetooth driver via bt_input() on
|
||||
* the Rx queue and received by logic on the Rx kernel thread.
|
||||
/* When a buffer is received from the Bluetooth driver via bt_hci_receive()
|
||||
* on the Rx queue and received by logic on the Rx kernel thread.
|
||||
*/
|
||||
|
||||
g_btdev.rx_queue = NULL;
|
||||
@@ -1243,7 +1244,7 @@ int bt_initialize(void)
|
||||
int err;
|
||||
|
||||
DEBUGASSERT(dev != NULL);
|
||||
bt_buf_init();
|
||||
bt_buf_initialize();
|
||||
|
||||
cmd_queue_init();
|
||||
rx_queue_init();
|
||||
@@ -1317,7 +1318,7 @@ void bt_driver_unregister(FAR const struct bt_driver_s *dev)
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_input
|
||||
* Name: bt_hci_receive
|
||||
*
|
||||
* Description:
|
||||
* Called by the Bluetooth low-level driver when new data is received from
|
||||
@@ -1332,7 +1333,7 @@ void bt_driver_unregister(FAR const struct bt_driver_s *dev)
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void bt_input(FAR struct bt_buf_s *buf)
|
||||
void bt_hci_receive(FAR struct bt_buf_s *buf)
|
||||
{
|
||||
FAR struct bt_hci_evt_hdr_s *hdr;
|
||||
int prio = BT_NORMAL_PRIO;
|
||||
@@ -1345,7 +1346,7 @@ void bt_input(FAR struct bt_buf_s *buf)
|
||||
if (buf->type != BT_EVT)
|
||||
{
|
||||
wlerr("ERROR: Invalid buf type %u\n", buf->type);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1386,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_get(BT_CMD, g_btdev.dev->head_reserve);
|
||||
buf = bt_buf_alloc(BT_CMD, g_btdev.dev->head_reserve);
|
||||
if (!buf)
|
||||
{
|
||||
wlerr("ERROR: Cannot get free buffer\n");
|
||||
@@ -1398,7 +1399,7 @@ FAR struct bt_buf_s *bt_hci_cmd_create(uint16_t opcode, uint8_t param_len)
|
||||
buf->u.hci.opcode = opcode;
|
||||
buf->u.hci.sync = NULL;
|
||||
|
||||
hdr = bt_buf_add(buf, sizeof(*hdr));
|
||||
hdr = bt_buf_extend(buf, sizeof(*hdr));
|
||||
hdr->opcode = BT_HOST2LE16(opcode);
|
||||
hdr->param_len = param_len;
|
||||
|
||||
@@ -1426,7 +1427,7 @@ int bt_hci_cmd_send(uint16_t opcode, FAR struct bt_buf_s *buf)
|
||||
if (opcode == BT_HCI_OP_HOST_NUM_COMPLETED_PACKETS)
|
||||
{
|
||||
g_btdev.dev->send(g_btdev.dev, buf);
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1500,10 +1501,10 @@ int bt_hci_cmd_send_sync(uint16_t opcode, FAR struct bt_buf_s *buf,
|
||||
}
|
||||
else if (buf->u.hci.sync)
|
||||
{
|
||||
bt_buf_put(buf->u.hci.sync);
|
||||
bt_buf_release(buf->u.hci.sync);
|
||||
}
|
||||
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -1544,7 +1545,7 @@ int bt_start_advertising(uint8_t type, FAR const struct bt_eir_s *ad,
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
set_data = bt_buf_add(buf, sizeof(*set_data));
|
||||
set_data = bt_buf_extend(buf, sizeof(*set_data));
|
||||
|
||||
memset(set_data, 0, sizeof(*set_data));
|
||||
|
||||
@@ -1576,7 +1577,7 @@ send_scan_rsp:
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
scan_rsp = bt_buf_add(buf, sizeof(*scan_rsp));
|
||||
scan_rsp = bt_buf_extend(buf, sizeof(*scan_rsp));
|
||||
|
||||
memset(scan_rsp, 0, sizeof(*scan_rsp));
|
||||
|
||||
@@ -1603,7 +1604,7 @@ send_set_param:
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
set_param = bt_buf_add(buf, sizeof(*set_param));
|
||||
set_param = bt_buf_extend(buf, sizeof(*set_param));
|
||||
|
||||
memset(set_param, 0, sizeof(*set_param));
|
||||
set_param->min_interval = BT_HOST2LE16(0x0800);
|
||||
@@ -1620,7 +1621,7 @@ send_set_param:
|
||||
}
|
||||
|
||||
g_btdev.adv_enable = 0x01;
|
||||
memcpy(bt_buf_add(buf, 1), &g_btdev.adv_enable, 1);
|
||||
memcpy(bt_buf_extend(buf, 1), &g_btdev.adv_enable, 1);
|
||||
|
||||
return bt_hci_cmd_send_sync(BT_HCI_OP_LE_SET_ADV_ENABLE, buf, NULL);
|
||||
}
|
||||
@@ -1652,7 +1653,7 @@ int bt_stop_advertising(void)
|
||||
}
|
||||
|
||||
g_btdev.adv_enable = 0x00;
|
||||
memcpy(bt_buf_add(buf, 1), &g_btdev.adv_enable, 1);
|
||||
memcpy(bt_buf_extend(buf, 1), &g_btdev.adv_enable, 1);
|
||||
|
||||
return bt_hci_cmd_send_sync(BT_HCI_OP_LE_SET_ADV_ENABLE, buf, NULL);
|
||||
}
|
||||
@@ -1776,7 +1777,7 @@ int bt_le_scan_update(void)
|
||||
|
||||
void bt_conn_cb_register(FAR struct bt_conn_cb_s *cb)
|
||||
{
|
||||
cb->next = g_callback_list;
|
||||
cb->flink = g_callback_list;
|
||||
g_callback_list = cb;
|
||||
}
|
||||
|
||||
|
||||
@@ -144,9 +144,11 @@ struct bt_dev_s
|
||||
struct bt_conn_s; /* Forward reference */
|
||||
struct bt_conn_cb_s
|
||||
{
|
||||
CODE void (*connected)(FAR struct bt_conn_s *conn);
|
||||
CODE void (*disconnected)(FAR struct bt_conn_s *conn);
|
||||
FAR struct bt_conn_cb_s *next;
|
||||
FAR struct bt_conn_cb_s *flink;
|
||||
FAR void *context;
|
||||
|
||||
CODE void (*connected)(FAR struct bt_conn_s *conn, FAR void *context);
|
||||
CODE void (*disconnected)(FAR struct bt_conn_s *conn, FAR void *context);
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
|
||||
@@ -75,6 +75,7 @@
|
||||
****************************************************************************/
|
||||
|
||||
static FAR struct bt_l2cap_chan_s *g_channels;
|
||||
static FAR struct bt_l2cap_chan_s *g_default;
|
||||
|
||||
/****************************************************************************
|
||||
* Private Functions
|
||||
@@ -98,47 +99,82 @@ void bt_l2cap_chan_register(FAR struct bt_l2cap_chan_s *chan)
|
||||
{
|
||||
wlinfo("CID 0x%04x\n", chan->cid);
|
||||
|
||||
chan->next = g_channels;
|
||||
chan->flink = g_channels;
|
||||
g_channels = chan;
|
||||
}
|
||||
|
||||
void bt_l2cap_chan_default(FAR struct bt_l2cap_chan_s *chan)
|
||||
{
|
||||
g_default = chan;
|
||||
}
|
||||
|
||||
void bt_l2cap_connected(FAR struct bt_conn_s *conn)
|
||||
{
|
||||
FAR struct bt_l2cap_chan_s *chan;
|
||||
|
||||
for (chan = g_channels; chan; chan = chan->next)
|
||||
/* Notify all registered channels of the connection event */
|
||||
|
||||
for (chan = g_channels; chan; chan = chan->flink)
|
||||
{
|
||||
if (chan->connected)
|
||||
if (chan->connected != NULL)
|
||||
{
|
||||
chan->connected(conn);
|
||||
chan->connected(conn, chan->context, chan->cid);
|
||||
}
|
||||
}
|
||||
|
||||
/* Notify any default listener of the connection event */
|
||||
|
||||
chan = g_default;
|
||||
if (chan != NULL && chan->connected != NULL)
|
||||
{
|
||||
chan->connected(conn, chan->context, chan->cid);
|
||||
}
|
||||
}
|
||||
|
||||
void bt_l2cap_disconnected(FAR struct bt_conn_s *conn)
|
||||
{
|
||||
FAR struct bt_l2cap_chan_s *chan;
|
||||
|
||||
for (chan = g_channels; chan; chan = chan->next)
|
||||
/* Notify all registered channels of the disconnection event */
|
||||
|
||||
for (chan = g_channels; chan; chan = chan->flink)
|
||||
{
|
||||
if (chan->disconnected)
|
||||
if (chan->disconnected != NULL)
|
||||
{
|
||||
chan->disconnected(conn);
|
||||
chan->disconnected(conn, chan->context, chan->cid);
|
||||
}
|
||||
}
|
||||
|
||||
/* Notify any default listener of the disconnection event */
|
||||
|
||||
chan = g_default;
|
||||
if (chan != NULL && chan->disconnected != NULL)
|
||||
{
|
||||
chan->disconnected(conn, chan->context, chan->cid);
|
||||
}
|
||||
}
|
||||
|
||||
void bt_l2cap_encrypt_change(FAR struct bt_conn_s *conn)
|
||||
{
|
||||
FAR struct bt_l2cap_chan_s *chan;
|
||||
|
||||
for (chan = g_channels; chan; chan = chan->next)
|
||||
/* Notify all registered channels of the encryption change event */
|
||||
|
||||
for (chan = g_channels; chan; chan = chan->flink)
|
||||
{
|
||||
if (chan->encrypt_change)
|
||||
if (chan->encrypt_change != NULL)
|
||||
{
|
||||
chan->encrypt_change(conn);
|
||||
chan->encrypt_change(conn, chan->context, chan->cid);
|
||||
}
|
||||
}
|
||||
|
||||
/* Notify any default listener of the encryption change event */
|
||||
|
||||
chan = g_default;
|
||||
if (chan != NULL && chan->encrypt_change != NULL)
|
||||
{
|
||||
chan->encrypt_change(conn, chan->context, chan->cid);
|
||||
}
|
||||
}
|
||||
|
||||
struct bt_buf_s *bt_l2cap_create_pdu(FAR struct bt_conn_s *conn)
|
||||
@@ -146,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_get(BT_ACL_OUT, head_reserve);
|
||||
return bt_buf_alloc(BT_ACL_OUT, head_reserve);
|
||||
}
|
||||
|
||||
void bt_l2cap_send(FAR struct bt_conn_s *conn, uint16_t cid,
|
||||
@@ -154,7 +190,7 @@ void bt_l2cap_send(FAR struct bt_conn_s *conn, uint16_t cid,
|
||||
{
|
||||
FAR struct bt_l2cap_hdr_s *hdr;
|
||||
|
||||
hdr = bt_buf_push(buf, sizeof(*hdr));
|
||||
hdr = bt_buf_provide(buf, sizeof(*hdr));
|
||||
hdr->len = BT_HOST2LE16(buf->len - sizeof(*hdr));
|
||||
hdr->cid = BT_HOST2LE16(cid);
|
||||
|
||||
@@ -173,12 +209,12 @@ static void rej_not_understood(FAR struct bt_conn_s *conn, uint8_t ident)
|
||||
return;
|
||||
}
|
||||
|
||||
hdr = bt_buf_add(buf, sizeof(*hdr));
|
||||
hdr = bt_buf_extend(buf, sizeof(*hdr));
|
||||
hdr->code = BT_L2CAP_CMD_REJECT;
|
||||
hdr->ident = ident;
|
||||
hdr->len = BT_HOST2LE16(sizeof(*rej));
|
||||
|
||||
rej = bt_buf_add(buf, sizeof(*rej));
|
||||
rej = bt_buf_extend(buf, sizeof(*rej));
|
||||
rej->reason = BT_HOST2LE16(BT_L2CAP_REJ_NOT_UNDERSTOOD);
|
||||
|
||||
bt_l2cap_send(conn, BT_L2CAP_CID_LE_SIG, buf);
|
||||
@@ -266,12 +302,12 @@ static void le_conn_param_update_req(FAR struct bt_conn_s *conn,
|
||||
|
||||
result = le_validate_conn_params(min, max, latency, timeout);
|
||||
|
||||
hdr = bt_buf_add(buf, sizeof(*hdr));
|
||||
hdr = bt_buf_extend(buf, sizeof(*hdr));
|
||||
hdr->code = BT_L2CAP_CONN_PARAM_RSP;
|
||||
hdr->ident = ident;
|
||||
hdr->len = BT_HOST2LE16(sizeof(*rsp));
|
||||
|
||||
rsp = bt_buf_add(buf, sizeof(*rsp));
|
||||
rsp = bt_buf_extend(buf, sizeof(*rsp));
|
||||
memset(rsp, 0, sizeof(*rsp));
|
||||
rsp->result = BT_HOST2LE16(result);
|
||||
|
||||
@@ -283,7 +319,8 @@ static void le_conn_param_update_req(FAR struct bt_conn_s *conn,
|
||||
}
|
||||
}
|
||||
|
||||
static void le_sig(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
static void le_sig(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
FAR void *context, uint16_t cid)
|
||||
{
|
||||
struct bt_l2cap_sig_hdr_s *hdr = (FAR void *)buf->data;
|
||||
uint16_t len;
|
||||
@@ -295,7 +332,7 @@ static void le_sig(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
}
|
||||
|
||||
len = BT_LE162HOST(hdr->len);
|
||||
bt_buf_pull(buf, sizeof(*hdr));
|
||||
bt_buf_consume(buf, sizeof(*hdr));
|
||||
|
||||
wlinfo("LE signaling code 0x%02x ident %u len %u\n", hdr->code,
|
||||
hdr->ident, len);
|
||||
@@ -329,10 +366,10 @@ static void le_sig(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
}
|
||||
|
||||
drop:
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
}
|
||||
|
||||
void bt_l2cap_recv(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
void bt_l2cap_receive(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
{
|
||||
FAR struct bt_l2cap_hdr_s *hdr = (FAR void *)buf->data;
|
||||
FAR struct bt_l2cap_chan_s *chan;
|
||||
@@ -341,16 +378,18 @@ void bt_l2cap_recv(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
if (buf->len < sizeof(*hdr))
|
||||
{
|
||||
wlerr("ERROR: Too small L2CAP PDU received\n");
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
return;
|
||||
}
|
||||
|
||||
cid = BT_LE162HOST(hdr->cid);
|
||||
bt_buf_pull(buf, sizeof(*hdr));
|
||||
bt_buf_consume(buf, sizeof(*hdr));
|
||||
|
||||
wlinfo("Packet for CID %u len %u\n", cid, buf->len);
|
||||
|
||||
for (chan = g_channels; chan; chan = chan->next)
|
||||
/* Search for a subscriber to this channel */
|
||||
|
||||
for (chan = g_channels; chan != NULL; chan = chan->flink)
|
||||
{
|
||||
if (chan->cid == cid)
|
||||
{
|
||||
@@ -358,14 +397,23 @@ void bt_l2cap_recv(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf)
|
||||
}
|
||||
}
|
||||
|
||||
if (!chan)
|
||||
/* If there is no subscriber, then send all received frames to the default
|
||||
* listener (if one is registered).
|
||||
*/
|
||||
|
||||
if (chan == NULL)
|
||||
{
|
||||
wlwarn("Ignoring data for unknown CID 0x%04x\n", cid);
|
||||
bt_buf_put(buf);
|
||||
chan = g_default;
|
||||
}
|
||||
|
||||
if (chan == NULL)
|
||||
{
|
||||
wlwarn("WARNING: No subscriber to CID 0x%04x\n", cid);
|
||||
bt_buf_release(buf);
|
||||
return;
|
||||
}
|
||||
|
||||
chan->recv(conn, buf);
|
||||
chan->receive(conn, buf, chan->context, chan->cid);
|
||||
}
|
||||
|
||||
void bt_l2cap_update_conn_param(FAR struct bt_conn_s *conn)
|
||||
@@ -388,12 +436,12 @@ void bt_l2cap_update_conn_param(FAR struct bt_conn_s *conn)
|
||||
return;
|
||||
}
|
||||
|
||||
hdr = bt_buf_add(buf, sizeof(*hdr));
|
||||
hdr = bt_buf_extend(buf, sizeof(*hdr));
|
||||
hdr->code = BT_L2CAP_CONN_PARAM_REQ;
|
||||
hdr->ident = get_ident(conn);
|
||||
hdr->len = BT_HOST2LE16(sizeof(*req));
|
||||
|
||||
req = bt_buf_add(buf, sizeof(*req));
|
||||
req = bt_buf_extend(buf, sizeof(*req));
|
||||
req->min_interval = BT_HOST2LE16(LE_CONN_MIN_INTERVAL);
|
||||
req->max_interval = BT_HOST2LE16(LE_CONN_MAX_INTERVAL);
|
||||
req->latency = BT_HOST2LE16(LE_CONN_LATENCY);
|
||||
@@ -404,22 +452,22 @@ void bt_l2cap_update_conn_param(FAR struct bt_conn_s *conn)
|
||||
|
||||
int bt_l2cap_init(void)
|
||||
{
|
||||
int err;
|
||||
int ret;
|
||||
|
||||
static struct bt_l2cap_chan_s chan =
|
||||
{
|
||||
.cid = BT_L2CAP_CID_LE_SIG,
|
||||
.recv = le_sig,
|
||||
.cid = BT_L2CAP_CID_LE_SIG,
|
||||
.receive = le_sig,
|
||||
};
|
||||
|
||||
bt_att_init();
|
||||
bt_att_initialize();
|
||||
|
||||
err = bt_smp_init();
|
||||
if (err)
|
||||
ret = bt_smp_initialize();
|
||||
if (ret < 0)
|
||||
{
|
||||
return err;
|
||||
return ret;
|
||||
}
|
||||
|
||||
bt_l2cap_chan_register(&chan);
|
||||
return 0;
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -100,24 +100,32 @@ begin_packed_struct struct bt_l2cap_conn_param_rsp_s
|
||||
|
||||
struct bt_l2cap_chan_s
|
||||
{
|
||||
FAR struct bt_l2cap_chan_s *flink;
|
||||
FAR void *context;
|
||||
uint16_t cid;
|
||||
|
||||
CODE void (*connected)(FAR struct bt_conn_s *conn);
|
||||
CODE void (*disconnected)(FAR struct bt_conn_s *conn);
|
||||
CODE void (*encrypt_change)(FAR struct bt_conn_s *conn);
|
||||
CODE void (*recv)(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf);
|
||||
|
||||
FAR struct bt_l2cap_chan_s *next;
|
||||
CODE void (*connected)(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid);
|
||||
CODE void (*disconnected)(FAR struct bt_conn_s *conn, FAR void *context,
|
||||
uint16_t cid);
|
||||
CODE void (*encrypt_change)(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid);
|
||||
CODE void (*receive)(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf,
|
||||
FAR void *context, uint16_t cid);
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
* Public Function Prototypes
|
||||
****************************************************************************/
|
||||
|
||||
/* Register a fixed L2CAP channel for L2CAP */
|
||||
/* Register a fixed L2CAP channel handler for L2CAP */
|
||||
|
||||
void bt_l2cap_chan_register(FAR struct bt_l2cap_chan_s *chan);
|
||||
|
||||
/* Register a default L2CAP channel handle for L2CAP */
|
||||
|
||||
void bt_l2cap_chan_default(FAR struct bt_l2cap_chan_s *chan);
|
||||
|
||||
/* Notify L2CAP channels of a new connection */
|
||||
|
||||
void bt_l2cap_connected(FAR struct bt_conn_s *conn);
|
||||
@@ -141,7 +149,7 @@ void bt_l2cap_send(FAR struct bt_conn_s *conn, uint16_t cid,
|
||||
|
||||
/* Receive a new L2CAP PDU from a connection */
|
||||
|
||||
void bt_l2cap_recv(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf);
|
||||
void bt_l2cap_receive(FAR struct bt_conn_s *conn, FAR struct bt_buf_s *buf);
|
||||
|
||||
/* Perform connection parameter update request */
|
||||
|
||||
|
||||
+152
-40
@@ -62,8 +62,11 @@
|
||||
#include <nuttx/net/radiodev.h>
|
||||
#include <nuttx/net/bluetooth.h>
|
||||
#include <nuttx/net/sixlowpan.h>
|
||||
#include <nuttx/wireless/bt_core.h>
|
||||
|
||||
#include "bt_hcicore.h"
|
||||
#include "bt_l2cap.h"
|
||||
#include "bt_conn.h"
|
||||
#include "bt_ioctl.h"
|
||||
|
||||
#if defined(CONFIG_NET_6LOWPAN) || defined(CONFIG_NET_BLUETOOTH)
|
||||
@@ -113,16 +116,17 @@ struct btnet_driver_s
|
||||
{
|
||||
/* This holds the information visible to the NuttX network */
|
||||
|
||||
struct radio_driver_s bd_dev; /* Interface understood by the network */
|
||||
/* Cast compatible with struct btnet_driver_s */
|
||||
struct radio_driver_s bd_dev; /* Interface understood by the network */
|
||||
/* Cast compatible with struct btnet_driver_s */
|
||||
|
||||
/* For internal use by this driver */
|
||||
|
||||
sem_t bd_exclsem; /* Exclusive access to struct */
|
||||
bool bd_bifup; /* true:ifup false:ifdown */
|
||||
WDOG_ID bd_txpoll; /* TX poll timer */
|
||||
struct work_s bd_pollwork; /* Defer poll work to the work queue */
|
||||
FAR struct bt_conn_cb_s bd_hcicb; /* Connection status callbacks */
|
||||
sem_t bd_exclsem; /* Exclusive access to struct */
|
||||
bool bd_bifup; /* true:ifup false:ifdown */
|
||||
WDOG_ID bd_txpoll; /* TX poll timer */
|
||||
struct work_s bd_pollwork; /* Defer poll work to the work queue */
|
||||
struct bt_conn_cb_s bd_hcicb; /* HCI connection status callbacks */
|
||||
struct bt_l2cap_chan_s bd_l2capcb; /* L2CAP status callbacks */
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
@@ -136,10 +140,23 @@ static inline void btnet_netmask(FAR struct net_driver_s *dev);
|
||||
|
||||
/* Bluetooth callback functions ***************************************/
|
||||
|
||||
static int btnet_rxframe(FAR struct btnet_driver_s *maccb,
|
||||
FAR struct bluetooth_frame_meta_s *meta);
|
||||
static void btnet_connected(FAR struct bt_conn_s *conn);
|
||||
static void btnet_disconnected(FAR struct bt_conn_s *conn);
|
||||
/* L2CAP callbacks */
|
||||
|
||||
static void btnet_l2cap_connected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid);
|
||||
static void btnet_l2cap_disconnected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid);
|
||||
static void btnet_l2cap_encrypt_change(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid);
|
||||
static void btnet_l2cap_receive(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf, FAR void *context, uint16_t cid);
|
||||
|
||||
/* HCI callbacks */
|
||||
|
||||
static void btnet_hci_connected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context);
|
||||
static void btnet_hci_disconnected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context);
|
||||
|
||||
/* Network interface support ************************************************/
|
||||
/* Common TX logic */
|
||||
@@ -252,10 +269,50 @@ static inline void btnet_netmask(FAR struct net_driver_s *dev)
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: btnet_rxframe
|
||||
* Name: btnet_hci_connect/disconnect/encrypt_change
|
||||
*
|
||||
* Description:
|
||||
* Handle received frames forward by the Bluetooth stack.
|
||||
* There are callbacks that are involved by the core HCI layer when a
|
||||
* change is detected in the connection status or encryption.
|
||||
*
|
||||
* Input Parameters:
|
||||
* conn - The connection whose
|
||||
*
|
||||
* Returned Value:
|
||||
* None
|
||||
*
|
||||
* Assumptions:
|
||||
* No assumption should be made about the thread of execution that these
|
||||
* are called from
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void btnet_l2cap_connected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid)
|
||||
{
|
||||
wlinfo("Connected\n");
|
||||
#warning Missing logic
|
||||
}
|
||||
|
||||
static void btnet_l2cap_disconnected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid)
|
||||
{
|
||||
wlinfo("Disconnected\n");
|
||||
#warning Missing logic
|
||||
}
|
||||
|
||||
static void btnet_l2cap_encrypt_change(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid)
|
||||
{
|
||||
wlinfo("Encryption change\n");
|
||||
#warning Missing logic
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: btnet_l2cap_receive
|
||||
*
|
||||
* Description:
|
||||
* Handle received frames forward by the Bluetooth L2CAP layer.
|
||||
*
|
||||
* Returned Value:
|
||||
* Zero (OK) is returned on success; a negated errno value is returned on
|
||||
@@ -265,24 +322,55 @@ static inline void btnet_netmask(FAR struct net_driver_s *dev)
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static int btnet_rxframe(FAR struct btnet_driver_s *priv,
|
||||
FAR struct bluetooth_frame_meta_s *meta)
|
||||
static void btnet_l2cap_receive(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf,
|
||||
FAR void *context, uint16_t cid)
|
||||
{
|
||||
FAR struct iob_s *iob;
|
||||
int ret;
|
||||
FAR struct btnet_driver_s *priv;
|
||||
FAR struct iob_s *frame;
|
||||
struct bluetooth_frame_meta_s meta;
|
||||
int ret = -ENODEV;
|
||||
|
||||
DEBUGASSERT(priv != NULL && meta != NULL);
|
||||
wlinfo("Received frame\n");
|
||||
|
||||
DEBUGASSERT(conn != NULL && buf != NULL && buf->frame != NULL &&
|
||||
context != NULL && cid < UINT8_MAX);
|
||||
|
||||
/* Detach the IOB frame from the buffer structure */
|
||||
|
||||
frame = buf->frame;
|
||||
buf->frame = NULL;
|
||||
|
||||
/* Ignore the frame if the network is not up */
|
||||
|
||||
priv = (FAR struct btnet_driver_s *)context;
|
||||
if (!priv->bd_bifup)
|
||||
{
|
||||
wlwarn("WARNING: Dropped... Network is down\n");
|
||||
return -ENETDOWN;
|
||||
goto drop;
|
||||
}
|
||||
|
||||
/* Make sure that the size/offset data matches the buffer structure data.
|
||||
* REVISIT: Wouldn't it be better to just have one copy rather than having
|
||||
* to synchronize?
|
||||
*/
|
||||
|
||||
frame->io_len = buf->len;
|
||||
frame->io_pktlen = buf->len;
|
||||
frame->io_offset = (unsigned int)
|
||||
((uintptr_t)buf->data - (uintptr_t)frame->io_data);
|
||||
|
||||
DEBUGASSERT(frame->io_len <= CONFIG_IOB_BUFSIZE);
|
||||
DEBUGASSERT(frame->io_offset < CONFIG_IOB_BUFSIZE);
|
||||
|
||||
/* Construct the frame meta data.
|
||||
* REVISIT: Where do we get the channel number?
|
||||
*/
|
||||
|
||||
BLUETOOTH_ADDRCOPY(meta.bm_raddr.val, conn->src.val);
|
||||
meta.bm_channel = cid;
|
||||
|
||||
/* Transfer the frame to the network logic */
|
||||
#warning Missing logic
|
||||
|
||||
net_lock();
|
||||
|
||||
@@ -292,14 +380,13 @@ static int btnet_rxframe(FAR struct btnet_driver_s *priv,
|
||||
* frame and return success.
|
||||
*/
|
||||
|
||||
ret = bluetooth_input(&priv->bd_dev, iob, (FAR void *)meta);
|
||||
if (ret < 0)
|
||||
ret = bluetooth_input(&priv->bd_dev, frame, (FAR void *)&meta);
|
||||
#endif
|
||||
#ifdef CONFIG_NET_6LOWPAN
|
||||
if (ret < 0)
|
||||
{
|
||||
/* If the frame is not a 6LoWPAN frame, then return an error. The
|
||||
* first byte following the MAC head at the io_offset should be a
|
||||
* valid IPHC header.
|
||||
/* If the frame is not a 6LoWPAN frame, then thefirst byte at the
|
||||
* io_offset should be a valid IPHC header.
|
||||
*/
|
||||
|
||||
if ((iob->io_data[iob->io_offset] & SIXLOWPAN_DISPATCH_NALP_MASK) ==
|
||||
@@ -320,25 +407,36 @@ static int btnet_rxframe(FAR struct btnet_driver_s *priv,
|
||||
ret = sixlowpan_input(&priv->bd_dev, iob, (FAR void *)meta);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
drop:
|
||||
|
||||
/* Handle errors */
|
||||
|
||||
if (ret < 0)
|
||||
#endif
|
||||
{
|
||||
net_unlock();
|
||||
return ret;
|
||||
iob_free(frame);
|
||||
|
||||
/* Increment statistics */
|
||||
|
||||
NETDEV_RXDROPPED(&priv->bd_dev.r_dev);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Increment statistics */
|
||||
|
||||
NETDEV_RXPACKETS(&priv->bd_dev.r_dev);
|
||||
NETDEV_RXIPV6(&priv->bd_dev.r_dev);
|
||||
}
|
||||
|
||||
/* Increment statistics */
|
||||
|
||||
NETDEV_RXPACKETS(&priv->bd_dev.r_dev);
|
||||
NETDEV_RXIPV6(&priv->bd_dev.r_dev);
|
||||
/* Release our reference on the buffer */
|
||||
|
||||
bt_buf_release(buf);
|
||||
net_unlock();
|
||||
return OK;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: btnet_txpoll_callback
|
||||
* Name: btnet_hci_connect/disconnect
|
||||
*
|
||||
* Description:
|
||||
* There are callbacks that are involved by the core HCI layer when a
|
||||
@@ -356,13 +454,17 @@ static int btnet_rxframe(FAR struct btnet_driver_s *priv,
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void btnet_connected(FAR struct bt_conn_s *conn)
|
||||
static void btnet_hci_connected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context)
|
||||
{
|
||||
wlinfo("Connected\n");
|
||||
#warning Missing logic
|
||||
}
|
||||
|
||||
static void btnet_disconnected(FAR struct bt_conn_s *conn)
|
||||
static void btnet_hci_disconnected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context)
|
||||
{
|
||||
wlinfo("Disconnected\n");
|
||||
#warning Missing logic
|
||||
}
|
||||
|
||||
@@ -914,6 +1016,7 @@ int bt_netdev_register(void)
|
||||
FAR struct radio_driver_s *radio;
|
||||
FAR struct net_driver_s *dev;
|
||||
FAR struct bt_conn_cb_s *hcicb;
|
||||
FAR struct bt_l2cap_chan_s *l2capcb;
|
||||
int ret;
|
||||
|
||||
/* Get the interface structure associated with this interface number. */
|
||||
@@ -946,13 +1049,22 @@ int bt_netdev_register(void)
|
||||
/* Connection status change callbacks */
|
||||
|
||||
hcicb = &priv->bd_hcicb;
|
||||
hcicb->connected = btnet_connected;
|
||||
hcicb->disconnected = btnet_disconnected;
|
||||
hcicb->context = priv;
|
||||
hcicb->connected = btnet_hci_connected;
|
||||
hcicb->disconnected = btnet_hci_disconnected;
|
||||
|
||||
bt_conn_cb_register(hcicb);
|
||||
|
||||
/* REVISIT: When and where to we register to get frames on a connection? */
|
||||
#warning Missing logic
|
||||
/* L2CAP status change callbacks */
|
||||
|
||||
l2capcb = &priv->bd_l2capcb;
|
||||
l2capcb->context = priv;
|
||||
l2capcb->connected = btnet_l2cap_connected;
|
||||
l2capcb->disconnected = btnet_l2cap_disconnected;
|
||||
l2capcb->encrypt_change = btnet_l2cap_encrypt_change;
|
||||
l2capcb->receive = btnet_l2cap_receive;
|
||||
|
||||
bt_l2cap_chan_default(l2capcb);
|
||||
|
||||
/* Create a watchdog for timing polling for and timing of transmissions */
|
||||
|
||||
|
||||
@@ -64,9 +64,11 @@
|
||||
* Private Types
|
||||
****************************************************************************/
|
||||
|
||||
/* A message is just a buffer structure */
|
||||
|
||||
struct bt_bufmsg_s
|
||||
{
|
||||
FAR struct iob_s *iob;
|
||||
FAR struct bt_buf_s *buf;
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
@@ -119,7 +121,7 @@ int bt_queue_open(FAR const char *name, int oflags, int nmsgs,
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_queue_recv
|
||||
* Name: bt_queue_receive
|
||||
*
|
||||
* Description:
|
||||
* Block until the next buffer is received on the queue.
|
||||
@@ -134,7 +136,7 @@ int bt_queue_open(FAR const char *name, int oflags, int nmsgs,
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int bt_queue_recv(mqd_t mqd, FAR struct bt_buf_s **buf)
|
||||
int bt_queue_receive(mqd_t mqd, FAR struct bt_buf_s **buf)
|
||||
{
|
||||
union
|
||||
{
|
||||
@@ -142,7 +144,6 @@ int bt_queue_recv(mqd_t mqd, FAR struct bt_buf_s **buf)
|
||||
char msgbuf[BT_MSGSIZE];
|
||||
} u;
|
||||
|
||||
FAR struct bt_buf_s *retbuf;
|
||||
ssize_t msgsize;
|
||||
int priority;
|
||||
int ret;
|
||||
@@ -158,17 +159,16 @@ int bt_queue_recv(mqd_t mqd, FAR struct bt_buf_s **buf)
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* Only message buffer messages are expected */
|
||||
/* Only buffers are expected as messages and all messages should have an
|
||||
* attached IOB frame.
|
||||
*/
|
||||
|
||||
DEBUGASSERT(msgsize == sizeof(struct bt_bufmsg_s));
|
||||
DEBUGASSERT(u.msg.iob != NULL);
|
||||
DEBUGASSERT(u.msg.buf->frame != NULL);
|
||||
|
||||
/* A few more sanity checks, then return the buffer */
|
||||
/* Return the buffer */
|
||||
|
||||
retbuf = (FAR struct bt_buf_s *)u.msg.iob->io_data;
|
||||
DEBUGASSERT(retbuf->iob == u.msg.iob);
|
||||
|
||||
*buf = retbuf;
|
||||
*buf = u.msg.buf;
|
||||
return OK;
|
||||
}
|
||||
|
||||
@@ -197,11 +197,11 @@ int bt_queue_send(mqd_t mqd, FAR struct bt_buf_s *buf, int priority)
|
||||
struct bt_bufmsg_s msg;
|
||||
int ret;
|
||||
|
||||
DEBUGASSERT(mqd != NULL && buf != NULL && buf->iob != NULL);
|
||||
DEBUGASSERT(mqd != NULL && buf != NULL && buf->frame != NULL);
|
||||
|
||||
/* Format and send the buffer message */
|
||||
|
||||
msg.iob = buf->iob;
|
||||
msg.buf = buf;
|
||||
ret = nxmq_send(mqd, (FAR const char *)&msg, sizeof(struct bt_bufmsg_s),
|
||||
priority);
|
||||
if (ret < 0)
|
||||
|
||||
@@ -105,7 +105,7 @@ int bt_queue_open(FAR const char *name, int oflags, int nmsgs,
|
||||
FAR mqd_t *mqd);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_queue_recv
|
||||
* Name: bt_queue_receive
|
||||
*
|
||||
* Description:
|
||||
* Block until the next buffer is received on the queue.
|
||||
@@ -120,7 +120,7 @@ int bt_queue_open(FAR const char *name, int oflags, int nmsgs,
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int bt_queue_recv(mqd_t mqd, FAR struct bt_buf_s **buf);
|
||||
int bt_queue_receive(mqd_t mqd, FAR struct bt_buf_s **buf);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: bt_queue_send
|
||||
|
||||
+35
-27
@@ -179,11 +179,15 @@ static uint8_t smp_ident_addr_info(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf);
|
||||
static uint8_t smp_security_request(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf);
|
||||
static void bt_smp_recv(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf);
|
||||
static void bt_smp_connected(FAR struct bt_conn_s *conn);
|
||||
static void bt_smp_disconnected(FAR struct bt_conn_s *conn);
|
||||
static void bt_smp_encrypt_change(FAR FAR struct bt_conn_s *conn);
|
||||
static void bt_smp_receive(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf, FAR void *context,
|
||||
uint16_t cid);
|
||||
static void bt_smp_connected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid);
|
||||
static void bt_smp_disconnected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid);
|
||||
static void bt_smp_encrypt_change(FAR FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid);
|
||||
#ifdef CONFIG_BLUETOOTH_SMP_SELFTEST
|
||||
static void swap_buf(FAR const uint8_t *src, FAR uint8_t *dst,
|
||||
uint16_t len);
|
||||
@@ -373,7 +377,7 @@ static int le_encrypt(const uint8_t key[16], const uint8_t plaintext[16],
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
cp = bt_buf_add(buf, sizeof(*cp));
|
||||
cp = bt_buf_extend(buf, sizeof(*cp));
|
||||
memcpy(cp->key, key, sizeof(cp->key));
|
||||
memcpy(cp->plaintext, plaintext, sizeof(cp->plaintext));
|
||||
|
||||
@@ -385,7 +389,7 @@ static int le_encrypt(const uint8_t key[16], const uint8_t plaintext[16],
|
||||
|
||||
rp = (void *)rsp->data;
|
||||
memcpy(enc_data, rp->enc_data, sizeof(rp->enc_data));
|
||||
bt_buf_put(rsp);
|
||||
bt_buf_release(rsp);
|
||||
|
||||
wlinfo("enc_data %s\n", h(enc_data, 16));
|
||||
|
||||
@@ -418,7 +422,7 @@ static int le_rand(FAR void *buf, size_t len)
|
||||
}
|
||||
|
||||
memcpy(ptr, rp->rand, copy);
|
||||
bt_buf_put(rsp);
|
||||
bt_buf_release(rsp);
|
||||
|
||||
len -= copy;
|
||||
ptr += copy;
|
||||
@@ -532,7 +536,7 @@ static FAR struct bt_buf_s *bt_smp_create_pdu(FAR struct bt_conn_s *conn,
|
||||
return NULL;
|
||||
}
|
||||
|
||||
hdr = bt_buf_add(buf, sizeof(*hdr));
|
||||
hdr = bt_buf_extend(buf, sizeof(*hdr));
|
||||
hdr->code = op;
|
||||
|
||||
return buf;
|
||||
@@ -549,7 +553,7 @@ static void send_err_rsp(FAR struct bt_conn_s *conn, uint8_t reason)
|
||||
return;
|
||||
}
|
||||
|
||||
rsp = bt_buf_add(buf, sizeof(*rsp));
|
||||
rsp = bt_buf_extend(buf, sizeof(*rsp));
|
||||
rsp->reason = reason;
|
||||
|
||||
bt_l2cap_send(conn, BT_L2CAP_CID_SMP, buf);
|
||||
@@ -603,7 +607,7 @@ static uint8_t smp_pairing_req(FAR struct bt_conn_s *conn,
|
||||
return BT_SMP_ERR_UNSPECIFIED;
|
||||
}
|
||||
|
||||
rsp = bt_buf_add(rsp_buf, sizeof(*rsp));
|
||||
rsp = bt_buf_extend(rsp_buf, sizeof(*rsp));
|
||||
|
||||
/* For JustWorks pairing simplify rsp parameters. TODO: needs to be reworked
|
||||
* later on.
|
||||
@@ -652,7 +656,7 @@ static uint8_t smp_send_pairing_confirm(FAR struct bt_conn_s *conn)
|
||||
return BT_SMP_ERR_UNSPECIFIED;
|
||||
}
|
||||
|
||||
req = bt_buf_add(rsp_buf, sizeof(*req));
|
||||
req = bt_buf_extend(rsp_buf, sizeof(*req));
|
||||
|
||||
if (conn->role == BT_HCI_ROLE_MASTER)
|
||||
{
|
||||
@@ -668,7 +672,7 @@ static uint8_t smp_send_pairing_confirm(FAR struct bt_conn_s *conn)
|
||||
err = smp_c1(smp->tk, smp->prnd, smp->preq, smp->prsp, ia, ra, req->val);
|
||||
if (err)
|
||||
{
|
||||
bt_buf_put(rsp_buf);
|
||||
bt_buf_release(rsp_buf);
|
||||
return BT_SMP_ERR_UNSPECIFIED;
|
||||
}
|
||||
|
||||
@@ -715,7 +719,7 @@ static uint8_t smp_send_pairing_random(FAR struct bt_conn_s *conn)
|
||||
return BT_SMP_ERR_UNSPECIFIED;
|
||||
}
|
||||
|
||||
req = bt_buf_add(rsp_buf, sizeof(*req));
|
||||
req = bt_buf_extend(rsp_buf, sizeof(*req));
|
||||
memcpy(req->val, smp->prnd, sizeof(req->val));
|
||||
|
||||
bt_l2cap_send(conn, BT_L2CAP_CID_SMP, rsp_buf);
|
||||
@@ -895,7 +899,7 @@ static void bt_smp_distribute_keys(FAR struct bt_conn_s *conn)
|
||||
return;
|
||||
}
|
||||
|
||||
info = bt_buf_add(buf, sizeof(struct bt_smp_encrypt_info_s));
|
||||
info = bt_buf_extend(buf, sizeof(struct bt_smp_encrypt_info_s));
|
||||
memcpy(info->ltk, keys->slave_ltk.val, sizeof(info->ltk));
|
||||
|
||||
bt_l2cap_send(conn, BT_L2CAP_CID_SMP, buf);
|
||||
@@ -908,7 +912,7 @@ static void bt_smp_distribute_keys(FAR struct bt_conn_s *conn)
|
||||
return;
|
||||
}
|
||||
|
||||
ident = bt_buf_add(buf, sizeof(struct bt_smp_master_ident_s));
|
||||
ident = bt_buf_extend(buf, sizeof(struct bt_smp_master_ident_s));
|
||||
ident->rand = keys->slave_ltk.rand;
|
||||
ident->ediv = keys->slave_ltk.ediv;
|
||||
|
||||
@@ -1080,8 +1084,9 @@ pair:
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void bt_smp_recv(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf)
|
||||
static void bt_smp_receive(FAR struct bt_conn_s *conn,
|
||||
FAR struct bt_buf_s *buf, FAR void *context,
|
||||
uint16_t cid)
|
||||
{
|
||||
FAR struct bt_smp_hdr_s *hdr = (FAR void *)buf->data;
|
||||
FAR struct bt_smp_s *smp = conn->smp;
|
||||
@@ -1095,7 +1100,7 @@ static void bt_smp_recv(FAR struct bt_conn_s *conn,
|
||||
|
||||
wlinfo("Received SMP code 0x%02x len %u\n", hdr->code, buf->len);
|
||||
|
||||
bt_buf_pull(buf, sizeof(*hdr));
|
||||
bt_buf_consume(buf, sizeof(*hdr));
|
||||
|
||||
if (hdr->code >= NHANDLERS || !g_smp_handlers[hdr->code].func)
|
||||
{
|
||||
@@ -1138,10 +1143,11 @@ static void bt_smp_recv(FAR struct bt_conn_s *conn,
|
||||
}
|
||||
|
||||
done:
|
||||
bt_buf_put(buf);
|
||||
bt_buf_release(buf);
|
||||
}
|
||||
|
||||
static void bt_smp_connected(FAR struct bt_conn_s *conn)
|
||||
static void bt_smp_connected(FAR struct bt_conn_s *conn, FAR void *context,
|
||||
uint16_t cid)
|
||||
{
|
||||
int i;
|
||||
|
||||
@@ -1176,7 +1182,8 @@ static void bt_smp_connected(FAR struct bt_conn_s *conn)
|
||||
wlerr("ERROR: No available SMP context for conn %p\n", conn);
|
||||
}
|
||||
|
||||
static void bt_smp_disconnected(FAR struct bt_conn_s *conn)
|
||||
static void bt_smp_disconnected(FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid)
|
||||
{
|
||||
struct bt_smp_s *smp = conn->smp;
|
||||
|
||||
@@ -1191,7 +1198,8 @@ static void bt_smp_disconnected(FAR struct bt_conn_s *conn)
|
||||
memset(smp, 0, sizeof(*smp));
|
||||
}
|
||||
|
||||
static void bt_smp_encrypt_change(FAR FAR struct bt_conn_s *conn)
|
||||
static void bt_smp_encrypt_change(FAR FAR struct bt_conn_s *conn,
|
||||
FAR void *context, uint16_t cid)
|
||||
{
|
||||
struct bt_smp_s *smp = conn->smp;
|
||||
|
||||
@@ -1539,12 +1547,12 @@ static inline int smp_self_test(void)
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
|
||||
int bt_smp_init(void)
|
||||
int bt_smp_initialize(void)
|
||||
{
|
||||
static struct bt_l2cap_chan_s chan =
|
||||
{
|
||||
.cid = BT_L2CAP_CID_SMP,
|
||||
.recv = bt_smp_recv,
|
||||
.receive = bt_smp_receive,
|
||||
.connected = bt_smp_connected,
|
||||
.disconnected = bt_smp_disconnected,
|
||||
.encrypt_change = bt_smp_encrypt_change,
|
||||
@@ -1569,7 +1577,7 @@ int bt_smp_send_security_req(FAR struct bt_conn_s *conn)
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
req = bt_buf_add(req_buf, sizeof(struct bt_smp_security_request_s));
|
||||
req = bt_buf_extend(req_buf, sizeof(struct bt_smp_security_request_s));
|
||||
req->auth_req = BT_SMP_AUTH_BONDING;
|
||||
bt_l2cap_send(conn, BT_L2CAP_CID_SMP, req_buf);
|
||||
|
||||
@@ -1595,7 +1603,7 @@ int bt_smp_send_pairing_req(FAR struct bt_conn_s *conn)
|
||||
return -ENOBUFS;
|
||||
}
|
||||
|
||||
req = bt_buf_add(req_buf, sizeof(*req));
|
||||
req = bt_buf_extend(req_buf, sizeof(*req));
|
||||
|
||||
/* For JustWorks pairing simplify req parameters. TODO: needs to be reworked
|
||||
* later on
|
||||
|
||||
@@ -172,8 +172,8 @@ begin_packed_struct struct bt_smp_security_request_s
|
||||
****************************************************************************/
|
||||
|
||||
bool bt_smp_irk_matches(FAR const uint8_t irk[16], FAR const bt_addr_t *addr);
|
||||
int bt_smp_send_pairing_req(FAR struct bt_conn_s *conn);
|
||||
int bt_smp_send_security_req(FAR struct bt_conn_s *conn);
|
||||
int bt_smp_init(void);
|
||||
int bt_smp_send_pairing_req(FAR struct bt_conn_s *conn);
|
||||
int bt_smp_send_security_req(FAR struct bt_conn_s *conn);
|
||||
int bt_smp_initialize(void);
|
||||
|
||||
#endif /* __WIRELESS_BLUETOOTH_BT_SMP_H */
|
||||
|
||||
@@ -29,8 +29,8 @@ config IEEE802154_PRIMITIVE_IRQRESERVE
|
||||
default 0
|
||||
depends on EXPERIMENTAL
|
||||
---help---
|
||||
If primitves can be allocated from interrupt handlers, then this
|
||||
specifies the number of pre-allocatd meta-data structures that are
|
||||
If primitives can be allocated from interrupt handlers, then this
|
||||
specifies the number of pre-allocated meta-data structures that are
|
||||
reserved for for use only by interrupt handlers. This may be zero to
|
||||
reserve no meta-data structures for interrupt handlers. In that case,
|
||||
the allocation will fail if tasking logic has allocated them all.
|
||||
|
||||
@@ -159,7 +159,7 @@ void ieee802154_primitivepool_initialize(void)
|
||||
int remaining = CONFIG_IEEE802154_PRIMITIVE_PREALLOC;
|
||||
|
||||
#if CONFIG_IEEE802154_PRIMITIVE_PREALLOC > CONFIG_IEEE802154_PRIMITIVE_IRQRESERVE
|
||||
/* Initialize g_primfree, thelist of primitive structures that are available
|
||||
/* Initialize g_primfree, the list of primitive structures that are available
|
||||
* for general use.
|
||||
*/
|
||||
|
||||
@@ -324,7 +324,7 @@ FAR struct ieee802154_primitive_s *ieee802154_primitive_allocate(void)
|
||||
}
|
||||
|
||||
/* We have successfully allocated memory from some source.
|
||||
* Zero and tag the alloated primitive structure.
|
||||
* Zero and tag the allocated primitive structure.
|
||||
*/
|
||||
|
||||
prim->pool = pool;
|
||||
|
||||
Reference in New Issue
Block a user