All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCHv3 0/6] EFS: extended flow specification option support
@ 2011-10-13 13:18 Emeltchenko Andrei
  2011-10-13 13:18 ` [PATCHv3 1/6] Bluetooth: EFS: definitions and headers Emeltchenko Andrei
                   ` (5 more replies)
  0 siblings, 6 replies; 9+ messages in thread
From: Emeltchenko Andrei @ 2011-10-13 13:18 UTC (permalink / raw)
  To: linux-bluetooth

From: Andrei Emeltchenko <andrei.emeltchenko@intel.com>

Implementation of EFS based upon series of patches sent upstream in Aug 2010
by Haijun Liu.

http://marc.info/?a=128277503500005&r=1&w=2

Changes:
	* RFC: initial release
	* RFCv2: rebase & take care about comments:
		- use flag in l2cap_chan instead of variable
		- move channel init out from parse_conf_req
		- other style fixes
	* PATCHv1: support only Best Effort channels for now.
	* PATCHv2: disable_flowspec -> enable_hs, style fixes
	* PATCHv3: rebase, split functionality to appropriate
		patches, taking comments from ML.

L2CAP sequence looks like the one below:
(my patches for decoding EFS have been applied to hcidump)

...
< ACL data: handle 1 flags 0x00 dlen 10
    L2CAP(s): Info req: type 2
> ACL data: handle 1 flags 0x02 dlen 16
    L2CAP(s): Info rsp: type 2 result 0
      Extended feature mask 0x00f8
        Enhanced Retransmission mode
        Streaming mode
        FCS Option
        Extended Flow Specification
        Fixed Channels
< ACL data: handle 1 flags 0x00 dlen 10
    L2CAP(s): Info req: type 3
> ACL data: handle 1 flags 0x02 dlen 20
    L2CAP(s): Info rsp: type 3 result 0
      Fixed channel list
< ACL data: handle 1 flags 0x00 dlen 12
    L2CAP(s): Connect req: psm 4113 scid 0x0040
> ACL data: handle 1 flags 0x02 dlen 16
    L2CAP(s): Connect rsp: dcid 0x0040 scid 0x0040 result 1 status 0
      Connection pending - No futher information available
> ACL data: handle 1 flags 0x02 dlen 10
    L2CAP(s): Info req: type 2
< ACL data: handle 1 flags 0x00 dlen 16
    L2CAP(s): Info rsp: type 2 result 0
      Extended feature mask 0x00f8
        Enhanced Retransmission mode
        Streaming mode
        FCS Option
        Extended Flow Specification
        Fixed Channels
> ACL data: handle 1 flags 0x02 dlen 10
    L2CAP(s): Info req: type 3
< ACL data: handle 1 flags 0x00 dlen 20
    L2CAP(s): Info rsp: type 3 result 0
      Fixed channel list
> ACL data: handle 1 flags 0x02 dlen 16
    L2CAP(s): Connect rsp: dcid 0x0040 scid 0x0040 result 0 status 0
      Connection successful
< ACL data: handle 1 flags 0x00 dlen 41
    L2CAP(s): Config req: dcid 0x0040 flags 0x00 clen 29
      RFC 0x03 (Enhanced Retransmission, TxWin 63, MaxTx 3, RTo 0,
          MTo 0, MPS 500) 
      EFS (Id 0x01, SerType Best Effort, MaxSDU 0xffff, SDUitime
          0xffffffff, AccLat 0xffffffff, FlushTO 0x0000ffff) 
> ACL data: handle 1 flags 0x02 dlen 41
    L2CAP(s): Config req: dcid 0x0040 flags 0x00 clen 29
      RFC 0x03 (Enhanced Retransmission, TxWin 63, MaxTx 3, RTo 0, MTo 0,
          MPS 1009) 
      EFS (Id 0x01, SerType Best Effort, MaxSDU 0xffff, SDUitime 0xffffffff,
          AccLat 0xffffffff, FlushTO 0x0000ffff) 
< ACL data: handle 1 flags 0x00 dlen 47
    L2CAP(s): Config rsp: scid 0x0040 flags 0x00 result 4 clen 33
      Pending
      MTU 672 
      RFC 0x03 (Enhanced Retransmission, TxWin 63, MaxTx 3, RTo 2000, MTo 12000,
          MPS 500) 
      EFS (Id 0x01, SerType Best Effort, MaxSDU 0xffff, SDUitime 0xffffffff,
          AccLat 0xffffffff, FlushTO 0x0000ffff) 
> ACL data: handle 1 flags 0x02 dlen 47
    L2CAP(s): Config rsp: scid 0x0040 flags 0x00 result 4 clen 33
      Pending
      MTU 672 
      RFC 0x03 (Enhanced Retransmission, TxWin 63, MaxTx 3, RTo 2000, MTo 12000,
          MPS 500) 
      EFS (Id 0x01, SerType Best Effort, MaxSDU 0xffff, SDUitime 0xffffffff,
          AccLat 0xffffffff, FlushTO 0x0000ffff) 
< ACL data: handle 1 flags 0x00 dlen 14
    L2CAP(s): Config rsp: scid 0x0040 flags 0x00 result 0 clen 0
      Success
> ACL data: handle 1 flags 0x02 dlen 14
    L2CAP(s): Config rsp: scid 0x0040 flags 0x00 result 0 clen 0
      Success
...
< ACL data: handle 1 flags 0x00 dlen 510
    L2CAP(d): cid 0x0040 len 506 ctrl 0x4000 fcs 0x5337 [psm 4113]
      I-frame: Start (len 672) TxSeq 0 ReqSeq 0
...

