Linux-2.6.12-rc2
[linux-flexiantxendom0-natty.git] / net / bluetooth / af_bluetooth.c
1 /* 
2    BlueZ - Bluetooth protocol stack for Linux
3    Copyright (C) 2000-2001 Qualcomm Incorporated
4
5    Written 2000,2001 by Maxim Krasnyansky <maxk@qualcomm.com>
6
7    This program is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License version 2 as
9    published by the Free Software Foundation;
10
11    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
12    OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
13    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY RIGHTS.
14    IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) AND AUTHOR(S) BE LIABLE FOR ANY
15    CLAIM, OR ANY SPECIAL INDIRECT OR CONSEQUENTIAL DAMAGES, OR ANY DAMAGES 
16    WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 
17    ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 
18    OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
19
20    ALL LIABILITY, INCLUDING LIABILITY FOR INFRINGEMENT OF ANY PATENTS, 
21    COPYRIGHTS, TRADEMARKS OR OTHER RIGHTS, RELATING TO USE OF THIS 
22    SOFTWARE IS DISCLAIMED.
23 */
24
25 /* Bluetooth address family and sockets. */
26
27 #include <linux/config.h>
28 #include <linux/module.h>
29
30 #include <linux/types.h>
31 #include <linux/list.h>
32 #include <linux/errno.h>
33 #include <linux/kernel.h>
34 #include <linux/major.h>
35 #include <linux/sched.h>
36 #include <linux/slab.h>
37 #include <linux/skbuff.h>
38 #include <linux/init.h>
39 #include <linux/poll.h>
40 #include <linux/proc_fs.h>
41 #include <net/sock.h>
42
43 #if defined(CONFIG_KMOD)
44 #include <linux/kmod.h>
45 #endif
46
47 #include <net/bluetooth/bluetooth.h>
48
49 #ifndef CONFIG_BT_SOCK_DEBUG
50 #undef  BT_DBG
51 #define BT_DBG(D...)
52 #endif
53
54 #define VERSION "2.7"
55
56 struct proc_dir_entry *proc_bt;
57 EXPORT_SYMBOL(proc_bt);
58
59 /* Bluetooth sockets */
60 #define BT_MAX_PROTO    8
61 static struct net_proto_family *bt_proto[BT_MAX_PROTO];
62
63 int bt_sock_register(int proto, struct net_proto_family *ops)
64 {
65         if (proto < 0 || proto >= BT_MAX_PROTO)
66                 return -EINVAL;
67
68         if (bt_proto[proto])
69                 return -EEXIST;
70
71         bt_proto[proto] = ops;
72         return 0;
73 }
74 EXPORT_SYMBOL(bt_sock_register);
75
76 int bt_sock_unregister(int proto)
77 {
78         if (proto < 0 || proto >= BT_MAX_PROTO)
79                 return -EINVAL;
80
81         if (!bt_proto[proto])
82                 return -ENOENT;
83
84         bt_proto[proto] = NULL;
85         return 0;
86 }
87 EXPORT_SYMBOL(bt_sock_unregister);
88
89 static int bt_sock_create(struct socket *sock, int proto)
90 {
91         int err = 0;
92
93         if (proto < 0 || proto >= BT_MAX_PROTO)
94                 return -EINVAL;
95
96 #if defined(CONFIG_KMOD)
97         if (!bt_proto[proto]) {
98                 request_module("bt-proto-%d", proto);
99         }
100 #endif
101         err = -EPROTONOSUPPORT;
102         if (bt_proto[proto] && try_module_get(bt_proto[proto]->owner)) {
103                 err = bt_proto[proto]->create(sock, proto);
104                 module_put(bt_proto[proto]->owner);
105         }
106         return err; 
107 }
108
109 void bt_sock_link(struct bt_sock_list *l, struct sock *sk)
110 {
111         write_lock_bh(&l->lock);
112         sk_add_node(sk, &l->head);
113         write_unlock_bh(&l->lock);
114 }
115 EXPORT_SYMBOL(bt_sock_link);
116
117 void bt_sock_unlink(struct bt_sock_list *l, struct sock *sk)
118 {
119         write_lock_bh(&l->lock);
120         sk_del_node_init(sk);
121         write_unlock_bh(&l->lock);
122 }
123 EXPORT_SYMBOL(bt_sock_unlink);
124
125 void bt_accept_enqueue(struct sock *parent, struct sock *sk)
126 {
127         BT_DBG("parent %p, sk %p", parent, sk);
128
129         sock_hold(sk);
130         list_add_tail(&bt_sk(sk)->accept_q, &bt_sk(parent)->accept_q);
131         bt_sk(sk)->parent = parent;
132         parent->sk_ack_backlog++;
133 }
134 EXPORT_SYMBOL(bt_accept_enqueue);
135
136 void bt_accept_unlink(struct sock *sk)
137 {
138         BT_DBG("sk %p state %d", sk, sk->sk_state);
139
140         list_del_init(&bt_sk(sk)->accept_q);
141         bt_sk(sk)->parent->sk_ack_backlog--;
142         bt_sk(sk)->parent = NULL;
143         sock_put(sk);
144 }
145 EXPORT_SYMBOL(bt_accept_unlink);
146
147 struct sock *bt_accept_dequeue(struct sock *parent, struct socket *newsock)
148 {
149         struct list_head *p, *n;
150         struct sock *sk;
151
152         BT_DBG("parent %p", parent);
153
154         list_for_each_safe(p, n, &bt_sk(parent)->accept_q) {
155                 sk = (struct sock *) list_entry(p, struct bt_sock, accept_q);
156
157                 lock_sock(sk);
158
159                 /* FIXME: Is this check still needed */
160                 if (sk->sk_state == BT_CLOSED) {
161                         release_sock(sk);
162                         bt_accept_unlink(sk);
163                         continue;
164                 }
165
166                 if (sk->sk_state == BT_CONNECTED || !newsock) {
167                         bt_accept_unlink(sk);
168                         if (newsock)
169                                 sock_graft(sk, newsock);
170                         release_sock(sk);
171                         return sk;
172                 }
173
174                 release_sock(sk);
175         }
176         return NULL;
177 }
178 EXPORT_SYMBOL(bt_accept_dequeue);
179
180 int bt_sock_recvmsg(struct kiocb *iocb, struct socket *sock,
181         struct msghdr *msg, size_t len, int flags)
182 {
183         int noblock = flags & MSG_DONTWAIT;
184         struct sock *sk = sock->sk;
185         struct sk_buff *skb;
186         size_t copied;
187         int err;
188
189         BT_DBG("sock %p sk %p len %d", sock, sk, len);
190
191         if (flags & (MSG_OOB))
192                 return -EOPNOTSUPP;
193
194         if (!(skb = skb_recv_datagram(sk, flags, noblock, &err))) {
195                 if (sk->sk_shutdown & RCV_SHUTDOWN)
196                         return 0;
197                 return err;
198         }
199
200         msg->msg_namelen = 0;
201
202         copied = skb->len;
203         if (len < copied) {
204                 msg->msg_flags |= MSG_TRUNC;
205                 copied = len;
206         }
207
208         skb->h.raw = skb->data;
209         err = skb_copy_datagram_iovec(skb, 0, msg->msg_iov, copied);
210
211         skb_free_datagram(sk, skb);
212
213         return err ? : copied;
214 }
215 EXPORT_SYMBOL(bt_sock_recvmsg);
216
217 static inline unsigned int bt_accept_poll(struct sock *parent)
218 {
219         struct list_head *p, *n;
220         struct sock *sk;
221
222         list_for_each_safe(p, n, &bt_sk(parent)->accept_q) {
223                 sk = (struct sock *) list_entry(p, struct bt_sock, accept_q);
224                 if (sk->sk_state == BT_CONNECTED)
225                         return POLLIN | POLLRDNORM;
226         }
227
228         return 0;
229 }
230
231 unsigned int bt_sock_poll(struct file * file, struct socket *sock, poll_table *wait)
232 {
233         struct sock *sk = sock->sk;
234         unsigned int mask = 0;
235
236         BT_DBG("sock %p, sk %p", sock, sk);
237
238         poll_wait(file, sk->sk_sleep, wait);
239
240         if (sk->sk_state == BT_LISTEN)
241                 return bt_accept_poll(sk);
242
243         if (sk->sk_err || !skb_queue_empty(&sk->sk_error_queue))
244                 mask |= POLLERR;
245
246         if (sk->sk_shutdown == SHUTDOWN_MASK)
247                 mask |= POLLHUP;
248
249         if (!skb_queue_empty(&sk->sk_receive_queue) || 
250                         (sk->sk_shutdown & RCV_SHUTDOWN))
251                 mask |= POLLIN | POLLRDNORM;
252
253         if (sk->sk_state == BT_CLOSED)
254                 mask |= POLLHUP;
255
256         if (sk->sk_state == BT_CONNECT ||
257                         sk->sk_state == BT_CONNECT2 ||
258                         sk->sk_state == BT_CONFIG)
259                 return mask;
260
261         if (sock_writeable(sk))
262                 mask |= POLLOUT | POLLWRNORM | POLLWRBAND;
263         else
264                 set_bit(SOCK_ASYNC_NOSPACE, &sk->sk_socket->flags);
265
266         return mask;
267 }
268 EXPORT_SYMBOL(bt_sock_poll);
269
270 int bt_sock_wait_state(struct sock *sk, int state, unsigned long timeo)
271 {
272         DECLARE_WAITQUEUE(wait, current);
273         int err = 0;
274
275         BT_DBG("sk %p", sk);
276
277         add_wait_queue(sk->sk_sleep, &wait);
278         while (sk->sk_state != state) {
279                 set_current_state(TASK_INTERRUPTIBLE);
280
281                 if (!timeo) {
282                         err = -EAGAIN;
283                         break;
284                 }
285
286                 if (signal_pending(current)) {
287                         err = sock_intr_errno(timeo);
288                         break;
289                 }
290
291                 release_sock(sk);
292                 timeo = schedule_timeout(timeo);
293                 lock_sock(sk);
294
295                 if (sk->sk_err) {
296                         err = sock_error(sk);
297                         break;
298                 }
299         }
300         set_current_state(TASK_RUNNING);
301         remove_wait_queue(sk->sk_sleep, &wait);
302         return err;
303 }
304 EXPORT_SYMBOL(bt_sock_wait_state);
305
306 static struct net_proto_family bt_sock_family_ops = {
307         .owner  = THIS_MODULE,
308         .family = PF_BLUETOOTH,
309         .create = bt_sock_create,
310 };
311
312 extern int hci_sock_init(void);
313 extern int hci_sock_cleanup(void);
314
315 extern int bt_sysfs_init(void);
316 extern int bt_sysfs_cleanup(void);
317
318 static int __init bt_init(void)
319 {
320         BT_INFO("Core ver %s", VERSION);
321
322         proc_bt = proc_mkdir("bluetooth", NULL);
323         if (proc_bt)
324                 proc_bt->owner = THIS_MODULE;
325
326         sock_register(&bt_sock_family_ops);
327
328         BT_INFO("HCI device and connection manager initialized");
329
330         bt_sysfs_init();
331
332         hci_sock_init();
333
334         return 0;
335 }
336
337 static void __exit bt_exit(void)
338 {
339         hci_sock_cleanup();
340
341         bt_sysfs_cleanup();
342
343         sock_unregister(PF_BLUETOOTH);
344
345         remove_proc_entry("bluetooth", NULL);
346 }
347
348 subsys_initcall(bt_init);
349 module_exit(bt_exit);
350
351 MODULE_AUTHOR("Maxim Krasnyansky <maxk@qualcomm.com>, Marcel Holtmann <marcel@holtmann.org>");
352 MODULE_DESCRIPTION("Bluetooth Core ver " VERSION);
353 MODULE_VERSION(VERSION);
354 MODULE_LICENSE("GPL");
355 MODULE_ALIAS_NETPROTO(PF_BLUETOOTH);