blob: 7cf193f0eea71749fee7de6b8a77f14d666474f5 [file] [log] [blame]
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +09001/*
Linus Torvalds1da177e2005-04-16 15:20:36 -07002 RFCOMM implementation for Linux Bluetooth stack (BlueZ).
3 Copyright (C) 2002 Maxim Krasnyansky <maxk@qualcomm.com>
4 Copyright (C) 2002 Marcel Holtmann <marcel@holtmann.org>
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License version 2 as
8 published by the Free Software Foundation;
9
10 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
11 OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
12 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY RIGHTS.
13 IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) AND AUTHOR(S) BE LIABLE FOR ANY
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +090014 CLAIM, OR ANY SPECIAL INDIRECT OR CONSEQUENTIAL DAMAGES, OR ANY DAMAGES
15 WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
16 ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
Linus Torvalds1da177e2005-04-16 15:20:36 -070017 OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
18
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +090019 ALL LIABILITY, INCLUDING LIABILITY FOR INFRINGEMENT OF ANY PATENTS,
20 COPYRIGHTS, TRADEMARKS OR OTHER RIGHTS, RELATING TO USE OF THIS
Linus Torvalds1da177e2005-04-16 15:20:36 -070021 SOFTWARE IS DISCLAIMED.
22*/
23
24/*
25 * RFCOMM TTY.
Linus Torvalds1da177e2005-04-16 15:20:36 -070026 */
27
Linus Torvalds1da177e2005-04-16 15:20:36 -070028#include <linux/module.h>
29
30#include <linux/tty.h>
31#include <linux/tty_driver.h>
32#include <linux/tty_flip.h>
33
Linus Torvalds1da177e2005-04-16 15:20:36 -070034#include <net/bluetooth/bluetooth.h>
Marcel Holtmann0a85b962006-07-06 13:09:02 +020035#include <net/bluetooth/hci_core.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070036#include <net/bluetooth/rfcomm.h>
37
Linus Torvalds1da177e2005-04-16 15:20:36 -070038#define RFCOMM_TTY_MAGIC 0x6d02 /* magic number for rfcomm struct */
39#define RFCOMM_TTY_PORTS RFCOMM_MAX_DEV /* whole lotta rfcomm devices */
40#define RFCOMM_TTY_MAJOR 216 /* device node major id of the usb/bluetooth.c driver */
41#define RFCOMM_TTY_MINOR 0
42
43static struct tty_driver *rfcomm_tty_driver;
44
45struct rfcomm_dev {
Jiri Slabyf60db8c2012-04-02 13:54:50 +020046 struct tty_port port;
Linus Torvalds1da177e2005-04-16 15:20:36 -070047 struct list_head list;
Linus Torvalds1da177e2005-04-16 15:20:36 -070048
49 char name[12];
50 int id;
51 unsigned long flags;
Linus Torvalds1da177e2005-04-16 15:20:36 -070052 int err;
53
54 bdaddr_t src;
55 bdaddr_t dst;
Andrei Emeltchenko285b4e92010-12-01 16:58:23 +020056 u8 channel;
Linus Torvalds1da177e2005-04-16 15:20:36 -070057
Andrei Emeltchenko285b4e92010-12-01 16:58:23 +020058 uint modem_status;
Linus Torvalds1da177e2005-04-16 15:20:36 -070059
60 struct rfcomm_dlc *dlc;
Linus Torvalds1da177e2005-04-16 15:20:36 -070061
Marcel Holtmannc1a33132007-02-17 23:58:57 +010062 struct device *tty_dev;
63
Andrei Emeltchenko285b4e92010-12-01 16:58:23 +020064 atomic_t wmem_alloc;
Marcel Holtmanna0c22f22008-07-14 20:13:52 +020065
66 struct sk_buff_head pending;
Linus Torvalds1da177e2005-04-16 15:20:36 -070067};
68
69static LIST_HEAD(rfcomm_dev_list);
Gustavo F. Padovan393432c2011-12-27 15:28:45 -020070static DEFINE_SPINLOCK(rfcomm_dev_lock);
Linus Torvalds1da177e2005-04-16 15:20:36 -070071
72static void rfcomm_dev_data_ready(struct rfcomm_dlc *dlc, struct sk_buff *skb);
73static void rfcomm_dev_state_change(struct rfcomm_dlc *dlc, int err);
74static void rfcomm_dev_modem_status(struct rfcomm_dlc *dlc, u8 v24_sig);
75
Linus Torvalds1da177e2005-04-16 15:20:36 -070076/* ---- Device functions ---- */
Jiri Slaby67054012012-04-02 13:54:51 +020077
Jiri Slaby67054012012-04-02 13:54:51 +020078static void rfcomm_dev_destruct(struct tty_port *port)
Linus Torvalds1da177e2005-04-16 15:20:36 -070079{
Jiri Slaby67054012012-04-02 13:54:51 +020080 struct rfcomm_dev *dev = container_of(port, struct rfcomm_dev, port);
Linus Torvalds1da177e2005-04-16 15:20:36 -070081 struct rfcomm_dlc *dlc = dev->dlc;
82
83 BT_DBG("dev %p dlc %p", dev, dlc);
84
Gianluca Anzolinebe937f2013-07-29 17:08:09 +020085 spin_lock(&rfcomm_dev_lock);
86 list_del(&dev->list);
87 spin_unlock(&rfcomm_dev_lock);
Ville Tervo8de0a152007-07-11 09:23:41 +020088
Linus Torvalds1da177e2005-04-16 15:20:36 -070089 rfcomm_dlc_lock(dlc);
90 /* Detach DLC if it's owned by this dev */
91 if (dlc->owner == dev)
92 dlc->owner = NULL;
93 rfcomm_dlc_unlock(dlc);
94
95 rfcomm_dlc_put(dlc);
96
97 tty_unregister_device(rfcomm_tty_driver, dev->id);
98
Linus Torvalds1da177e2005-04-16 15:20:36 -070099 kfree(dev);
100
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900101 /* It's safe to call module_put() here because socket still
Linus Torvalds1da177e2005-04-16 15:20:36 -0700102 holds reference to this module. */
103 module_put(THIS_MODULE);
104}
105
Gianluca Anzolincad348a2013-07-29 17:08:11 +0200106/* device-specific initialization: open the dlc */
107static int rfcomm_dev_activate(struct tty_port *port, struct tty_struct *tty)
108{
109 struct rfcomm_dev *dev = container_of(port, struct rfcomm_dev, port);
110
Peter Hurley136c3732014-02-09 20:59:02 -0500111 return rfcomm_dlc_open(dev->dlc, &dev->src, &dev->dst, dev->channel);
Gianluca Anzolincad348a2013-07-29 17:08:11 +0200112}
113
Peter Hurley7f717b92014-02-09 20:59:01 -0500114/* we block the open until the dlc->state becomes BT_CONNECTED */
115static int rfcomm_dev_carrier_raised(struct tty_port *port)
116{
117 struct rfcomm_dev *dev = container_of(port, struct rfcomm_dev, port);
118
119 return (dev->dlc->state == BT_CONNECTED);
120}
121
Gianluca Anzolincad348a2013-07-29 17:08:11 +0200122/* device-specific cleanup: close the dlc */
123static void rfcomm_dev_shutdown(struct tty_port *port)
124{
125 struct rfcomm_dev *dev = container_of(port, struct rfcomm_dev, port);
126
127 if (dev->tty_dev->parent)
128 device_move(dev->tty_dev, NULL, DPM_ORDER_DEV_LAST);
129
130 /* close the dlc */
131 rfcomm_dlc_close(dev->dlc, 0);
132}
133
Jiri Slaby67054012012-04-02 13:54:51 +0200134static const struct tty_port_operations rfcomm_port_ops = {
135 .destruct = rfcomm_dev_destruct,
Gianluca Anzolincad348a2013-07-29 17:08:11 +0200136 .activate = rfcomm_dev_activate,
137 .shutdown = rfcomm_dev_shutdown,
Peter Hurley136c3732014-02-09 20:59:02 -0500138 .carrier_raised = rfcomm_dev_carrier_raised,
Jiri Slaby67054012012-04-02 13:54:51 +0200139};
Linus Torvalds1da177e2005-04-16 15:20:36 -0700140
141static struct rfcomm_dev *__rfcomm_dev_get(int id)
142{
143 struct rfcomm_dev *dev;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700144
Luiz Augusto von Dentz8035ded2011-11-01 10:58:56 +0200145 list_for_each_entry(dev, &rfcomm_dev_list, list)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700146 if (dev->id == id)
147 return dev;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700148
149 return NULL;
150}
151
Gustavo Padovan6039aa72012-05-23 04:04:18 -0300152static struct rfcomm_dev *rfcomm_dev_get(int id)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700153{
154 struct rfcomm_dev *dev;
155
Gustavo F. Padovan393432c2011-12-27 15:28:45 -0200156 spin_lock(&rfcomm_dev_lock);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700157
158 dev = __rfcomm_dev_get(id);
Ville Tervo8de0a152007-07-11 09:23:41 +0200159
Peter Hurley082a1532014-02-09 20:59:05 -0500160 if (dev && !tty_port_get(&dev->port))
161 dev = NULL;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700162
Gustavo F. Padovan393432c2011-12-27 15:28:45 -0200163 spin_unlock(&rfcomm_dev_lock);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700164
165 return dev;
166}
167
Peter Hurleyf87c24e2014-02-09 20:59:03 -0500168static struct device *rfcomm_get_device(struct rfcomm_dev *dev)
169{
170 struct hci_dev *hdev;
171 struct hci_conn *conn;
172
173 hdev = hci_get_route(&dev->dst, &dev->src);
174 if (!hdev)
175 return NULL;
176
177 conn = hci_conn_hash_lookup_ba(hdev, ACL_LINK, &dev->dst);
178
179 hci_dev_put(hdev);
180
181 return conn ? &conn->dev : NULL;
182}
183
Marcel Holtmanndae6a0f2007-10-20 14:52:38 +0200184static ssize_t show_address(struct device *tty_dev, struct device_attribute *attr, char *buf)
185{
186 struct rfcomm_dev *dev = dev_get_drvdata(tty_dev);
Andrei Emeltchenkofcb73332012-09-25 12:49:44 +0300187 return sprintf(buf, "%pMR\n", &dev->dst);
Marcel Holtmanndae6a0f2007-10-20 14:52:38 +0200188}
189
190static ssize_t show_channel(struct device *tty_dev, struct device_attribute *attr, char *buf)
191{
192 struct rfcomm_dev *dev = dev_get_drvdata(tty_dev);
193 return sprintf(buf, "%d\n", dev->channel);
194}
195
196static DEVICE_ATTR(address, S_IRUGO, show_address, NULL);
197static DEVICE_ATTR(channel, S_IRUGO, show_channel, NULL);
198
Linus Torvalds1da177e2005-04-16 15:20:36 -0700199static int rfcomm_dev_add(struct rfcomm_dev_req *req, struct rfcomm_dlc *dlc)
200{
Luiz Augusto von Dentz8035ded2011-11-01 10:58:56 +0200201 struct rfcomm_dev *dev, *entry;
Luiz Augusto von Dentze57d758a2012-03-07 20:20:14 +0200202 struct list_head *head = &rfcomm_dev_list;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700203 int err = 0;
204
205 BT_DBG("id %d channel %d", req->dev_id, req->channel);
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900206
Marcel Holtmann25ea6db2006-07-06 15:40:09 +0200207 dev = kzalloc(sizeof(struct rfcomm_dev), GFP_KERNEL);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700208 if (!dev)
209 return -ENOMEM;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700210
Gustavo F. Padovan393432c2011-12-27 15:28:45 -0200211 spin_lock(&rfcomm_dev_lock);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700212
213 if (req->dev_id < 0) {
214 dev->id = 0;
215
Luiz Augusto von Dentz8035ded2011-11-01 10:58:56 +0200216 list_for_each_entry(entry, &rfcomm_dev_list, list) {
217 if (entry->id != dev->id)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700218 break;
219
220 dev->id++;
Luiz Augusto von Dentze57d758a2012-03-07 20:20:14 +0200221 head = &entry->list;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700222 }
223 } else {
224 dev->id = req->dev_id;
225
Luiz Augusto von Dentz8035ded2011-11-01 10:58:56 +0200226 list_for_each_entry(entry, &rfcomm_dev_list, list) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700227 if (entry->id == dev->id) {
228 err = -EADDRINUSE;
229 goto out;
230 }
231
232 if (entry->id > dev->id - 1)
233 break;
234
Luiz Augusto von Dentze57d758a2012-03-07 20:20:14 +0200235 head = &entry->list;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700236 }
237 }
238
239 if ((dev->id < 0) || (dev->id > RFCOMM_MAX_DEV - 1)) {
240 err = -ENFILE;
241 goto out;
242 }
243
244 sprintf(dev->name, "rfcomm%d", dev->id);
245
246 list_add(&dev->list, head);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700247
248 bacpy(&dev->src, &req->src);
249 bacpy(&dev->dst, &req->dst);
250 dev->channel = req->channel;
251
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900252 dev->flags = req->flags &
Linus Torvalds1da177e2005-04-16 15:20:36 -0700253 ((1 << RFCOMM_RELEASE_ONHUP) | (1 << RFCOMM_REUSE_DLC));
254
Jiri Slabyf60db8c2012-04-02 13:54:50 +0200255 tty_port_init(&dev->port);
Jiri Slaby67054012012-04-02 13:54:51 +0200256 dev->port.ops = &rfcomm_port_ops;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700257
Marcel Holtmanna0c22f22008-07-14 20:13:52 +0200258 skb_queue_head_init(&dev->pending);
259
Linus Torvalds1da177e2005-04-16 15:20:36 -0700260 rfcomm_dlc_lock(dlc);
Marcel Holtmanna0c22f22008-07-14 20:13:52 +0200261
262 if (req->flags & (1 << RFCOMM_REUSE_DLC)) {
263 struct sock *sk = dlc->owner;
264 struct sk_buff *skb;
265
266 BUG_ON(!sk);
267
268 rfcomm_dlc_throttle(dlc);
269
270 while ((skb = skb_dequeue(&sk->sk_receive_queue))) {
271 skb_orphan(skb);
272 skb_queue_tail(&dev->pending, skb);
273 atomic_sub(skb->len, &sk->sk_rmem_alloc);
274 }
275 }
276
Linus Torvalds1da177e2005-04-16 15:20:36 -0700277 dlc->data_ready = rfcomm_dev_data_ready;
278 dlc->state_change = rfcomm_dev_state_change;
279 dlc->modem_status = rfcomm_dev_modem_status;
280
281 dlc->owner = dev;
282 dev->dlc = dlc;
Marcel Holtmann8b6b3da2008-07-14 20:13:52 +0200283
284 rfcomm_dev_modem_status(dlc, dlc->remote_v24_sig);
285
Linus Torvalds1da177e2005-04-16 15:20:36 -0700286 rfcomm_dlc_unlock(dlc);
287
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900288 /* It's safe to call __module_get() here because socket already
Linus Torvalds1da177e2005-04-16 15:20:36 -0700289 holds reference to this module. */
290 __module_get(THIS_MODULE);
291
292out:
Gustavo F. Padovan393432c2011-12-27 15:28:45 -0200293 spin_unlock(&rfcomm_dev_lock);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700294
Ilpo Järvinen037322a2008-12-14 23:18:00 -0800295 if (err < 0)
296 goto free;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700297
Jiri Slaby734cc172012-08-07 21:47:47 +0200298 dev->tty_dev = tty_port_register_device(&dev->port, rfcomm_tty_driver,
299 dev->id, NULL);
Ville Tervo8de0a152007-07-11 09:23:41 +0200300 if (IS_ERR(dev->tty_dev)) {
Marcel Holtmann09c7d822007-07-26 00:12:25 -0700301 err = PTR_ERR(dev->tty_dev);
Gianluca Anzolinebe937f2013-07-29 17:08:09 +0200302 spin_lock(&rfcomm_dev_lock);
Ville Tervo8de0a152007-07-11 09:23:41 +0200303 list_del(&dev->list);
Gianluca Anzolinebe937f2013-07-29 17:08:09 +0200304 spin_unlock(&rfcomm_dev_lock);
Ilpo Järvinen037322a2008-12-14 23:18:00 -0800305 goto free;
Ville Tervo8de0a152007-07-11 09:23:41 +0200306 }
307
Marcel Holtmanndae6a0f2007-10-20 14:52:38 +0200308 dev_set_drvdata(dev->tty_dev, dev);
309
310 if (device_create_file(dev->tty_dev, &dev_attr_address) < 0)
311 BT_ERR("Failed to create address attribute");
312
313 if (device_create_file(dev->tty_dev, &dev_attr_channel) < 0)
314 BT_ERR("Failed to create channel attribute");
315
Linus Torvalds1da177e2005-04-16 15:20:36 -0700316 return dev->id;
Ilpo Järvinen037322a2008-12-14 23:18:00 -0800317
318free:
319 kfree(dev);
320 return err;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700321}
322
Linus Torvalds1da177e2005-04-16 15:20:36 -0700323/* ---- Send buffer ---- */
324static inline unsigned int rfcomm_room(struct rfcomm_dlc *dlc)
325{
326 /* We can't let it be zero, because we don't get a callback
327 when tx_credits becomes nonzero, hence we'd never wake up */
328 return dlc->mtu * (dlc->tx_credits?:1);
329}
330
331static void rfcomm_wfree(struct sk_buff *skb)
332{
333 struct rfcomm_dev *dev = (void *) skb->sk;
334 atomic_sub(skb->truesize, &dev->wmem_alloc);
Gianluca Anzolin396dc222013-07-29 17:08:08 +0200335 if (test_bit(RFCOMM_TTY_ATTACHED, &dev->flags))
336 tty_port_tty_wakeup(&dev->port);
Jiri Slaby67054012012-04-02 13:54:51 +0200337 tty_port_put(&dev->port);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700338}
339
Gustavo Padovan6039aa72012-05-23 04:04:18 -0300340static void rfcomm_set_owner_w(struct sk_buff *skb, struct rfcomm_dev *dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700341{
Jiri Slaby67054012012-04-02 13:54:51 +0200342 tty_port_get(&dev->port);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700343 atomic_add(skb->truesize, &dev->wmem_alloc);
344 skb->sk = (void *) dev;
345 skb->destructor = rfcomm_wfree;
346}
347
Al Virodd0fc662005-10-07 07:46:04 +0100348static struct sk_buff *rfcomm_wmalloc(struct rfcomm_dev *dev, unsigned long size, gfp_t priority)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700349{
350 if (atomic_read(&dev->wmem_alloc) < rfcomm_room(dev->dlc)) {
351 struct sk_buff *skb = alloc_skb(size, priority);
352 if (skb) {
353 rfcomm_set_owner_w(skb, dev);
354 return skb;
355 }
356 }
357 return NULL;
358}
359
360/* ---- Device IOCTLs ---- */
361
362#define NOCAP_FLAGS ((1 << RFCOMM_REUSE_DLC) | (1 << RFCOMM_RELEASE_ONHUP))
363
364static int rfcomm_create_dev(struct sock *sk, void __user *arg)
365{
366 struct rfcomm_dev_req req;
367 struct rfcomm_dlc *dlc;
368 int id;
369
370 if (copy_from_user(&req, arg, sizeof(req)))
371 return -EFAULT;
372
Ville Tervo8de0a152007-07-11 09:23:41 +0200373 BT_DBG("sk %p dev_id %d flags 0x%x", sk, req.dev_id, req.flags);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700374
375 if (req.flags != NOCAP_FLAGS && !capable(CAP_NET_ADMIN))
376 return -EPERM;
377
378 if (req.flags & (1 << RFCOMM_REUSE_DLC)) {
379 /* Socket must be connected */
380 if (sk->sk_state != BT_CONNECTED)
381 return -EBADFD;
382
383 dlc = rfcomm_pi(sk)->dlc;
384 rfcomm_dlc_hold(dlc);
385 } else {
386 dlc = rfcomm_dlc_alloc(GFP_KERNEL);
387 if (!dlc)
388 return -ENOMEM;
389 }
390
391 id = rfcomm_dev_add(&req, dlc);
392 if (id < 0) {
393 rfcomm_dlc_put(dlc);
394 return id;
395 }
396
397 if (req.flags & (1 << RFCOMM_REUSE_DLC)) {
398 /* DLC is now used by device.
399 * Socket must be disconnected */
400 sk->sk_state = BT_CLOSED;
401 }
402
403 return id;
404}
405
406static int rfcomm_release_dev(void __user *arg)
407{
408 struct rfcomm_dev_req req;
409 struct rfcomm_dev *dev;
Gianluca Anzolin396dc222013-07-29 17:08:08 +0200410 struct tty_struct *tty;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700411
412 if (copy_from_user(&req, arg, sizeof(req)))
413 return -EFAULT;
414
Ville Tervo8de0a152007-07-11 09:23:41 +0200415 BT_DBG("dev_id %d flags 0x%x", req.dev_id, req.flags);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700416
Andrei Emeltchenko285b4e92010-12-01 16:58:23 +0200417 dev = rfcomm_dev_get(req.dev_id);
418 if (!dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700419 return -ENODEV;
420
421 if (dev->flags != NOCAP_FLAGS && !capable(CAP_NET_ADMIN)) {
Jiri Slaby67054012012-04-02 13:54:51 +0200422 tty_port_put(&dev->port);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700423 return -EPERM;
424 }
425
426 if (req.flags & (1 << RFCOMM_HANGUP_NOW))
427 rfcomm_dlc_close(dev->dlc, 0);
428
Mikko Rapeli84950cf2007-07-11 09:18:15 +0200429 /* Shut down TTY synchronously before freeing rfcomm_dev */
Gianluca Anzolin396dc222013-07-29 17:08:08 +0200430 tty = tty_port_tty_get(&dev->port);
431 if (tty) {
432 tty_vhangup(tty);
433 tty_kref_put(tty);
434 }
Mikko Rapeli84950cf2007-07-11 09:18:15 +0200435
Gianluca Anzolin5b899242014-01-06 21:23:50 +0100436 if (!test_bit(RFCOMM_RELEASE_ONHUP, &dev->flags) &&
437 !test_and_set_bit(RFCOMM_TTY_RELEASED, &dev->flags))
Gianluca Anzolinece31502013-07-29 17:08:12 +0200438 tty_port_put(&dev->port);
439
Jiri Slaby67054012012-04-02 13:54:51 +0200440 tty_port_put(&dev->port);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700441 return 0;
442}
443
444static int rfcomm_get_dev_list(void __user *arg)
445{
Luiz Augusto von Dentz8035ded2011-11-01 10:58:56 +0200446 struct rfcomm_dev *dev;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700447 struct rfcomm_dev_list_req *dl;
448 struct rfcomm_dev_info *di;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700449 int n = 0, size, err;
450 u16 dev_num;
451
452 BT_DBG("");
453
454 if (get_user(dev_num, (u16 __user *) arg))
455 return -EFAULT;
456
457 if (!dev_num || dev_num > (PAGE_SIZE * 4) / sizeof(*di))
458 return -EINVAL;
459
460 size = sizeof(*dl) + dev_num * sizeof(*di);
461
Mathias Krausef9432c52012-08-15 11:31:49 +0000462 dl = kzalloc(size, GFP_KERNEL);
Andrei Emeltchenko285b4e92010-12-01 16:58:23 +0200463 if (!dl)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700464 return -ENOMEM;
465
466 di = dl->dev_info;
467
Gustavo F. Padovan393432c2011-12-27 15:28:45 -0200468 spin_lock(&rfcomm_dev_lock);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700469
Luiz Augusto von Dentz8035ded2011-11-01 10:58:56 +0200470 list_for_each_entry(dev, &rfcomm_dev_list, list) {
Ville Tervo8de0a152007-07-11 09:23:41 +0200471 if (test_bit(RFCOMM_TTY_RELEASED, &dev->flags))
472 continue;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700473 (di + n)->id = dev->id;
474 (di + n)->flags = dev->flags;
475 (di + n)->state = dev->dlc->state;
476 (di + n)->channel = dev->channel;
477 bacpy(&(di + n)->src, &dev->src);
478 bacpy(&(di + n)->dst, &dev->dst);
479 if (++n >= dev_num)
480 break;
481 }
482
Gustavo F. Padovan393432c2011-12-27 15:28:45 -0200483 spin_unlock(&rfcomm_dev_lock);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700484
485 dl->dev_num = n;
486 size = sizeof(*dl) + n * sizeof(*di);
487
488 err = copy_to_user(arg, dl, size);
489 kfree(dl);
490
491 return err ? -EFAULT : 0;
492}
493
494static int rfcomm_get_dev_info(void __user *arg)
495{
496 struct rfcomm_dev *dev;
497 struct rfcomm_dev_info di;
498 int err = 0;
499
500 BT_DBG("");
501
502 if (copy_from_user(&di, arg, sizeof(di)))
503 return -EFAULT;
504
Andrei Emeltchenko285b4e92010-12-01 16:58:23 +0200505 dev = rfcomm_dev_get(di.id);
506 if (!dev)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700507 return -ENODEV;
508
509 di.flags = dev->flags;
510 di.channel = dev->channel;
511 di.state = dev->dlc->state;
512 bacpy(&di.src, &dev->src);
513 bacpy(&di.dst, &dev->dst);
514
515 if (copy_to_user(arg, &di, sizeof(di)))
516 err = -EFAULT;
517
Jiri Slaby67054012012-04-02 13:54:51 +0200518 tty_port_put(&dev->port);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700519 return err;
520}
521
522int rfcomm_dev_ioctl(struct sock *sk, unsigned int cmd, void __user *arg)
523{
524 BT_DBG("cmd %d arg %p", cmd, arg);
525
526 switch (cmd) {
527 case RFCOMMCREATEDEV:
528 return rfcomm_create_dev(sk, arg);
529
530 case RFCOMMRELEASEDEV:
531 return rfcomm_release_dev(arg);
532
533 case RFCOMMGETDEVLIST:
534 return rfcomm_get_dev_list(arg);
535
536 case RFCOMMGETDEVINFO:
537 return rfcomm_get_dev_info(arg);
538 }
539
540 return -EINVAL;
541}
542
543/* ---- DLC callbacks ---- */
544static void rfcomm_dev_data_ready(struct rfcomm_dlc *dlc, struct sk_buff *skb)
545{
546 struct rfcomm_dev *dev = dlc->owner;
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900547
Marcel Holtmanna0c22f22008-07-14 20:13:52 +0200548 if (!dev) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700549 kfree_skb(skb);
550 return;
551 }
552
Jiri Slaby2e124b42013-01-03 15:53:06 +0100553 if (!skb_queue_empty(&dev->pending)) {
Marcel Holtmanna0c22f22008-07-14 20:13:52 +0200554 skb_queue_tail(&dev->pending, skb);
555 return;
556 }
557
Jiri Slaby2e124b42013-01-03 15:53:06 +0100558 BT_DBG("dlc %p len %d", dlc, skb->len);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700559
Jiri Slaby05c7cd32013-01-03 15:53:04 +0100560 tty_insert_flip_string(&dev->port, skb->data, skb->len);
Jiri Slaby2e124b42013-01-03 15:53:06 +0100561 tty_flip_buffer_push(&dev->port);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700562
563 kfree_skb(skb);
564}
565
566static void rfcomm_dev_state_change(struct rfcomm_dlc *dlc, int err)
567{
568 struct rfcomm_dev *dev = dlc->owner;
569 if (!dev)
570 return;
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900571
Linus Torvalds1da177e2005-04-16 15:20:36 -0700572 BT_DBG("dlc %p dev %p err %d", dlc, dev, err);
573
574 dev->err = err;
Peter Hurley136c3732014-02-09 20:59:02 -0500575 if (dlc->state == BT_CONNECTED) {
576 device_move(dev->tty_dev, rfcomm_get_device(dev),
577 DPM_ORDER_DEV_AFTER_PARENT);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700578
Peter Hurley136c3732014-02-09 20:59:02 -0500579 wake_up_interruptible(&dev->port.open_wait);
580 } else if (dlc->state == BT_CLOSED)
Gianluca Anzolin29cd7182013-08-27 18:28:46 +0200581 tty_port_tty_hangup(&dev->port, false);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700582}
583
584static void rfcomm_dev_modem_status(struct rfcomm_dlc *dlc, u8 v24_sig)
585{
586 struct rfcomm_dev *dev = dlc->owner;
587 if (!dev)
588 return;
Timo Teräs7b9eb9e2005-08-09 20:28:21 -0700589
Linus Torvalds1da177e2005-04-16 15:20:36 -0700590 BT_DBG("dlc %p dev %p v24_sig 0x%02x", dlc, dev, v24_sig);
591
Gianluca Anzolin396dc222013-07-29 17:08:08 +0200592 if ((dev->modem_status & TIOCM_CD) && !(v24_sig & RFCOMM_V24_DV))
593 tty_port_tty_hangup(&dev->port, true);
Timo Teräs7b9eb9e2005-08-09 20:28:21 -0700594
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900595 dev->modem_status =
Linus Torvalds1da177e2005-04-16 15:20:36 -0700596 ((v24_sig & RFCOMM_V24_RTC) ? (TIOCM_DSR | TIOCM_DTR) : 0) |
597 ((v24_sig & RFCOMM_V24_RTR) ? (TIOCM_RTS | TIOCM_CTS) : 0) |
598 ((v24_sig & RFCOMM_V24_IC) ? TIOCM_RI : 0) |
599 ((v24_sig & RFCOMM_V24_DV) ? TIOCM_CD : 0);
600}
601
602/* ---- TTY functions ---- */
Marcel Holtmanna0c22f22008-07-14 20:13:52 +0200603static void rfcomm_tty_copy_pending(struct rfcomm_dev *dev)
604{
Marcel Holtmanna0c22f22008-07-14 20:13:52 +0200605 struct sk_buff *skb;
606 int inserted = 0;
607
Jiri Slaby2e124b42013-01-03 15:53:06 +0100608 BT_DBG("dev %p", dev);
Marcel Holtmanna0c22f22008-07-14 20:13:52 +0200609
610 rfcomm_dlc_lock(dev->dlc);
611
612 while ((skb = skb_dequeue(&dev->pending))) {
Jiri Slaby05c7cd32013-01-03 15:53:04 +0100613 inserted += tty_insert_flip_string(&dev->port, skb->data,
614 skb->len);
Marcel Holtmanna0c22f22008-07-14 20:13:52 +0200615 kfree_skb(skb);
616 }
617
618 rfcomm_dlc_unlock(dev->dlc);
619
620 if (inserted > 0)
Jiri Slaby2e124b42013-01-03 15:53:06 +0100621 tty_flip_buffer_push(&dev->port);
Marcel Holtmanna0c22f22008-07-14 20:13:52 +0200622}
623
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200624/* do the reverse of install, clearing the tty fields and releasing the
625 * reference to tty_port
626 */
627static void rfcomm_tty_cleanup(struct tty_struct *tty)
628{
629 struct rfcomm_dev *dev = tty->driver_data;
630
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200631 clear_bit(RFCOMM_TTY_ATTACHED, &dev->flags);
632
633 rfcomm_dlc_lock(dev->dlc);
634 tty->driver_data = NULL;
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200635 rfcomm_dlc_unlock(dev->dlc);
636
Gianluca Anzolinffe6b682013-07-29 17:08:13 +0200637 /*
638 * purge the dlc->tx_queue to avoid circular dependencies
639 * between dev and dlc
640 */
641 skb_queue_purge(&dev->dlc->tx_queue);
642
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200643 tty_port_put(&dev->port);
644}
645
646/* we acquire the tty_port reference since it's here the tty is first used
647 * by setting the termios. We also populate the driver_data field and install
648 * the tty port
649 */
650static int rfcomm_tty_install(struct tty_driver *driver, struct tty_struct *tty)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700651{
Linus Torvalds1da177e2005-04-16 15:20:36 -0700652 struct rfcomm_dev *dev;
653 struct rfcomm_dlc *dlc;
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200654 int err;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700655
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200656 dev = rfcomm_dev_get(tty->index);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700657 if (!dev)
658 return -ENODEV;
659
Linus Torvalds1da177e2005-04-16 15:20:36 -0700660 dlc = dev->dlc;
661
662 /* Attach TTY and open DLC */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700663 rfcomm_dlc_lock(dlc);
664 tty->driver_data = dev;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700665 rfcomm_dlc_unlock(dlc);
666 set_bit(RFCOMM_TTY_ATTACHED, &dev->flags);
667
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200668 /* install the tty_port */
669 err = tty_port_install(&dev->port, driver, tty);
Gianluca Anzolin5b899242014-01-06 21:23:50 +0100670 if (err) {
Gianluca Anzolincad348a2013-07-29 17:08:11 +0200671 rfcomm_tty_cleanup(tty);
Gianluca Anzolin5b899242014-01-06 21:23:50 +0100672 return err;
673 }
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200674
Gianluca Anzolin5b899242014-01-06 21:23:50 +0100675 /* take over the tty_port reference if the port was created with the
676 * flag RFCOMM_RELEASE_ONHUP. This will force the release of the port
677 * when the last process closes the tty. The behaviour is expected by
678 * userspace.
679 */
680 if (test_bit(RFCOMM_RELEASE_ONHUP, &dev->flags))
681 tty_port_put(&dev->port);
682
683 return 0;
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200684}
685
686static int rfcomm_tty_open(struct tty_struct *tty, struct file *filp)
687{
688 struct rfcomm_dev *dev = tty->driver_data;
Gianluca Anzolincad348a2013-07-29 17:08:11 +0200689 int err;
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200690
691 BT_DBG("tty %p id %d", tty, tty->index);
692
693 BT_DBG("dev %p dst %pMR channel %d opened %d", dev, &dev->dst,
694 dev->channel, dev->port.count);
695
Gianluca Anzolincad348a2013-07-29 17:08:11 +0200696 err = tty_port_open(&dev->port, tty, filp);
697 if (err)
698 return err;
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200699
700 /*
701 * FIXME: rfcomm should use proper flow control for
702 * received data. This hack will be unnecessary and can
703 * be removed when that's implemented
704 */
Marcel Holtmanna0c22f22008-07-14 20:13:52 +0200705 rfcomm_tty_copy_pending(dev);
706
707 rfcomm_dlc_unthrottle(dev->dlc);
708
Gianluca Anzolin54b926a2013-07-29 17:08:10 +0200709 return 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700710}
711
712static void rfcomm_tty_close(struct tty_struct *tty, struct file *filp)
713{
714 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
Jiri Slabyf997a012012-04-02 13:54:53 +0200715
Marcel Holtmann9a5df922008-11-30 12:17:29 +0100716 BT_DBG("tty %p dev %p dlc %p opened %d", tty, dev, dev->dlc,
Jiri Slabyf997a012012-04-02 13:54:53 +0200717 dev->port.count);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700718
Gianluca Anzolincad348a2013-07-29 17:08:11 +0200719 tty_port_close(&dev->port, tty, filp);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700720}
721
722static int rfcomm_tty_write(struct tty_struct *tty, const unsigned char *buf, int count)
723{
724 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
725 struct rfcomm_dlc *dlc = dev->dlc;
726 struct sk_buff *skb;
727 int err = 0, sent = 0, size;
728
729 BT_DBG("tty %p count %d", tty, count);
730
731 while (count) {
732 size = min_t(uint, count, dlc->mtu);
733
734 skb = rfcomm_wmalloc(dev, size + RFCOMM_SKB_RESERVE, GFP_ATOMIC);
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900735
Linus Torvalds1da177e2005-04-16 15:20:36 -0700736 if (!skb)
737 break;
738
739 skb_reserve(skb, RFCOMM_SKB_HEAD_RESERVE);
740
741 memcpy(skb_put(skb, size), buf + sent, size);
742
Andrei Emeltchenko285b4e92010-12-01 16:58:23 +0200743 err = rfcomm_dlc_send(dlc, skb);
744 if (err < 0) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700745 kfree_skb(skb);
746 break;
747 }
748
749 sent += size;
750 count -= size;
751 }
752
753 return sent ? sent : err;
754}
755
756static int rfcomm_tty_write_room(struct tty_struct *tty)
757{
758 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
759 int room;
760
761 BT_DBG("tty %p", tty);
762
Marcel Holtmannb6e557f2007-01-08 02:16:27 +0100763 if (!dev || !dev->dlc)
764 return 0;
765
Linus Torvalds1da177e2005-04-16 15:20:36 -0700766 room = rfcomm_room(dev->dlc) - atomic_read(&dev->wmem_alloc);
767 if (room < 0)
768 room = 0;
Marcel Holtmannb6e557f2007-01-08 02:16:27 +0100769
Linus Torvalds1da177e2005-04-16 15:20:36 -0700770 return room;
771}
772
Alan Cox6caa76b2011-02-14 16:27:22 +0000773static int rfcomm_tty_ioctl(struct tty_struct *tty, unsigned int cmd, unsigned long arg)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700774{
775 BT_DBG("tty %p cmd 0x%02x", tty, cmd);
776
777 switch (cmd) {
778 case TCGETS:
779 BT_DBG("TCGETS is not supported");
780 return -ENOIOCTLCMD;
781
782 case TCSETS:
783 BT_DBG("TCSETS is not supported");
784 return -ENOIOCTLCMD;
785
786 case TIOCMIWAIT:
787 BT_DBG("TIOCMIWAIT");
788 break;
789
Linus Torvalds1da177e2005-04-16 15:20:36 -0700790 case TIOCGSERIAL:
791 BT_ERR("TIOCGSERIAL is not supported");
792 return -ENOIOCTLCMD;
793
794 case TIOCSSERIAL:
795 BT_ERR("TIOCSSERIAL is not supported");
796 return -ENOIOCTLCMD;
797
798 case TIOCSERGSTRUCT:
799 BT_ERR("TIOCSERGSTRUCT is not supported");
800 return -ENOIOCTLCMD;
801
802 case TIOCSERGETLSR:
803 BT_ERR("TIOCSERGETLSR is not supported");
804 return -ENOIOCTLCMD;
805
806 case TIOCSERCONFIG:
807 BT_ERR("TIOCSERCONFIG is not supported");
808 return -ENOIOCTLCMD;
809
810 default:
811 return -ENOIOCTLCMD; /* ioctls which we must ignore */
812
813 }
814
815 return -ENOIOCTLCMD;
816}
817
Alan Cox606d0992006-12-08 02:38:45 -0800818static void rfcomm_tty_set_termios(struct tty_struct *tty, struct ktermios *old)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700819{
Alan Coxadc8d742012-07-14 15:31:47 +0100820 struct ktermios *new = &tty->termios;
J. Suter3a5e9032005-08-09 20:28:46 -0700821 int old_baud_rate = tty_termios_baud_rate(old);
822 int new_baud_rate = tty_termios_baud_rate(new);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700823
J. Suter3a5e9032005-08-09 20:28:46 -0700824 u8 baud, data_bits, stop_bits, parity, x_on, x_off;
825 u16 changes = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700826
J. Suter3a5e9032005-08-09 20:28:46 -0700827 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
828
829 BT_DBG("tty %p termios %p", tty, old);
830
Marcel Holtmannff2d3672006-11-18 22:14:42 +0100831 if (!dev || !dev->dlc || !dev->dlc->session)
Marcel Holtmanncb19d9e2006-10-15 17:31:10 +0200832 return;
833
J. Suter3a5e9032005-08-09 20:28:46 -0700834 /* Handle turning off CRTSCTS */
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900835 if ((old->c_cflag & CRTSCTS) && !(new->c_cflag & CRTSCTS))
J. Suter3a5e9032005-08-09 20:28:46 -0700836 BT_DBG("Turning off CRTSCTS unsupported");
837
838 /* Parity on/off and when on, odd/even */
839 if (((old->c_cflag & PARENB) != (new->c_cflag & PARENB)) ||
Andrei Emeltchenko285b4e92010-12-01 16:58:23 +0200840 ((old->c_cflag & PARODD) != (new->c_cflag & PARODD))) {
J. Suter3a5e9032005-08-09 20:28:46 -0700841 changes |= RFCOMM_RPN_PM_PARITY;
842 BT_DBG("Parity change detected.");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700843 }
J. Suter3a5e9032005-08-09 20:28:46 -0700844
845 /* Mark and space parity are not supported! */
846 if (new->c_cflag & PARENB) {
847 if (new->c_cflag & PARODD) {
848 BT_DBG("Parity is ODD");
849 parity = RFCOMM_RPN_PARITY_ODD;
850 } else {
851 BT_DBG("Parity is EVEN");
852 parity = RFCOMM_RPN_PARITY_EVEN;
853 }
854 } else {
855 BT_DBG("Parity is OFF");
856 parity = RFCOMM_RPN_PARITY_NONE;
857 }
858
859 /* Setting the x_on / x_off characters */
860 if (old->c_cc[VSTOP] != new->c_cc[VSTOP]) {
861 BT_DBG("XOFF custom");
862 x_on = new->c_cc[VSTOP];
863 changes |= RFCOMM_RPN_PM_XON;
864 } else {
865 BT_DBG("XOFF default");
866 x_on = RFCOMM_RPN_XON_CHAR;
867 }
868
869 if (old->c_cc[VSTART] != new->c_cc[VSTART]) {
870 BT_DBG("XON custom");
871 x_off = new->c_cc[VSTART];
872 changes |= RFCOMM_RPN_PM_XOFF;
873 } else {
874 BT_DBG("XON default");
875 x_off = RFCOMM_RPN_XOFF_CHAR;
876 }
877
878 /* Handle setting of stop bits */
879 if ((old->c_cflag & CSTOPB) != (new->c_cflag & CSTOPB))
880 changes |= RFCOMM_RPN_PM_STOP;
881
882 /* POSIX does not support 1.5 stop bits and RFCOMM does not
883 * support 2 stop bits. So a request for 2 stop bits gets
884 * translated to 1.5 stop bits */
Andrei Emeltchenko285b4e92010-12-01 16:58:23 +0200885 if (new->c_cflag & CSTOPB)
J. Suter3a5e9032005-08-09 20:28:46 -0700886 stop_bits = RFCOMM_RPN_STOP_15;
Andrei Emeltchenko285b4e92010-12-01 16:58:23 +0200887 else
J. Suter3a5e9032005-08-09 20:28:46 -0700888 stop_bits = RFCOMM_RPN_STOP_1;
J. Suter3a5e9032005-08-09 20:28:46 -0700889
890 /* Handle number of data bits [5-8] */
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900891 if ((old->c_cflag & CSIZE) != (new->c_cflag & CSIZE))
J. Suter3a5e9032005-08-09 20:28:46 -0700892 changes |= RFCOMM_RPN_PM_DATA;
893
894 switch (new->c_cflag & CSIZE) {
895 case CS5:
896 data_bits = RFCOMM_RPN_DATA_5;
897 break;
898 case CS6:
899 data_bits = RFCOMM_RPN_DATA_6;
900 break;
901 case CS7:
902 data_bits = RFCOMM_RPN_DATA_7;
903 break;
904 case CS8:
905 data_bits = RFCOMM_RPN_DATA_8;
906 break;
907 default:
908 data_bits = RFCOMM_RPN_DATA_8;
909 break;
910 }
911
912 /* Handle baudrate settings */
913 if (old_baud_rate != new_baud_rate)
914 changes |= RFCOMM_RPN_PM_BITRATE;
915
916 switch (new_baud_rate) {
917 case 2400:
918 baud = RFCOMM_RPN_BR_2400;
919 break;
920 case 4800:
921 baud = RFCOMM_RPN_BR_4800;
922 break;
923 case 7200:
924 baud = RFCOMM_RPN_BR_7200;
925 break;
926 case 9600:
927 baud = RFCOMM_RPN_BR_9600;
928 break;
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900929 case 19200:
J. Suter3a5e9032005-08-09 20:28:46 -0700930 baud = RFCOMM_RPN_BR_19200;
931 break;
932 case 38400:
933 baud = RFCOMM_RPN_BR_38400;
934 break;
935 case 57600:
936 baud = RFCOMM_RPN_BR_57600;
937 break;
938 case 115200:
939 baud = RFCOMM_RPN_BR_115200;
940 break;
941 case 230400:
942 baud = RFCOMM_RPN_BR_230400;
943 break;
944 default:
945 /* 9600 is standard accordinag to the RFCOMM specification */
946 baud = RFCOMM_RPN_BR_9600;
947 break;
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +0900948
J. Suter3a5e9032005-08-09 20:28:46 -0700949 }
950
951 if (changes)
952 rfcomm_send_rpn(dev->dlc->session, 1, dev->dlc->dlci, baud,
953 data_bits, stop_bits, parity,
954 RFCOMM_RPN_FLOW_NONE, x_on, x_off, changes);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700955}
956
957static void rfcomm_tty_throttle(struct tty_struct *tty)
958{
959 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
960
961 BT_DBG("tty %p dev %p", tty, dev);
J. Suter3a5e9032005-08-09 20:28:46 -0700962
Linus Torvalds1da177e2005-04-16 15:20:36 -0700963 rfcomm_dlc_throttle(dev->dlc);
964}
965
966static void rfcomm_tty_unthrottle(struct tty_struct *tty)
967{
968 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
969
970 BT_DBG("tty %p dev %p", tty, dev);
J. Suter3a5e9032005-08-09 20:28:46 -0700971
Linus Torvalds1da177e2005-04-16 15:20:36 -0700972 rfcomm_dlc_unthrottle(dev->dlc);
973}
974
975static int rfcomm_tty_chars_in_buffer(struct tty_struct *tty)
976{
977 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700978
979 BT_DBG("tty %p dev %p", tty, dev);
980
Marcel Holtmannb6e557f2007-01-08 02:16:27 +0100981 if (!dev || !dev->dlc)
982 return 0;
983
984 if (!skb_queue_empty(&dev->dlc->tx_queue))
985 return dev->dlc->mtu;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700986
987 return 0;
988}
989
990static void rfcomm_tty_flush_buffer(struct tty_struct *tty)
991{
992 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700993
994 BT_DBG("tty %p dev %p", tty, dev);
995
Marcel Holtmannb6e557f2007-01-08 02:16:27 +0100996 if (!dev || !dev->dlc)
997 return;
998
Linus Torvalds1da177e2005-04-16 15:20:36 -0700999 skb_queue_purge(&dev->dlc->tx_queue);
Alan Coxa352def2008-07-16 21:53:12 +01001000 tty_wakeup(tty);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001001}
1002
1003static void rfcomm_tty_send_xchar(struct tty_struct *tty, char ch)
1004{
1005 BT_DBG("tty %p ch %c", tty, ch);
1006}
1007
1008static void rfcomm_tty_wait_until_sent(struct tty_struct *tty, int timeout)
1009{
1010 BT_DBG("tty %p timeout %d", tty, timeout);
1011}
1012
1013static void rfcomm_tty_hangup(struct tty_struct *tty)
1014{
1015 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001016
1017 BT_DBG("tty %p dev %p", tty, dev);
1018
Gianluca Anzolincad348a2013-07-29 17:08:11 +02001019 tty_port_hangup(&dev->port);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001020}
1021
Alan Cox60b33c12011-02-14 16:26:14 +00001022static int rfcomm_tty_tiocmget(struct tty_struct *tty)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001023{
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +09001024 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001025
1026 BT_DBG("tty %p dev %p", tty, dev);
1027
YOSHIFUJI Hideaki8e87d142007-02-09 23:24:33 +09001028 return dev->modem_status;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001029}
1030
Alan Cox20b9d172011-02-14 16:26:50 +00001031static int rfcomm_tty_tiocmset(struct tty_struct *tty, unsigned int set, unsigned int clear)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001032{
J. Suter3a5e9032005-08-09 20:28:46 -07001033 struct rfcomm_dev *dev = (struct rfcomm_dev *) tty->driver_data;
1034 struct rfcomm_dlc *dlc = dev->dlc;
1035 u8 v24_sig;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001036
1037 BT_DBG("tty %p dev %p set 0x%02x clear 0x%02x", tty, dev, set, clear);
1038
J. Suter3a5e9032005-08-09 20:28:46 -07001039 rfcomm_dlc_get_modem_status(dlc, &v24_sig);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001040
J. Suter3a5e9032005-08-09 20:28:46 -07001041 if (set & TIOCM_DSR || set & TIOCM_DTR)
1042 v24_sig |= RFCOMM_V24_RTC;
1043 if (set & TIOCM_RTS || set & TIOCM_CTS)
1044 v24_sig |= RFCOMM_V24_RTR;
1045 if (set & TIOCM_RI)
1046 v24_sig |= RFCOMM_V24_IC;
1047 if (set & TIOCM_CD)
1048 v24_sig |= RFCOMM_V24_DV;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001049
J. Suter3a5e9032005-08-09 20:28:46 -07001050 if (clear & TIOCM_DSR || clear & TIOCM_DTR)
1051 v24_sig &= ~RFCOMM_V24_RTC;
1052 if (clear & TIOCM_RTS || clear & TIOCM_CTS)
1053 v24_sig &= ~RFCOMM_V24_RTR;
1054 if (clear & TIOCM_RI)
1055 v24_sig &= ~RFCOMM_V24_IC;
1056 if (clear & TIOCM_CD)
1057 v24_sig &= ~RFCOMM_V24_DV;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001058
J. Suter3a5e9032005-08-09 20:28:46 -07001059 rfcomm_dlc_set_modem_status(dlc, v24_sig);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001060
J. Suter3a5e9032005-08-09 20:28:46 -07001061 return 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001062}
1063
1064/* ---- TTY structure ---- */
1065
Jeff Dikeb68e31d2006-10-02 02:17:18 -07001066static const struct tty_operations rfcomm_ops = {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001067 .open = rfcomm_tty_open,
1068 .close = rfcomm_tty_close,
1069 .write = rfcomm_tty_write,
1070 .write_room = rfcomm_tty_write_room,
1071 .chars_in_buffer = rfcomm_tty_chars_in_buffer,
1072 .flush_buffer = rfcomm_tty_flush_buffer,
1073 .ioctl = rfcomm_tty_ioctl,
1074 .throttle = rfcomm_tty_throttle,
1075 .unthrottle = rfcomm_tty_unthrottle,
1076 .set_termios = rfcomm_tty_set_termios,
1077 .send_xchar = rfcomm_tty_send_xchar,
1078 .hangup = rfcomm_tty_hangup,
1079 .wait_until_sent = rfcomm_tty_wait_until_sent,
Linus Torvalds1da177e2005-04-16 15:20:36 -07001080 .tiocmget = rfcomm_tty_tiocmget,
1081 .tiocmset = rfcomm_tty_tiocmset,
Gianluca Anzolin54b926a2013-07-29 17:08:10 +02001082 .install = rfcomm_tty_install,
1083 .cleanup = rfcomm_tty_cleanup,
Linus Torvalds1da177e2005-04-16 15:20:36 -07001084};
1085
Gustavo F. Padovan2f8362a2010-07-24 02:04:45 -03001086int __init rfcomm_init_ttys(void)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001087{
David Herrmann5ada9912011-10-24 15:30:57 +02001088 int error;
1089
Linus Torvalds1da177e2005-04-16 15:20:36 -07001090 rfcomm_tty_driver = alloc_tty_driver(RFCOMM_TTY_PORTS);
1091 if (!rfcomm_tty_driver)
David Herrmann5ada9912011-10-24 15:30:57 +02001092 return -ENOMEM;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001093
Linus Torvalds1da177e2005-04-16 15:20:36 -07001094 rfcomm_tty_driver->driver_name = "rfcomm";
Linus Torvalds1da177e2005-04-16 15:20:36 -07001095 rfcomm_tty_driver->name = "rfcomm";
1096 rfcomm_tty_driver->major = RFCOMM_TTY_MAJOR;
1097 rfcomm_tty_driver->minor_start = RFCOMM_TTY_MINOR;
1098 rfcomm_tty_driver->type = TTY_DRIVER_TYPE_SERIAL;
1099 rfcomm_tty_driver->subtype = SERIAL_TYPE_NORMAL;
Greg Kroah-Hartman331b8312005-06-20 21:15:16 -07001100 rfcomm_tty_driver->flags = TTY_DRIVER_REAL_RAW | TTY_DRIVER_DYNAMIC_DEV;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001101 rfcomm_tty_driver->init_termios = tty_std_termios;
Peter Hurley136c3732014-02-09 20:59:02 -05001102 rfcomm_tty_driver->init_termios.c_cflag = B9600 | CS8 | CREAD | HUPCL;
Marcel Holtmannca37bdd52008-07-14 20:13:52 +02001103 rfcomm_tty_driver->init_termios.c_lflag &= ~ICANON;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001104 tty_set_operations(rfcomm_tty_driver, &rfcomm_ops);
1105
David Herrmann5ada9912011-10-24 15:30:57 +02001106 error = tty_register_driver(rfcomm_tty_driver);
1107 if (error) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001108 BT_ERR("Can't register RFCOMM TTY driver");
1109 put_tty_driver(rfcomm_tty_driver);
David Herrmann5ada9912011-10-24 15:30:57 +02001110 return error;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001111 }
1112
1113 BT_INFO("RFCOMM TTY layer initialized");
1114
1115 return 0;
1116}
1117
Gustavo F. Padovan28e95092010-07-31 19:57:05 -03001118void rfcomm_cleanup_ttys(void)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001119{
1120 tty_unregister_driver(rfcomm_tty_driver);
1121 put_tty_driver(rfcomm_tty_driver);
1122}