Andrei Emeltchenko (6):
  Bluetooth: EFS: definitions and headers
  Bluetooth: EFS: assign default values in chan add
  Bluetooth: EFS: add efs option in L2CAP conf req
  Bluetooth: EFS: parse L2CAP config request
  Bluetooth: EFS: parse L2CAP config response
  Bluetooth: EFS: implement L2CAP config pending state

 include/net/bluetooth/l2cap.h |   38 +++++++++
 net/bluetooth/l2cap_core.c    |  167 ++++++++++++++++++++++++++++++++++++++++-
 2 files changed, 203 insertions(+), 2 deletions(-)

-- 
1.7.4.1


^ permalink raw reply	[flat|nested] 9+ messages in thread

* [PATCHv3 1/6] Bluetooth: EFS: definitions and headers
  2011-10-13 13:18 [PATCHv3 0/6] EFS: extended flow specification option support Emeltchenko Andrei
@ 2011-10-13 13:18 ` Emeltchenko Andrei
  2011-10-13 13:18 ` [PATCHv3 2/6] Bluetooth: EFS: assign default values in chan add Emeltchenko Andrei
                   ` (4 subsequent siblings)
  5 siblings, 0 replies; 9+ messages in thread
From: Emeltchenko Andrei @ 2011-10-13 13:18 UTC (permalink / raw)
  To: linux-bluetooth

From: Andrei Emeltchenko <andrei.emeltchenko@intel.com>

Define Extended Flow Specification structures and default values.
Based upon haijun.liu <haijun.liu@atheros.com> series of patches
(sent Sun, 22 Aug 2010)

Signed-off-by: Andrei Emeltchenko <andrei.emeltchenko@intel.com>
---
 include/net/bluetooth/l2cap.h |   26 ++++++++++++++++++++++++++
 1 files changed, 26 insertions(+), 0 deletions(-)

diff --git a/include/net/bluetooth/l2cap.h b/include/net/bluetooth/l2cap.h
index f195978..860b36f 100644
--- a/include/net/bluetooth/l2cap.h
+++ b/include/net/bluetooth/l2cap.h
@@ -250,6 +250,7 @@ struct l2cap_conf_rsp {
 #define L2CAP_CONF_UNACCEPT	0x0001
 #define L2CAP_CONF_REJECT	0x0002
 #define L2CAP_CONF_UNKNOWN	0x0003
+#define L2CAP_CONF_EFS_REJECT	0x0005
 
 struct l2cap_conf_opt {
 	__u8       type;
@@ -266,6 +267,7 @@ struct l2cap_conf_opt {
 #define L2CAP_CONF_QOS		0x03
 #define L2CAP_CONF_RFC		0x04
 #define L2CAP_CONF_FCS		0x05
+#define L2CAP_CONF_EFS		0x06
 #define L2CAP_CONF_EWS		0x07
 
 #define L2CAP_CONF_MAX_SIZE	22
@@ -285,6 +287,15 @@ struct l2cap_conf_rfc {
 #define L2CAP_MODE_ERTM		0x03
 #define L2CAP_MODE_STREAMING	0x04
 
+struct l2cap_conf_efs {
+	__u8	id;
+	__u8	stype;
+	__le16	msdu;
+	__le32	sdu_itime;
+	__le32	acc_lat;
+	__le32	flush_to;
+} __packed;
+
 struct l2cap_disconn_req {
 	__le16     dcid;
 	__le16     scid;
@@ -411,6 +422,20 @@ struct l2cap_chan {
 	__u8		remote_max_tx;
 	__u16		remote_mps;
 
+	__u8		local_id;
+	__u8		local_stype;
+	__u16		local_msdu;
+	__u32		local_sdu_itime;
+	__u32		local_acc_lat;
+	__u32		local_flush_to;
+
+	__u8		remote_id;
+	__u8		remote_stype;
+	__u16		remote_msdu;
+	__u32		remote_sdu_itime;
+	__u32		remote_acc_lat;
+	__u32		remote_flush_to;
+
 	struct timer_list	chan_timer;
 	struct timer_list	retrans_timer;
 	struct timer_list	monitor_timer;
@@ -518,6 +543,7 @@ enum {
 	FLAG_FORCE_RELIABLE,
 	FLAG_FLUSHABLE,
 	FLAG_EXT_CTRL,
+	FLAG_EFS_ENABLE,
 };
 
 #define __set_chan_timer(c, t) l2cap_set_timer(c, &c->chan_timer, (t))
-- 
1.7.4.1


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCHv3 2/6] Bluetooth: EFS: assign default values in chan add
  2011-10-13 13:18 [PATCHv3 0/6] EFS: extended flow specification option support Emeltchenko Andrei
  2011-10-13 13:18 ` [PATCHv3 1/6] Bluetooth: EFS: definitions and headers Emeltchenko Andrei
