.. | .. |
---|
40 | 40 | static bool disable_cfc; |
---|
41 | 41 | static bool l2cap_ertm; |
---|
42 | 42 | static int channel_mtu = -1; |
---|
43 | | -static unsigned int l2cap_mtu = RFCOMM_MAX_L2CAP_MTU; |
---|
44 | 43 | |
---|
45 | 44 | static struct task_struct *rfcomm_thread; |
---|
46 | 45 | |
---|
.. | .. |
---|
73 | 72 | |
---|
74 | 73 | /* ---- RFCOMM frame parsing macros ---- */ |
---|
75 | 74 | #define __get_dlci(b) ((b & 0xfc) >> 2) |
---|
76 | | -#define __get_channel(b) ((b & 0xf8) >> 3) |
---|
77 | | -#define __get_dir(b) ((b & 0x04) >> 2) |
---|
78 | 75 | #define __get_type(b) ((b & 0xef)) |
---|
79 | 76 | |
---|
80 | 77 | #define __test_ea(b) ((b & 0x01)) |
---|
.. | .. |
---|
87 | 84 | #define __ctrl(type, pf) (((type & 0xef) | (pf << 4))) |
---|
88 | 85 | #define __dlci(dir, chn) (((chn & 0x1f) << 1) | dir) |
---|
89 | 86 | #define __srv_channel(dlci) (dlci >> 1) |
---|
90 | | -#define __dir(dlci) (dlci & 0x01) |
---|
91 | 87 | |
---|
92 | 88 | #define __len8(len) (((len) << 1) | 1) |
---|
93 | 89 | #define __len16(len) ((len) << 1) |
---|
.. | .. |
---|
483 | 479 | /* if closing a dlc in a session that hasn't been started, |
---|
484 | 480 | * just close and unlink the dlc |
---|
485 | 481 | */ |
---|
| 482 | + fallthrough; |
---|
486 | 483 | |
---|
487 | 484 | default: |
---|
488 | 485 | rfcomm_dlc_clear_timer(d); |
---|
.. | .. |
---|
552 | 549 | return dlc; |
---|
553 | 550 | } |
---|
554 | 551 | |
---|
555 | | -int rfcomm_dlc_send(struct rfcomm_dlc *d, struct sk_buff *skb) |
---|
| 552 | +static int rfcomm_dlc_send_frag(struct rfcomm_dlc *d, struct sk_buff *frag) |
---|
556 | 553 | { |
---|
557 | | - int len = skb->len; |
---|
558 | | - |
---|
559 | | - if (d->state != BT_CONNECTED) |
---|
560 | | - return -ENOTCONN; |
---|
| 554 | + int len = frag->len; |
---|
561 | 555 | |
---|
562 | 556 | BT_DBG("dlc %p mtu %d len %d", d, d->mtu, len); |
---|
563 | 557 | |
---|
564 | 558 | if (len > d->mtu) |
---|
565 | 559 | return -EINVAL; |
---|
566 | 560 | |
---|
567 | | - rfcomm_make_uih(skb, d->addr); |
---|
568 | | - skb_queue_tail(&d->tx_queue, skb); |
---|
| 561 | + rfcomm_make_uih(frag, d->addr); |
---|
| 562 | + __skb_queue_tail(&d->tx_queue, frag); |
---|
569 | 563 | |
---|
570 | | - if (!test_bit(RFCOMM_TX_THROTTLED, &d->flags)) |
---|
| 564 | + return len; |
---|
| 565 | +} |
---|
| 566 | + |
---|
| 567 | +int rfcomm_dlc_send(struct rfcomm_dlc *d, struct sk_buff *skb) |
---|
| 568 | +{ |
---|
| 569 | + unsigned long flags; |
---|
| 570 | + struct sk_buff *frag, *next; |
---|
| 571 | + int len; |
---|
| 572 | + |
---|
| 573 | + if (d->state != BT_CONNECTED) |
---|
| 574 | + return -ENOTCONN; |
---|
| 575 | + |
---|
| 576 | + frag = skb_shinfo(skb)->frag_list; |
---|
| 577 | + skb_shinfo(skb)->frag_list = NULL; |
---|
| 578 | + |
---|
| 579 | + /* Queue all fragments atomically. */ |
---|
| 580 | + spin_lock_irqsave(&d->tx_queue.lock, flags); |
---|
| 581 | + |
---|
| 582 | + len = rfcomm_dlc_send_frag(d, skb); |
---|
| 583 | + if (len < 0 || !frag) |
---|
| 584 | + goto unlock; |
---|
| 585 | + |
---|
| 586 | + for (; frag; frag = next) { |
---|
| 587 | + int ret; |
---|
| 588 | + |
---|
| 589 | + next = frag->next; |
---|
| 590 | + |
---|
| 591 | + ret = rfcomm_dlc_send_frag(d, frag); |
---|
| 592 | + if (ret < 0) { |
---|
| 593 | + dev_kfree_skb_irq(frag); |
---|
| 594 | + goto unlock; |
---|
| 595 | + } |
---|
| 596 | + |
---|
| 597 | + len += ret; |
---|
| 598 | + } |
---|
| 599 | + |
---|
| 600 | +unlock: |
---|
| 601 | + spin_unlock_irqrestore(&d->tx_queue.lock, flags); |
---|
| 602 | + |
---|
| 603 | + if (len > 0 && !test_bit(RFCOMM_TX_THROTTLED, &d->flags)) |
---|
571 | 604 | rfcomm_schedule(); |
---|
572 | 605 | return len; |
---|
573 | 606 | } |
---|
.. | .. |
---|
751 | 784 | /* Set L2CAP options */ |
---|
752 | 785 | sk = sock->sk; |
---|
753 | 786 | lock_sock(sk); |
---|
754 | | - l2cap_pi(sk)->chan->imtu = l2cap_mtu; |
---|
| 787 | + /* Set MTU to 0 so L2CAP can auto select the MTU */ |
---|
| 788 | + l2cap_pi(sk)->chan->imtu = 0; |
---|
755 | 789 | l2cap_pi(sk)->chan->sec_level = sec_level; |
---|
756 | 790 | if (l2cap_ertm) |
---|
757 | 791 | l2cap_pi(sk)->chan->mode = L2CAP_MODE_ERTM; |
---|
.. | .. |
---|
2038 | 2072 | /* Set L2CAP options */ |
---|
2039 | 2073 | sk = sock->sk; |
---|
2040 | 2074 | lock_sock(sk); |
---|
2041 | | - l2cap_pi(sk)->chan->imtu = l2cap_mtu; |
---|
| 2075 | + /* Set MTU to 0 so L2CAP can auto select the MTU */ |
---|
| 2076 | + l2cap_pi(sk)->chan->imtu = 0; |
---|
2042 | 2077 | release_sock(sk); |
---|
2043 | 2078 | |
---|
2044 | 2079 | /* Start listening on the socket */ |
---|
.. | .. |
---|
2166 | 2201 | return 0; |
---|
2167 | 2202 | } |
---|
2168 | 2203 | |
---|
2169 | | -static int rfcomm_dlc_debugfs_open(struct inode *inode, struct file *file) |
---|
2170 | | -{ |
---|
2171 | | - return single_open(file, rfcomm_dlc_debugfs_show, inode->i_private); |
---|
2172 | | -} |
---|
2173 | | - |
---|
2174 | | -static const struct file_operations rfcomm_dlc_debugfs_fops = { |
---|
2175 | | - .open = rfcomm_dlc_debugfs_open, |
---|
2176 | | - .read = seq_read, |
---|
2177 | | - .llseek = seq_lseek, |
---|
2178 | | - .release = single_release, |
---|
2179 | | -}; |
---|
| 2204 | +DEFINE_SHOW_ATTRIBUTE(rfcomm_dlc_debugfs); |
---|
2180 | 2205 | |
---|
2181 | 2206 | static struct dentry *rfcomm_dlc_debugfs; |
---|
2182 | 2207 | |
---|
.. | .. |
---|
2245 | 2270 | |
---|
2246 | 2271 | module_param(channel_mtu, int, 0644); |
---|
2247 | 2272 | MODULE_PARM_DESC(channel_mtu, "Default MTU for the RFCOMM channel"); |
---|
2248 | | - |
---|
2249 | | -module_param(l2cap_mtu, uint, 0644); |
---|
2250 | | -MODULE_PARM_DESC(l2cap_mtu, "Default MTU for the L2CAP connection"); |
---|
2251 | 2273 | |
---|
2252 | 2274 | module_param(l2cap_ertm, bool, 0644); |
---|
2253 | 2275 | MODULE_PARM_DESC(l2cap_ertm, "Use L2CAP ERTM mode for connection"); |
---|