@ 2011-10-13 13:18 ` Emeltchenko Andrei
  2011-10-13 13:18 ` [PATCHv3 3/6] Bluetooth: EFS: add efs option in L2CAP conf req Emeltchenko Andrei
                   ` (3 subsequent siblings)
  5 siblings, 0 replies; 9+ messages in thread
From: Emeltchenko Andrei @ 2011-10-13 13:18 UTC (permalink / raw)
  To: linux-bluetooth

From: Andrei Emeltchenko <andrei.emeltchenko@intel.com>

Assign default EFS values when creating L2CAP channel

Signed-off-by: Andrei Emeltchenko <andrei.emeltchenko@intel.com>
---
 include/net/bluetooth/l2cap.h |    9 +++++++++
 net/bluetooth/l2cap_core.c    |    7 +++++++
 2 files changed, 16 insertions(+), 0 deletions(-)

diff --git a/include/net/bluetooth/l2cap.h b/include/net/bluetooth/l2cap.h
index 860b36f..aa3de2f9 100644
--- a/include/net/bluetooth/l2cap.h
+++ b/include/net/bluetooth/l2cap.h
@@ -41,6 +41,9 @@
 #define L2CAP_DEFAULT_MAX_PDU_SIZE	1009    /* Sized for 3-DH5 packet */
 #define L2CAP_DEFAULT_ACK_TO		200
 #define L2CAP_LE_DEFAULT_MTU		23
+#define L2CAP_DEFAULT_MAX_SDU_SIZE	0xFFFF
+#define L2CAP_DEFAULT_SDU_ITIME		0xFFFFFFFF
+#define L2CAP_DEFAULT_ACC_LAT		0xFFFFFFFF
 
 #define L2CAP_CONN_TIMEOUT	(40000) /* 40 seconds */
 #define L2CAP_INFO_TIMEOUT	(4000)  /*  4 seconds */
@@ -296,6 +299,12 @@ struct l2cap_conf_efs {
 	__le32	flush_to;
 } __packed;
 
+#define L2CAP_SERV_NOTRAFIC	0x00
+#define L2CAP_SERV_BESTEFFORT	0x01
+#define L2CAP_SERV_GUARANTEED	0x02
+
+#define L2CAP_BESTEFFORT_ID	0x01
+
 struct l2cap_disconn_req {
 	__le16     dcid;
 	__le16     scid;
diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c
index 152b68f..a73f77e 100644
--- a/net/bluetooth/l2cap_core.c
+++ b/net/bluetooth/l2cap_core.c
@@ -338,6 +338,13 @@ static void __l2cap_chan_add(struct l2cap_conn *conn, struct l2cap_chan *chan)
 		chan->omtu = L2CAP_DEFAULT_MTU;
 	}
 
+	chan->local_id		= L2CAP_BESTEFFORT_ID;
+	chan->local_stype	= L2CAP_SERV_BESTEFFORT;
+	chan->local_msdu	= L2CAP_DEFAULT_MAX_SDU_SIZE;
+	chan->local_sdu_itime	= L2CAP_DEFAULT_SDU_ITIME;
+	chan->local_acc_lat	= L2CAP_DEFAULT_ACC_LAT;
+	chan->local_flush_to	= L2CAP_DEFAULT_FLUSH_TO;
+
 	chan_hold(chan);
 
 	list_add(&chan->list, &conn->chan_l);
-- 
1.7.4.1


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCHv3 3/6] Bluetooth: EFS: add efs option in L2CAP conf req
  2011-10-13 13:18 [PATCHv3 0/6] EFS: extended flow specification option support Emeltchenko Andrei
  2011-10-13 13:18 ` [PATCHv3 1/6] Bluetooth: EFS: definitions and headers Emeltchenko Andrei
  2011-10-13 13:18 ` [PATCHv3 2/6] Bluetooth: EFS: assign default values in chan add Emeltchenko Andrei
@ 2011-10-13 13:18 ` Emeltchenko Andrei
  2011-10-13 20:10   ` Gustavo Padovan
  2011-10-13 13:18 ` [PATCHv3 4/6] Bluetooth: EFS: parse L2CAP config request Emeltchenko Andrei
                   ` (2 subsequent siblings)
  5 siblings, 1 reply; 9+ messages in thread
From: Emeltchenko Andrei @ 2011-10-13 13:18 UTC (permalink / raw)
  To: linux-bluetooth

From: Andrei Emeltchenko <andrei.emeltchenko@intel.com>

Add Extended Flow Specification option when building L2CAP
Configuration Request. EFS is added if both the local and
remote L2CAP entities have indicated support for the
Extended Flow Specification for BR/EDR.

...
< ACL data: handle 1 flags 0x00 dlen 10
    L2CAP(s): Info req: type 2
> ACL data: handle 1 flags 0x02 dlen 16
    L2CAP(s): Info rsp: type 2 result 0
      Extended feature mask 0x01f8
        Enhanced Retransmission mode
        Streaming mode
        FCS Option
        Extended Flow Specification
        Fixed Channels
        Extended Window Size
...
< ACL data: handle 1 flags 0x00 dlen 45
    L2CAP(s): Config req: dcid 0x0040 flags 0x00 clen 33
      RFC 0x03 (Enhanced Retransmission, TxWin 63, MaxTx 3, RTo 0, MTo 0, MPS 498)
      EFS (Id 0x01, SerType Best Effort, MaxSDU 0xffff, SDUitime 0xffffffff,
          AccLat 0xffffffff, FlushTO 0x0000ffff)
...

Based upon haijun.liu <haijun.liu@atheros.com> series of patches
(sent Sun, 22 Aug 2010)

Signed-off-by: Andrei Emeltchenko <andrei.emeltchenko@intel.com>
---
 net/bluetooth/l2cap_core.c |   45 ++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 45 insertions(+), 0 deletions(-)

diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c
index a73f77e..f5c4bbb 100644
--- a/net/bluetooth/l2cap_core.c
+++ b/net/bluetooth/l2cap_core.c
@@ -1884,6 +1884,37 @@ static void l2cap_add_conf_opt(void **ptr, u8 type, u8 len, unsigned long val)
 	*ptr += L2CAP_CONF_OPT_SIZE + len;
 }
 
+static void l2cap_add_opt_efs(void **ptr, struct l2cap_chan *chan)
+{
+	struct l2cap_conf_efs efs;
+
+	switch(chan->mode) {
+	case L2CAP_MODE_ERTM:
+		efs.id		= chan->local_id;
+		efs.stype	= chan->local_stype;
+		efs.msdu	= cpu_to_le16(chan->local_msdu);
+		efs.sdu_itime	= cpu_to_le32(chan->local_sdu_itime);
+		efs.acc_lat	= cpu_to_le32(L2CAP_DEFAULT_ACC_LAT);
+		efs.flush_to	= cpu_to_le32(L2CAP_DEFAULT_FLUSH_TO);
+		break;
+
+	case L2CAP_MODE_STREAMING:
+		efs.id		= 1;
+		efs.stype	= L2CAP_SERV_BESTEFFORT;
+		efs.msdu	= cpu_to_le16(chan->local_msdu);
+		efs.sdu_itime	= cpu_to_le32(chan->local_sdu_itime);
+		efs.acc_lat	= 0;
+		efs.flush_to	= 0;
+		break;
+
+	default:
+		return;
+	}
+
+	l2cap_add_conf_opt(ptr, L2CAP_CONF_EFS, sizeof(efs),
+							(unsigned long) &efs);
+}
+
 static void l2cap_ack_timeout(unsigned long arg)
 {
 	struct l2cap_chan *chan = (void *) arg;
@@ -1935,6 +1966,11 @@ static inline bool __l2cap_ews_supported(struct l2cap_chan *chan)
 	return enable_hs && chan->conn->feat_mask & L2CAP_FEAT_EXT_WINDOW;
 }
 
+static inline bool __l2cap_efs_supported(struct l2cap_chan *chan)
+{
+	return enable_hs && chan->conn->feat_mask & L2CAP_FEAT_EXT_FLOW;
+}
+
 static inline void l2cap_txwin_setup(struct l2cap_chan *chan)
 {
 	if (chan->tx_win > L2CAP_DEFAULT_TX_WINDOW &&
@@ -1967,6 +2003,9 @@ static int l2cap_build_conf_req(struct l2cap_chan *chan, void *data)
 		if (test_bit(CONF_STATE2_DEVICE, &chan->conf_state))
 			break;
 
+		if (__l2cap_efs_supported(chan))
+			set_bit(FLAG_EFS_ENABLE, &chan->flags);
+
 		/* fall through */
 	default:
 		chan->mode = l2cap_select_mode(rfc.mode, chan->conn->feat_mask);
@@ -2014,6 +2053,9 @@ done:
 		l2cap_add_conf_opt(&ptr, L2CAP_CONF_RFC, sizeof(rfc),
 							(unsigned long) &rfc);
 
+		if (test_bit(FLAG_EFS_ENABLE, &chan->flags))
+			l2cap_add_opt_efs(&ptr, chan);
+
 		if (!(chan->conn->feat_mask & L2CAP_FEAT_FCS))
 			break;
 
@@ -2044,6 +2086,9 @@ done:
 		l2cap_add_conf_opt(&ptr, L2CAP_CONF_RFC, sizeof(rfc),
 							(unsigned long) &rfc);
 
+		if (test_bit(FLAG_EFS_ENABLE, &chan->flags))
+			l2cap_add_opt_efs(&ptr, chan);
+
 		if (!(chan->conn->feat_mask & L2CAP_FEAT_FCS))
 			break;
 
-- 
1.7.4.1


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCHv3 4/6] Bluetooth: EFS: parse L2CAP config request
  2011-10-13 13:18 [PATCHv3 0/6] EFS: extended flow specification option support Emeltchenko Andrei
                   ` (2 preceding siblings ...)
  2011-10-13 13:18 ` [PATCHv3 3/6] Bluetooth: EFS: add efs option in L2CAP conf req Emeltchenko Andrei
@ 2011-10-13 13:18 ` Emeltchenko Andrei
  2011-10-13 20:15   ` Gustavo Padovan
  2011-10-13 13:18 ` [PATCHv3 5/6] Bluetooth: EFS: parse L2CAP config response Emeltchenko Andrei
  2011-10-13 13:18 ` [PATCHv3 6/6] Bluetooth: EFS: implement L2CAP config pending state Emeltchenko Andrei
  5 siblings, 1 reply; 9+ messages in thread
From: Emeltchenko Andrei @ 2011-10-13 13:18 UTC (permalink / raw)
  To: linux-bluetooth

From: Andrei Emeltchenko <andrei.emeltchenko@intel.com>

Add parsing Extended Flow Specification option in L2CAP Config Request
Based upon haijun.liu <haijun.liu@atheros.com> series of patches
(sent Sun, 22 Aug 2010)

Signed-off-by: Andrei Emeltchenko <andrei.emeltchenko@intel.com>
---
 net/bluetooth/l2cap_core.c |   43 +++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 43 insertions(+), 0 deletions(-)

diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c
index f5c4bbb..255dada 100644
--- a/net/bluetooth/l2cap_core.c
+++ b/net/bluetooth/l2cap_core.c
@@ -2115,6 +2115,8 @@ static int l2cap_parse_conf_req(struct l2cap_chan *chan, void *data)
 	int type, hint, olen;
 	unsigned long val;
 	struct l2cap_conf_rfc rfc = { .mode = L2CAP_MODE_BASIC };
+	struct l2cap_conf_efs efs;
+	u8 remote_efs = 0;
 	u16 mtu = L2CAP_DEFAULT_MTU;
 	u16 result = L2CAP_CONF_SUCCESS;
 	u16 size;
@@ -2147,7 +2149,12 @@ static int l2cap_parse_conf_req(struct l2cap_chan *chan, void *data)
 		case L2CAP_CONF_FCS:
 			if (val == L2CAP_FCS_NONE)
 				set_bit(CONF_NO_FCS_RECV, &chan->conf_state);
+			break;
 
+		case L2CAP_CONF_EFS:
+			remote_efs = 1;
+			if (olen == sizeof(efs))
+				memcpy(&efs, (void *) val, olen);
 			break;
 
 		case L2CAP_CONF_EWS:
@@ -2182,6 +2189,9 @@ static int l2cap_parse_conf_req(struct l2cap_chan *chan, void *data)
 			break;
 		}
 
+		if (remote_efs && __l2cap_efs_supported(chan))
+			set_bit(FLAG_EFS_ENABLE, &chan->flags);
+
 		if (chan->mode != rfc.mode)
 			return -ECONNREFUSED;
 
@@ -2200,6 +2210,26 @@ done:
 					sizeof(rfc), (unsigned long) &rfc);
 	}
 
+	/*
+	   Add extended flow specification option check here.
+	 */
+	if (result == L2CAP_CONF_SUCCESS && remote_efs) {
+		if (!test_bit(FLAG_EFS_ENABLE, &chan->flags))
+			return -ECONNREFUSED;
+
+		if (chan->local_stype != L2CAP_SERV_NOTRAFIC &&
+					efs.stype != L2CAP_SERV_NOTRAFIC &&
+					efs.stype != chan->local_stype) {
+
+			result = L2CAP_CONF_UNACCEPT;
+
+			if (chan->num_conf_req >= 1)
+				return -ECONNREFUSED;
+
+			l2cap_add_conf_opt(&ptr, L2CAP_CONF_EFS,
+					sizeof(efs), (unsigned long) &efs);
+		}
+	}
 
 	if (result == L2CAP_CONF_SUCCESS) {
 		/* Configure output options and let the other side know
@@ -2245,6 +2275,19 @@ done:
 			l2cap_add_conf_opt(&ptr, L2CAP_CONF_RFC,
 					sizeof(rfc), (unsigned long) &rfc);
 
+			if (test_bit(FLAG_EFS_ENABLE, &chan->flags)) {
+				chan->remote_id = efs.id;
+				chan->remote_stype = efs.stype;
+				chan->remote_msdu = le16_to_cpu(efs.msdu);
+				chan->remote_flush_to =
+						le32_to_cpu(efs.flush_to);
+				chan->remote_acc_lat =
+						le32_to_cpu(efs.acc_lat);
+				chan->remote_sdu_itime =
+					le32_to_cpu(efs.sdu_itime);
+				l2cap_add_conf_opt(&ptr, L2CAP_CONF_EFS,
+					sizeof(efs), (unsigned long) &efs);
+			}
 			break;
 
 		case L2CAP_MODE_STREAMING:
-- 
1.7.4.1


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCHv3 5/6] Bluetooth: EFS: parse L2CAP config response
  2011-10-13 13:18 [PATCHv3 0/6] EFS: extended flow specification option support Emeltchenko Andrei
                   ` (3 preceding siblings ...)
  2011-10-13 13:18 ` [PATCHv3 4/6] Bluetooth: EFS: parse L2CAP config request Emeltchenko Andrei
@ 2011-10-13 13:18 ` Emeltchenko Andrei
  2011-10-13 13:18 ` [PATCHv3 6/6] Bluetooth: EFS: implement L2CAP config pending state Emeltchenko Andrei
  5 siblings, 0 replies; 9+ messages in thread
From: Emeltchenko Andrei @ 2011-10-13 13:18 UTC (permalink / raw)
  To: linux-bluetooth

From: Andrei Emeltchenko <andrei.emeltchenko@intel.com>

Add parsing Extended Flow Specification in L2CAP Config Response.
Based upon haijun.liu <haijun.liu@atheros.com> series of patches
(sent Sun, 22 Aug 2010)

Signed-off-by: Andrei Emeltchenko <andrei.emeltchenko@intel.com>
---
 net/bluetooth/l2cap_core.c |   24 ++++++++++++++++++++++++
 1 files changed, 24 insertions(+), 0 deletions(-)

diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c
index 255dada..7eab3a2 100644
--- a/net/bluetooth/l2cap_core.c
+++ b/net/bluetooth/l2cap_core.c
@@ -2330,6 +2330,7 @@ static int l2cap_parse_conf_rsp(struct l2cap_chan *chan, void *rsp, int len, voi
 	int type, olen;
 	unsigned long val;
 	struct l2cap_conf_rfc rfc;
+	struct l2cap_conf_efs efs;
 
 	BT_DBG("chan %p, rsp %p, len %d, req %p", chan, rsp, len, data);
 
@@ -2372,6 +2373,19 @@ static int l2cap_parse_conf_rsp(struct l2cap_chan *chan, void *rsp, int len, voi
 			l2cap_add_conf_opt(&ptr, L2CAP_CONF_EWS,
 							2, chan->tx_win);
 			break;
+
+		case L2CAP_CONF_EFS:
+			if (olen == sizeof(efs))
+				memcpy(&efs, (void *)val, olen);
+
+			if (chan->local_stype != L2CAP_SERV_NOTRAFIC &&
+					efs.stype != L2CAP_SERV_NOTRAFIC &&
+					efs.stype != chan->local_stype)
+				return -ECONNREFUSED;
+
+			l2cap_add_conf_opt(&ptr, L2CAP_CONF_EFS,
+					sizeof(efs), (unsigned long) &efs);
+			break;
 		}
 	}
 
@@ -2386,7 +2400,17 @@ static int l2cap_parse_conf_rsp(struct l2cap_chan *chan, void *rsp, int len, voi
 			chan->retrans_timeout = le16_to_cpu(rfc.retrans_timeout);
 			chan->monitor_timeout = le16_to_cpu(rfc.monitor_timeout);
 			chan->mps    = le16_to_cpu(rfc.max_pdu_size);
+
+			if (test_bit(FLAG_EFS_ENABLE, &chan->flags)) {
+				chan->local_msdu = le16_to_cpu(efs.msdu);
+				chan->local_sdu_itime =
+						le32_to_cpu(efs.sdu_itime);
+				chan->local_acc_lat = le32_to_cpu(efs.acc_lat);
+				chan->local_flush_to =
+						le32_to_cpu(efs.flush_to);
+			}
 			break;
+
 		case L2CAP_MODE_STREAMING:
 			chan->mps    = le16_to_cpu(rfc.max_pdu_size);
 		}
-- 
1.7.4.1


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCHv3 6/6] Bluetooth: EFS: implement L2CAP config pending state
  2011-10-13 13:18 [PATCHv3 0/6] EFS: extended flow specification option support Emeltchenko Andrei
                   ` (4 preceding siblings ...)
  2011-10-13 13:18 ` [PATCHv3 5/6] Bluetooth: EFS: parse L2CAP config response Emeltchenko Andrei
@ 2011-10-13 13:18 ` Emeltchenko Andrei
  5 siblings, 0 replies; 9+ messages in thread
From: Emeltchenko Andrei @ 2011-10-13 13:18 UTC (permalink / raw)
  To: linux-bluetooth

From: Andrei Emeltchenko <andrei.emeltchenko@intel.com>

Add L2CAP Config Pending state for EFS. Currently after receiving
Config Response Pending respond with Config Response Success.

...
> ACL data: handle 1 flags 0x02 dlen 16
    L2CAP(s): Connect rsp: dcid 0x0040 scid 0x0040 result 0 status 0
      Connection successful
> ACL data: handle 1 flags 0x02 dlen 45
    L2CAP(s): Config req: dcid 0x0040 flags 0x00 clen 33
      RFC 0x03 (Enhanced Retransmission, TxWin 63, MaxTx 3, RTo 0, MTo 0, MPS 1009)
      EFS (Id 0x01, SerType Best Effort, MaxSDU 0xffff, SDUitime 0xffffffff,
          AccLat 0xffffffff, FlushTO 0x0000ffff)
< ACL data: handle 1 flags 0x00 dlen 45
    L2CAP(s): Config req: dcid 0x0040 flags 0x00 clen 33
      RFC 0x03 (Enhanced Retransmission, TxWin 63, MaxTx 3, RTo 0, MTo 0, MPS 498)
      EFS (Id 0x01, SerType Best Effort, MaxSDU 0xffff, SDUitime 0xffffffff,
          AccLat 0xffffffff, FlushTO 0x0000ffff)
< ACL data: handle 1 flags 0x00 dlen 47
    L2CAP(s): Config rsp: scid 0x0040 flags 0x00 result 4 clen 33
      Pending
      MTU 672
      RFC 0x03 (Enhanced Retransmission, TxWin 63, MaxTx 3, RTo 2000, MTo 12000, MPS 498)
      EFS (Id 0x01, SerType Best Effort, MaxSDU 0xffff, SDUitime 0xffffffff,
          AccLat 0xffffffff, FlushTO 0x0000ffff)
> ACL data: handle 1 flags 0x02 dlen 47
    L2CAP(s): Config rsp: scid 0x0040 flags 0x00 result 4 clen 33
      Pending
      MTU 672
      RFC 0x03 (Enhanced Retransmission, TxWin 63, MaxTx 3, RTo 2000, MTo 12000, MPS 498)
      EFS (Id 0x01, SerType Best Effort, MaxSDU 0xffff, SDUitime 0xffffffff,
          AccLat 0xffffffff, FlushTO 0x0000ffff)
> ACL data: handle 1 flags 0x02 dlen 14
    L2CAP(s): Config rsp: scid 0x0040 flags 0x00 result 0 clen 0
      Success
< ACL data: handle 1 flags 0x00 dlen 14
    L2CAP(s): Config rsp: scid 0x0040 flags 0x00 result 0 clen 0
      Success
< ACL data: handle 1 flags 0x00 dlen 510
    L2CAP(d): cid 0x0040 len 506 ext_ctrl 0x00010000 fcs 0xebe0 [psm 4113]
      I-frame: Start (len 672) TxSeq 0 ReqSeq 0
...

Signed-off-by: Andrei Emeltchenko <andrei.emeltchenko@intel.com>
---
 include/net/bluetooth/l2cap.h |    3 ++
 net/bluetooth/l2cap_core.c    |   48 +++++++++++++++++++++++++++++++++++++++-
 2 files changed, 49 insertions(+), 2 deletions(-)

diff --git a/include/net/bluetooth/l2cap.h b/include/net/bluetooth/l2cap.h
index aa3de2f9..6e218e6 100644
--- a/include/net/bluetooth/l2cap.h
+++ b/include/net/bluetooth/l2cap.h
@@ -253,6 +253,7 @@ struct l2cap_conf_rsp {
 #define L2CAP_CONF_UNACCEPT	0x0001
 #define L2CAP_CONF_REJECT	0x0002
 #define L2CAP_CONF_UNKNOWN	0x0003
+#define L2CAP_CONF_PENDING	0x0004
 #define L2CAP_CONF_EFS_REJECT	0x0005
 
 struct l2cap_conf_opt {
@@ -528,6 +529,8 @@ enum {
 	CONF_NO_FCS_RECV,
 	CONF_STATE2_DEVICE,
 	CONF_EWS_RECV,
+	CONF_LOC_CONF_PEND,
+	CONF_REM_CONF_PEND,
 };
 
 #define L2CAP_CONF_MAX_CONF_REQ 2
diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c
index 7eab3a2..613ea9c 100644
--- a/net/bluetooth/l2cap_core.c
+++ b/net/bluetooth/l2cap_core.c
@@ -2228,10 +2228,14 @@ done:
 
 			l2cap_add_conf_opt(&ptr, L2CAP_CONF_EFS,
 					sizeof(efs), (unsigned long) &efs);
+		} else {
+			/* Send PENDING Conf Rsp and mark state LOC_PENDING */
+			result = L2CAP_CONF_PENDING;
+			set_bit(CONF_LOC_CONF_PEND, &chan->conf_state);
 		}
 	}
 
-	if (result == L2CAP_CONF_SUCCESS) {
+	if (result == L2CAP_CONF_SUCCESS || result == L2CAP_CONF_PENDING) {
 		/* Configure output options and let the other side know
 		 * which ones we don't like. */
 
@@ -2394,7 +2398,7 @@ static int l2cap_parse_conf_rsp(struct l2cap_chan *chan, void *rsp, int len, voi
 
 	chan->mode = rfc.mode;
 
-	if (*result == L2CAP_CONF_SUCCESS) {
+	if (*result == L2CAP_CONF_SUCCESS || *result == L2CAP_CONF_PENDING) {
 		switch (rfc.mode) {
 		case L2CAP_MODE_ERTM:
 			chan->retrans_timeout = le16_to_cpu(rfc.retrans_timeout);
@@ -2820,6 +2824,21 @@ static inline int l2cap_config_req(struct l2cap_conn *conn, struct l2cap_cmd_hdr
 		chan->num_conf_req++;
 	}
 
+	/* Got Conf Rsp PENDING from remote side and asume we sent
+	   Conf Rsp PENDING in the code above */
+	if (test_bit(CONF_REM_CONF_PEND, &chan->conf_state) &&
+			test_bit(CONF_LOC_CONF_PEND, &chan->conf_state)) {
+
+		/* check compatibility */
+
+		clear_bit(CONF_LOC_CONF_PEND, &chan->conf_state);
+		set_bit(CONF_OUTPUT_DONE, &chan->conf_state);
+
+		l2cap_send_cmd(conn, cmd->ident, L2CAP_CONF_RSP,
+				l2cap_build_conf_rsp(chan, rsp,
+					L2CAP_CONF_SUCCESS, 0x0000), rsp);
+	}
+
 unlock:
 	bh_unlock_sock(sk);
 	return 0;
@@ -2849,8 +2868,33 @@ static inline int l2cap_config_rsp(struct l2cap_conn *conn, struct l2cap_cmd_hdr
 	switch (result) {
 	case L2CAP_CONF_SUCCESS:
 		l2cap_conf_rfc_get(chan, rsp->data, len);
+		clear_bit(CONF_REM_CONF_PEND, &chan->conf_state);
 		break;
 
+	case L2CAP_CONF_PENDING:
+		set_bit(CONF_REM_CONF_PEND, &chan->conf_state);
+
+		if (test_bit(CONF_LOC_CONF_PEND, &chan->conf_state)) {
+			char buf[64];
+
+			len = l2cap_parse_conf_rsp(chan, rsp->data, len,
+								buf, &result);
+			if (len < 0) {
+				l2cap_send_disconn_req(conn, chan, ECONNRESET);
+				goto done;
+			}
+
+			/* check compatibility */
+
+			clear_bit(CONF_LOC_CONF_PEND, &chan->conf_state);
+			set_bit(CONF_OUTPUT_DONE, &chan->conf_state);
+
+			l2cap_send_cmd(conn, cmd->ident, L2CAP_CONF_RSP,
+					l2cap_build_conf_rsp(chan, buf,
+						L2CAP_CONF_SUCCESS, 0x0000), buf);
+		}
+		goto done;
+
 	case L2CAP_CONF_UNACCEPT:
 		if (chan->num_conf_rsp <= L2CAP_CONF_MAX_CONF_RSP) {
 			char req[64];
-- 
1.7.4.1


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* Re: [PATCHv3 3/6] Bluetooth: EFS: add efs option in L2CAP conf req
  2011-10-13 13:18 ` [PATCHv3 3/6] Bluetooth: EFS: add efs option in L2CAP conf req Emeltchenko Andrei
@ 2011-10-13 20:10   ` Gustavo Padovan
  0 siblings, 0 replies; 9+ messages in thread
From: Gustavo Padovan @ 2011-10-13 20:10 UTC (permalink / raw)
  To: Emeltchenko Andrei; +Cc: linux-bluetooth

Hi Andrei,

* Emeltchenko Andrei <Andrei.Emeltchenko.news@gmail.com> [2011-10-13 16:18:55 +0300]:

> From: Andrei Emeltchenko <andrei.emeltchenko@intel.com>
> 
> Add Extended Flow Specification option when building L2CAP
> Configuration Request. EFS is added if both the local and
> remote L2CAP entities have indicated support for the
> Extended Flow Specification for BR/EDR.
> 
> ...
> < ACL data: handle 1 flags 0x00 dlen 10
>     L2CAP(s): Info req: type 2
> > ACL data: handle 1 flags 0x02 dlen 16
>     L2CAP(s): Info rsp: type 2 result 0
>       Extended feature mask 0x01f8
>         Enhanced Retransmission mode
>         Streaming mode
>         FCS Option
>         Extended Flow Specification
>         Fixed Channels
>         Extended Window Size
> ...
> < ACL data: handle 1 flags 0x00 dlen 45
>     L2CAP(s): Config req: dcid 0x0040 flags 0x00 clen 33
>       RFC 0x03 (Enhanced Retransmission, TxWin 63, MaxTx 3, RTo 0, MTo 0, MPS 498)
>       EFS (Id 0x01, SerType Best Effort, MaxSDU 0xffff, SDUitime 0xffffffff,
>           AccLat 0xffffffff, FlushTO 0x0000ffff)
> ...
> 
> Based upon haijun.liu <haijun.liu@atheros.com> series of patches
> (sent Sun, 22 Aug 2010)
> 
> Signed-off-by: Andrei Emeltchenko <andrei.emeltchenko@intel.com>
> ---
>  net/bluetooth/l2cap_core.c |   45 ++++++++++++++++++++++++++++++++++++++++++++
>  1 files changed, 45 insertions(+), 0 deletions(-)

Patches 1 to 3 have been applied. Thanks.

	Gustavo

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCHv3 4/6] Bluetooth: EFS: parse L2CAP config request
  2011-10-13 13:18 ` [PATCHv3 4/6] Bluetooth: EFS: parse L2CAP config request Emeltchenko Andrei
@ 2011-10-13 20:15   ` Gustavo Padovan
  0 siblings, 0 replies; 9+ messages in thread
From: Gustavo Padovan @ 2011-10-13 20:15 UTC (permalink / raw)
  To: Emeltchenko Andrei; +Cc: linux-bluetooth

* Emeltchenko Andrei <Andrei.Emeltchenko.news@gmail.com> [2011-10-13 16:18:56 +0300]:

> From: Andrei Emeltchenko <andrei.emeltchenko@intel.com>
> 
> Add parsing Extended Flow Specification option in L2CAP Config Request
> Based upon haijun.liu <haijun.liu@atheros.com> series of patches
> (sent Sun, 22 Aug 2010)
> 
> Signed-off-by: Andrei Emeltchenko <andrei.emeltchenko@intel.com>
> ---
>  net/bluetooth/l2cap_core.c |   43 +++++++++++++++++++++++++++++++++++++++++++
>  1 files changed, 43 insertions(+), 0 deletions(-)
> 
> diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c
> index f5c4bbb..255dada 100644
> --- a/net/bluetooth/l2cap_core.c
> +++ b/net/bluetooth/l2cap_core.c
> @@ -2115,6 +2115,8 @@ static int l2cap_parse_conf_req(struct l2cap_chan *chan, void *data)
>  	int type, hint, olen;
>  	unsigned long val;
>  	struct l2cap_conf_rfc rfc = { .mode = L2CAP_MODE_BASIC };
> +	struct l2cap_conf_efs efs;
> +	u8 remote_efs = 0;
>  	u16 mtu = L2CAP_DEFAULT_MTU;
>  	u16 result = L2CAP_CONF_SUCCESS;
>  	u16 size;
> @@ -2147,7 +2149,12 @@ static int l2cap_parse_conf_req(struct l2cap_chan *chan, void *data)
>  		case L2CAP_CONF_FCS:
>  			if (val == L2CAP_FCS_NONE)
>  				set_bit(CONF_NO_FCS_RECV, &chan->conf_state);
> +			break;
>  
> +		case L2CAP_CONF_EFS:
> +			remote_efs = 1;
> +			if (olen == sizeof(efs))
> +				memcpy(&efs, (void *) val, olen);
>  			break;
>  
>  		case L2CAP_CONF_EWS:
> @@ -2182,6 +2189,9 @@ static int l2cap_parse_conf_req(struct l2cap_chan *chan, void *data)
>  			break;
>  		}
>  
> +		if (remote_efs && __l2cap_efs_supported(chan))
> +			set_bit(FLAG_EFS_ENABLE, &chan->flags);

This could be:

		if (remote_efs) {
			if (__l2cap_efs_supported()
				set_bit()
			else
				return -ECONNREFUSED;
		}

> +
>  		if (chan->mode != rfc.mode)
>  			return -ECONNREFUSED;
>  
> @@ -2200,6 +2210,26 @@ done:
>  					sizeof(rfc), (unsigned long) &rfc);
>  	}
>  
> +	/*
> +	   Add extended flow specification option check here.
> +	 */
> +	if (result == L2CAP_CONF_SUCCESS && remote_efs) {
> +		if (!test_bit(FLAG_EFS_ENABLE, &chan->flags))
> +			return -ECONNREFUSED;

Then you don't need to do this check here, and everything can be potentially 
be placed under the same if (L2CAP_CONF_SUCCESS).

	Gustavo

^ permalink raw reply	[flat|nested] 9+ messages in thread

end of thread, other threads:[~2011-10-13 20:15 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-10-13 13:18 [PATCHv3 0/6] EFS: extended flow specification option support Emeltchenko Andrei
2011-10-13 13:18 ` [PATCHv3 1/6] Bluetooth: EFS: definitions and headers Emeltchenko Andrei
2011-10-13 13:18 ` [PATCHv3 2/6] Bluetooth: EFS: assign default values in chan add Emeltchenko Andrei
2011-10-13 13:18 ` [PATCHv3 3/6] Bluetooth: EFS: add efs option in L2CAP conf req Emeltchenko Andrei
2011-10-13 20:10   ` Gustavo Padovan
2011-10-13 13:18 ` [PATCHv3 4/6] Bluetooth: EFS: parse L2CAP config request Emeltchenko Andrei
2011-10-13 20:15   ` Gustavo Padovan
2011-10-13 13:18 ` [PATCHv3 5/6] Bluetooth: EFS: parse L2CAP config response Emeltchenko Andrei
2011-10-13 13:18 ` [PATCHv3 6/6] Bluetooth: EFS: implement L2CAP config pending state Emeltchenko Andrei

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.