xref: /linux/net/bluetooth/bnep/core.c (revision ddd664bbff63e09e7a7f9acae9c43605d4cf185f)
1 /*
2    BNEP implementation for Linux Bluetooth stack (BlueZ).
3    Copyright (C) 2001-2002 Inventel Systemes
4    Written 2001-2002 by
5 	Clément Moreau <clement.moreau@inventel.fr>
6 	David Libault  <david.libault@inventel.fr>
7 
8    Copyright (C) 2002 Maxim Krasnyansky <maxk@qualcomm.com>
9 
10    This program is free software; you can redistribute it and/or modify
11    it under the terms of the GNU General Public License version 2 as
12    published by the Free Software Foundation;
13 
14    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
15    OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY RIGHTS.
17    IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) AND AUTHOR(S) BE LIABLE FOR ANY
18    CLAIM, OR ANY SPECIAL INDIRECT OR CONSEQUENTIAL DAMAGES, OR ANY DAMAGES
19    WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
20    ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
21    OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
22 
23    ALL LIABILITY, INCLUDING LIABILITY FOR INFRINGEMENT OF ANY PATENTS,
24    COPYRIGHTS, TRADEMARKS OR OTHER RIGHTS, RELATING TO USE OF THIS
25    SOFTWARE IS DISCLAIMED.
26 */
27 
28 #include <linux/module.h>
29 #include <linux/kthread.h>
30 #include <linux/file.h>
31 #include <linux/etherdevice.h>
32 #include <linux/unaligned.h>
33 
34 #include <net/bluetooth/bluetooth.h>
35 #include <net/bluetooth/l2cap.h>
36 #include <net/bluetooth/hci_core.h>
37 
38 #include "bnep.h"
39 
40 #define VERSION "1.3"
41 
42 static bool compress_src = true;
43 static bool compress_dst = true;
44 
45 static LIST_HEAD(bnep_session_list);
46 static DECLARE_RWSEM(bnep_session_sem);
47 
__bnep_get_session(u8 * dst)48 static struct bnep_session *__bnep_get_session(u8 *dst)
49 {
50 	struct bnep_session *s;
51 
52 	BT_DBG("");
53 
54 	list_for_each_entry(s, &bnep_session_list, list)
55 		if (ether_addr_equal(dst, s->eh.h_source))
56 			return s;
57 
58 	return NULL;
59 }
60 
__bnep_link_session(struct bnep_session * s)61 static void __bnep_link_session(struct bnep_session *s)
62 {
63 	list_add(&s->list, &bnep_session_list);
64 }
65 
__bnep_unlink_session(struct bnep_session * s)66 static void __bnep_unlink_session(struct bnep_session *s)
67 {
68 	list_del(&s->list);
69 }
70 
bnep_send(struct bnep_session * s,void * data,size_t len)71 static int bnep_send(struct bnep_session *s, void *data, size_t len)
72 {
73 	struct socket *sock = s->sock;
74 	struct kvec iv = { data, len };
75 
76 	return kernel_sendmsg(sock, &s->msg, &iv, 1, len);
77 }
78 
bnep_send_rsp(struct bnep_session * s,u8 ctrl,u16 resp)79 static int bnep_send_rsp(struct bnep_session *s, u8 ctrl, u16 resp)
80 {
81 	struct bnep_control_rsp rsp;
82 	rsp.type = BNEP_CONTROL;
83 	rsp.ctrl = ctrl;
84 	rsp.resp = htons(resp);
85 	return bnep_send(s, &rsp, sizeof(rsp));
86 }
87 
88 #ifdef CONFIG_BT_BNEP_PROTO_FILTER
bnep_set_default_proto_filter(struct bnep_session * s)89 static inline void bnep_set_default_proto_filter(struct bnep_session *s)
90 {
91 	/* (IPv4, ARP)  */
92 	s->proto_filter[0].start = ETH_P_IP;
93 	s->proto_filter[0].end   = ETH_P_ARP;
94 	/* (RARP, AppleTalk) */
95 	s->proto_filter[1].start = ETH_P_RARP;
96 	s->proto_filter[1].end   = ETH_P_AARP;
97 	/* (IPX, IPv6) */
98 	s->proto_filter[2].start = ETH_P_IPX;
99 	s->proto_filter[2].end   = ETH_P_IPV6;
100 }
101 #endif
102 
bnep_ctrl_set_netfilter(struct bnep_session * s,__be16 * data,int len)103 static int bnep_ctrl_set_netfilter(struct bnep_session *s, __be16 *data, int len)
104 {
105 	int n;
106 
107 	if (len < 2)
108 		return -EILSEQ;
109 
110 	n = get_unaligned_be16(data);
111 	data++;
112 	len -= 2;
113 
114 	if (len < n)
115 		return -EILSEQ;
116 
117 	BT_DBG("filter len %d", n);
118 
119 #ifdef CONFIG_BT_BNEP_PROTO_FILTER
120 	n /= 4;
121 	if (n <= BNEP_MAX_PROTO_FILTERS) {
122 		struct bnep_proto_filter *f = s->proto_filter;
123 		int i;
124 
125 		for (i = 0; i < n; i++) {
126 			f[i].start = get_unaligned_be16(data++);
127 			f[i].end   = get_unaligned_be16(data++);
128 
129 			BT_DBG("proto filter start %u end %u",
130 			       f[i].start, f[i].end);
131 		}
132 
133 		if (i < BNEP_MAX_PROTO_FILTERS)
134 			memset(f + i, 0, sizeof(*f));
135 
136 		if (n == 0)
137 			bnep_set_default_proto_filter(s);
138 
139 		bnep_send_rsp(s, BNEP_FILTER_NET_TYPE_RSP, BNEP_SUCCESS);
140 	} else {
141 		bnep_send_rsp(s, BNEP_FILTER_NET_TYPE_RSP, BNEP_FILTER_LIMIT_REACHED);
142 	}
143 #else
144 	bnep_send_rsp(s, BNEP_FILTER_NET_TYPE_RSP, BNEP_FILTER_UNSUPPORTED_REQ);
145 #endif
146 	return 0;
147 }
148 
bnep_ctrl_set_mcfilter(struct bnep_session * s,u8 * data,int len)149 static int bnep_ctrl_set_mcfilter(struct bnep_session *s, u8 *data, int len)
150 {
151 	int n;
152 
153 	if (len < 2)
154 		return -EILSEQ;
155 
156 	n = get_unaligned_be16(data);
157 	data += 2;
158 	len -= 2;
159 
160 	if (len < n)
161 		return -EILSEQ;
162 
163 	BT_DBG("filter len %d", n);
164 
165 #ifdef CONFIG_BT_BNEP_MC_FILTER
166 	n /= (ETH_ALEN * 2);
167 
168 	if (n > 0) {
169 		int i;
170 
171 		s->mc_filter = 0;
172 
173 		/* Always send broadcast */
174 		set_bit(bnep_mc_hash(s->dev->broadcast), (ulong *) &s->mc_filter);
175 
176 		/* Add address ranges to the multicast hash */
177 		for (; n > 0; n--) {
178 			u8 a1[6], *a2;
179 
180 			memcpy(a1, data, ETH_ALEN);
181 			data += ETH_ALEN;
182 			a2 = data;
183 			data += ETH_ALEN;
184 
185 			BT_DBG("mc filter %pMR -> %pMR", a1, a2);
186 
187 			/* Iterate from a1 to a2 */
188 			set_bit(bnep_mc_hash(a1), (ulong *) &s->mc_filter);
189 			while (memcmp(a1, a2, 6) < 0 && s->mc_filter != ~0LL) {
190 				/* Increment a1 */
191 				i = 5;
192 				while (i >= 0 && ++a1[i--] == 0)
193 					;
194 
195 				set_bit(bnep_mc_hash(a1), (ulong *) &s->mc_filter);
196 			}
197 		}
198 	}
199 
200 	BT_DBG("mc filter hash 0x%llx", s->mc_filter);
201 
202 	bnep_send_rsp(s, BNEP_FILTER_MULTI_ADDR_RSP, BNEP_SUCCESS);
203 #else
204 	bnep_send_rsp(s, BNEP_FILTER_MULTI_ADDR_RSP, BNEP_FILTER_UNSUPPORTED_REQ);
205 #endif
206 	return 0;
207 }
208 
bnep_rx_control_cmd(struct bnep_session * s,u8 cmd,void * data,int len)209 static int bnep_rx_control_cmd(struct bnep_session *s, u8 cmd, void *data,
210 			       int len)
211 {
212 	int err = 0;
213 
214 	switch (cmd) {
215 	case BNEP_CMD_NOT_UNDERSTOOD:
216 	case BNEP_SETUP_CONN_RSP:
217 	case BNEP_FILTER_NET_TYPE_RSP:
218 	case BNEP_FILTER_MULTI_ADDR_RSP:
219 		/* Ignore these for now */
220 		break;
221 
222 	case BNEP_FILTER_NET_TYPE_SET:
223 		err = bnep_ctrl_set_netfilter(s, data, len);
224 		break;
225 
226 	case BNEP_FILTER_MULTI_ADDR_SET:
227 		err = bnep_ctrl_set_mcfilter(s, data, len);
228 		break;
229 
230 	case BNEP_SETUP_CONN_REQ:
231 		/* Successful response should be sent only once */
232 		if (test_bit(BNEP_SETUP_RESPONSE, &s->flags) &&
233 		    !test_and_set_bit(BNEP_SETUP_RSP_SENT, &s->flags))
234 			err = bnep_send_rsp(s, BNEP_SETUP_CONN_RSP,
235 					    BNEP_SUCCESS);
236 		else
237 			err = bnep_send_rsp(s, BNEP_SETUP_CONN_RSP,
238 					    BNEP_CONN_NOT_ALLOWED);
239 		break;
240 
241 	default: {
242 			u8 pkt[3];
243 			pkt[0] = BNEP_CONTROL;
244 			pkt[1] = BNEP_CMD_NOT_UNDERSTOOD;
245 			pkt[2] = cmd;
246 			err = bnep_send(s, pkt, sizeof(pkt));
247 		}
248 		break;
249 	}
250 
251 	return err;
252 }
253 
bnep_rx_control(struct bnep_session * s,void * data,int len)254 static int bnep_rx_control(struct bnep_session *s, void *data, int len)
255 {
256 	if (len < 1)
257 		return -EILSEQ;
258 
259 	return bnep_rx_control_cmd(s, *(u8 *)data, data + 1, len - 1);
260 }
261 
bnep_rx_extension(struct bnep_session * s,struct sk_buff * skb)262 static int bnep_rx_extension(struct bnep_session *s, struct sk_buff *skb)
263 {
264 	struct bnep_ext_hdr *h;
265 	int err = 0;
266 
267 	do {
268 		h = (void *) skb->data;
269 		if (!skb_pull(skb, sizeof(*h))) {
270 			err = -EILSEQ;
271 			break;
272 		}
273 
274 		BT_DBG("type 0x%x len %u", h->type, h->len);
275 
276 		switch (h->type & BNEP_TYPE_MASK) {
277 		case BNEP_EXT_CONTROL:
278 			bnep_rx_control(s, skb->data, skb->len);
279 			break;
280 
281 		default:
282 			/* Unknown extension, skip it. */
283 			break;
284 		}
285 
286 		if (!skb_pull(skb, h->len)) {
287 			err = -EILSEQ;
288 			break;
289 		}
290 	} while (!err && (h->type & BNEP_EXT_HEADER));
291 
292 	return err;
293 }
294 
295 static u8 __bnep_rx_hlen[] = {
296 	ETH_HLEN,     /* BNEP_GENERAL */
297 	0,            /* BNEP_CONTROL */
298 	2,            /* BNEP_COMPRESSED */
299 	ETH_ALEN + 2, /* BNEP_COMPRESSED_SRC_ONLY */
300 	ETH_ALEN + 2  /* BNEP_COMPRESSED_DST_ONLY */
301 };
302 
bnep_rx_frame(struct bnep_session * s,struct sk_buff * skb)303 static int bnep_rx_frame(struct bnep_session *s, struct sk_buff *skb)
304 {
305 	struct net_device *dev = s->dev;
306 	struct sk_buff *nskb;
307 	u8 *data;
308 	u8 type, ctrl_type;
309 
310 	dev->stats.rx_bytes += skb->len;
311 
312 	data = skb_pull_data(skb, sizeof(type));
313 	if (!data)
314 		goto badframe;
315 	type = *data;
316 
317 	if ((type & BNEP_TYPE_MASK) >= sizeof(__bnep_rx_hlen))
318 		goto badframe;
319 
320 	if ((type & BNEP_TYPE_MASK) == BNEP_CONTROL) {
321 		data = skb_pull_data(skb, sizeof(ctrl_type));
322 		if (!data)
323 			goto badframe;
324 		ctrl_type = *data;
325 
326 		if (bnep_rx_control_cmd(s, ctrl_type, skb->data, skb->len) < 0) {
327 			dev->stats.tx_errors++;
328 			kfree_skb(skb);
329 			return 0;
330 		}
331 
332 		if (!(type & BNEP_EXT_HEADER)) {
333 			kfree_skb(skb);
334 			return 0;
335 		}
336 
337 		/* Verify and pull ctrl message since it's already processed */
338 		switch (ctrl_type) {
339 		case BNEP_SETUP_CONN_REQ: {
340 			u8 uuid_size;
341 
342 			/* Pull uuid_size and the dst/src service UUIDs. */
343 			data = skb_pull_data(skb, sizeof(uuid_size));
344 			if (!data)
345 				goto badframe;
346 			uuid_size = *data;
347 			if (!skb_pull(skb, uuid_size + uuid_size))
348 				goto badframe;
349 			break;
350 		}
351 		case BNEP_FILTER_MULTI_ADDR_SET:
352 		case BNEP_FILTER_NET_TYPE_SET:
353 			/* Pull: len (2 b), data (len bytes) */
354 			data = skb_pull_data(skb, sizeof(u16));
355 			if (!data)
356 				goto badframe;
357 			if (!skb_pull(skb, get_unaligned_be16(data)))
358 				goto badframe;
359 			break;
360 		default:
361 			kfree_skb(skb);
362 			return 0;
363 		}
364 	} else {
365 		skb_reset_mac_header(skb);
366 
367 		/* Verify and pull out header */
368 		if (!skb_pull(skb, __bnep_rx_hlen[type & BNEP_TYPE_MASK]))
369 			goto badframe;
370 
371 		s->eh.h_proto = get_unaligned((__be16 *) (skb->data - 2));
372 	}
373 
374 	if (type & BNEP_EXT_HEADER) {
375 		if (bnep_rx_extension(s, skb) < 0)
376 			goto badframe;
377 	}
378 
379 	/* Strip 802.1p header */
380 	if (ntohs(s->eh.h_proto) == ETH_P_8021Q) {
381 		if (!skb_pull(skb, 4))
382 			goto badframe;
383 		s->eh.h_proto = get_unaligned((__be16 *) (skb->data - 2));
384 	}
385 
386 	/* We have to alloc new skb and copy data here :(. Because original skb
387 	 * may not be modified and because of the alignment requirements. */
388 	nskb = alloc_skb(2 + ETH_HLEN + skb->len, GFP_KERNEL);
389 	if (!nskb) {
390 		dev->stats.rx_dropped++;
391 		kfree_skb(skb);
392 		return -ENOMEM;
393 	}
394 	skb_reserve(nskb, 2);
395 
396 	/* Decompress header and construct ether frame */
397 	switch (type & BNEP_TYPE_MASK) {
398 	case BNEP_COMPRESSED:
399 		__skb_put_data(nskb, &s->eh, ETH_HLEN);
400 		break;
401 
402 	case BNEP_COMPRESSED_SRC_ONLY:
403 		__skb_put_data(nskb, s->eh.h_dest, ETH_ALEN);
404 		__skb_put_data(nskb, skb_mac_header(skb), ETH_ALEN);
405 		put_unaligned(s->eh.h_proto, (__be16 *) __skb_put(nskb, 2));
406 		break;
407 
408 	case BNEP_COMPRESSED_DST_ONLY:
409 		__skb_put_data(nskb, skb_mac_header(skb), ETH_ALEN);
410 		__skb_put_data(nskb, s->eh.h_source, ETH_ALEN);
411 		put_unaligned(s->eh.h_proto, (__be16 *)__skb_put(nskb, 2));
412 		break;
413 
414 	case BNEP_GENERAL:
415 		__skb_put_data(nskb, skb_mac_header(skb), ETH_ALEN * 2);
416 		put_unaligned(s->eh.h_proto, (__be16 *) __skb_put(nskb, 2));
417 		break;
418 	}
419 
420 	skb_copy_from_linear_data(skb, __skb_put(nskb, skb->len), skb->len);
421 	kfree_skb(skb);
422 
423 	dev->stats.rx_packets++;
424 	nskb->ip_summed = CHECKSUM_NONE;
425 	nskb->protocol  = eth_type_trans(nskb, dev);
426 	netif_rx(nskb);
427 	return 0;
428 
429 badframe:
430 	dev->stats.rx_errors++;
431 	kfree_skb(skb);
432 	return 0;
433 }
434 
435 static u8 __bnep_tx_types[] = {
436 	BNEP_GENERAL,
437 	BNEP_COMPRESSED_SRC_ONLY,
438 	BNEP_COMPRESSED_DST_ONLY,
439 	BNEP_COMPRESSED
440 };
441 
bnep_tx_frame(struct bnep_session * s,struct sk_buff * skb)442 static int bnep_tx_frame(struct bnep_session *s, struct sk_buff *skb)
443 {
444 	struct ethhdr *eh = (void *) skb->data;
445 	struct socket *sock = s->sock;
446 	struct kvec iv[3];
447 	int len = 0, il = 0;
448 	u8 type = 0;
449 
450 	BT_DBG("skb %p dev %p type %u", skb, skb->dev, skb->pkt_type);
451 
452 	if (!skb->dev) {
453 		/* Control frame sent by us */
454 		goto send;
455 	}
456 
457 	iv[il++] = (struct kvec) { &type, 1 };
458 	len++;
459 
460 	if (compress_src && ether_addr_equal(eh->h_dest, s->eh.h_source))
461 		type |= 0x01;
462 
463 	if (compress_dst && ether_addr_equal(eh->h_source, s->eh.h_dest))
464 		type |= 0x02;
465 
466 	if (type)
467 		skb_pull(skb, ETH_ALEN * 2);
468 
469 	type = __bnep_tx_types[type];
470 	switch (type) {
471 	case BNEP_COMPRESSED_SRC_ONLY:
472 		iv[il++] = (struct kvec) { eh->h_source, ETH_ALEN };
473 		len += ETH_ALEN;
474 		break;
475 
476 	case BNEP_COMPRESSED_DST_ONLY:
477 		iv[il++] = (struct kvec) { eh->h_dest, ETH_ALEN };
478 		len += ETH_ALEN;
479 		break;
480 	}
481 
482 send:
483 	iv[il++] = (struct kvec) { skb->data, skb->len };
484 	len += skb->len;
485 
486 	/* FIXME: linearize skb */
487 	{
488 		len = kernel_sendmsg(sock, &s->msg, iv, il, len);
489 	}
490 	kfree_skb(skb);
491 
492 	if (len > 0) {
493 		s->dev->stats.tx_bytes += len;
494 		s->dev->stats.tx_packets++;
495 		return 0;
496 	}
497 
498 	return len;
499 }
500 
bnep_session(void * arg)501 static int bnep_session(void *arg)
502 {
503 	struct bnep_session *s = arg;
504 	struct net_device *dev = s->dev;
505 	struct sock *sk = s->sock->sk;
506 	struct sk_buff *skb;
507 	DEFINE_WAIT_FUNC(wait, woken_wake_function);
508 
509 	BT_DBG("");
510 
511 	set_user_nice(current, -15);
512 
513 	add_wait_queue(sk_sleep(sk), &wait);
514 	while (1) {
515 		if (atomic_read(&s->terminate))
516 			break;
517 		/* RX */
518 		while ((skb = skb_dequeue(&sk->sk_receive_queue))) {
519 			skb_orphan(skb);
520 			if (!skb_linearize(skb))
521 				bnep_rx_frame(s, skb);
522 			else
523 				kfree_skb(skb);
524 		}
525 
526 		if (sk->sk_state != BT_CONNECTED)
527 			break;
528 
529 		/* TX */
530 		while ((skb = skb_dequeue(&sk->sk_write_queue)))
531 			if (bnep_tx_frame(s, skb))
532 				break;
533 		netif_wake_queue(dev);
534 
535 		/*
536 		 * wait_woken() performs the necessary memory barriers
537 		 * for us; see the header comment for this primitive.
538 		 */
539 		wait_woken(&wait, TASK_INTERRUPTIBLE, MAX_SCHEDULE_TIMEOUT);
540 	}
541 	remove_wait_queue(sk_sleep(sk), &wait);
542 
543 	/* Cleanup session */
544 	down_write(&bnep_session_sem);
545 
546 	/* Delete network device */
547 	unregister_netdev(dev);
548 
549 	/* Wakeup user-space polling for socket errors */
550 	s->sock->sk->sk_err = EUNATCH;
551 
552 	wake_up_interruptible(sk_sleep(s->sock->sk));
553 
554 	/* Release the socket */
555 	fput(s->sock->file);
556 
557 	__bnep_unlink_session(s);
558 
559 	up_write(&bnep_session_sem);
560 	free_netdev(dev);
561 	module_put_and_kthread_exit(0);
562 	return 0;
563 }
564 
bnep_get_device(struct bnep_session * session)565 static struct device *bnep_get_device(struct bnep_session *session)
566 {
567 	struct l2cap_conn *conn = l2cap_pi(session->sock->sk)->chan->conn;
568 
569 	if (!conn || !conn->hcon)
570 		return NULL;
571 
572 	return &conn->hcon->dev;
573 }
574 
575 static const struct device_type bnep_type = {
576 	.name	= "bluetooth",
577 };
578 
bnep_add_connection(struct bnep_connadd_req * req,struct socket * sock)579 int bnep_add_connection(struct bnep_connadd_req *req, struct socket *sock)
580 {
581 	u32 valid_flags = BIT(BNEP_SETUP_RESPONSE);
582 	struct net_device *dev;
583 	struct bnep_session *s, *ss;
584 	u8 dst[ETH_ALEN], src[ETH_ALEN];
585 	int err;
586 
587 	BT_DBG("");
588 
589 	if (!l2cap_is_socket(sock))
590 		return -EBADFD;
591 
592 	if (req->flags & ~valid_flags)
593 		return -EINVAL;
594 
595 	baswap((void *) dst, &l2cap_pi(sock->sk)->chan->dst);
596 	baswap((void *) src, &l2cap_pi(sock->sk)->chan->src);
597 
598 	/* session struct allocated as private part of net_device */
599 	dev = alloc_netdev(sizeof(struct bnep_session),
600 			   (*req->device) ? req->device : "bnep%d",
601 			   NET_NAME_UNKNOWN,
602 			   bnep_net_setup);
603 	if (!dev)
604 		return -ENOMEM;
605 
606 	down_write(&bnep_session_sem);
607 
608 	ss = __bnep_get_session(dst);
609 	if (ss && ss->state == BT_CONNECTED) {
610 		err = -EEXIST;
611 		goto failed;
612 	}
613 
614 	s = netdev_priv(dev);
615 
616 	/* This is rx header therefore addresses are swapped.
617 	 * ie. eh.h_dest is our local address. */
618 	memcpy(s->eh.h_dest,   &src, ETH_ALEN);
619 	memcpy(s->eh.h_source, &dst, ETH_ALEN);
620 	eth_hw_addr_set(dev, s->eh.h_dest);
621 
622 	s->dev   = dev;
623 	s->sock  = sock;
624 	s->role  = req->role;
625 	s->state = BT_CONNECTED;
626 	s->flags = req->flags;
627 
628 	s->msg.msg_flags = MSG_NOSIGNAL;
629 
630 #ifdef CONFIG_BT_BNEP_MC_FILTER
631 	/* Set default mc filter to not filter out any mc addresses
632 	 * as defined in the BNEP specification (revision 0.95a)
633 	 * http://grouper.ieee.org/groups/802/15/Bluetooth/BNEP.pdf
634 	 */
635 	s->mc_filter = ~0LL;
636 #endif
637 
638 #ifdef CONFIG_BT_BNEP_PROTO_FILTER
639 	/* Set default protocol filter */
640 	bnep_set_default_proto_filter(s);
641 #endif
642 
643 	SET_NETDEV_DEV(dev, bnep_get_device(s));
644 	SET_NETDEV_DEVTYPE(dev, &bnep_type);
645 
646 	err = register_netdev(dev);
647 	if (err)
648 		goto failed;
649 
650 	__bnep_link_session(s);
651 
652 	__module_get(THIS_MODULE);
653 	s->task = kthread_run(bnep_session, s, "kbnepd %s", dev->name);
654 	if (IS_ERR(s->task)) {
655 		/* Session thread start failed, gotta cleanup. */
656 		module_put(THIS_MODULE);
657 		unregister_netdev(dev);
658 		__bnep_unlink_session(s);
659 		err = PTR_ERR(s->task);
660 		goto failed;
661 	}
662 
663 	strcpy(req->device, dev->name);
664 	up_write(&bnep_session_sem);
665 	return 0;
666 
667 failed:
668 	up_write(&bnep_session_sem);
669 	free_netdev(dev);
670 	return err;
671 }
672 
bnep_del_connection(struct bnep_conndel_req * req)673 int bnep_del_connection(struct bnep_conndel_req *req)
674 {
675 	u32 valid_flags = 0;
676 	struct bnep_session *s;
677 	int  err = 0;
678 
679 	BT_DBG("");
680 
681 	if (req->flags & ~valid_flags)
682 		return -EINVAL;
683 
684 	down_read(&bnep_session_sem);
685 
686 	s = __bnep_get_session(req->dst);
687 	if (s) {
688 		atomic_inc(&s->terminate);
689 		wake_up_interruptible(sk_sleep(s->sock->sk));
690 	} else
691 		err = -ENOENT;
692 
693 	up_read(&bnep_session_sem);
694 	return err;
695 }
696 
__bnep_copy_ci(struct bnep_conninfo * ci,struct bnep_session * s)697 static void __bnep_copy_ci(struct bnep_conninfo *ci, struct bnep_session *s)
698 {
699 	u32 valid_flags = BIT(BNEP_SETUP_RESPONSE);
700 
701 	memset(ci, 0, sizeof(*ci));
702 	memcpy(ci->dst, s->eh.h_source, ETH_ALEN);
703 	strcpy(ci->device, s->dev->name);
704 	ci->flags = s->flags & valid_flags;
705 	ci->state = s->state;
706 	ci->role  = s->role;
707 }
708 
bnep_get_connlist(struct bnep_connlist_req * req)709 int bnep_get_connlist(struct bnep_connlist_req *req)
710 {
711 	struct bnep_session *s;
712 	int err = 0, n = 0;
713 
714 	down_read(&bnep_session_sem);
715 
716 	list_for_each_entry(s, &bnep_session_list, list) {
717 		struct bnep_conninfo ci;
718 
719 		__bnep_copy_ci(&ci, s);
720 
721 		if (copy_to_user(req->ci, &ci, sizeof(ci))) {
722 			err = -EFAULT;
723 			break;
724 		}
725 
726 		if (++n >= req->cnum)
727 			break;
728 
729 		req->ci++;
730 	}
731 	req->cnum = n;
732 
733 	up_read(&bnep_session_sem);
734 	return err;
735 }
736 
bnep_get_conninfo(struct bnep_conninfo * ci)737 int bnep_get_conninfo(struct bnep_conninfo *ci)
738 {
739 	struct bnep_session *s;
740 	int err = 0;
741 
742 	down_read(&bnep_session_sem);
743 
744 	s = __bnep_get_session(ci->dst);
745 	if (s)
746 		__bnep_copy_ci(ci, s);
747 	else
748 		err = -ENOENT;
749 
750 	up_read(&bnep_session_sem);
751 	return err;
752 }
753 
bnep_init(void)754 static int __init bnep_init(void)
755 {
756 	char flt[50] = "";
757 
758 #ifdef CONFIG_BT_BNEP_PROTO_FILTER
759 	strcat(flt, "protocol ");
760 #endif
761 
762 #ifdef CONFIG_BT_BNEP_MC_FILTER
763 	strcat(flt, "multicast");
764 #endif
765 
766 	BT_INFO("BNEP (Ethernet Emulation) ver %s", VERSION);
767 	if (flt[0])
768 		BT_INFO("BNEP filters: %s", flt);
769 
770 	return bnep_sock_init();
771 }
772 
bnep_exit(void)773 static void __exit bnep_exit(void)
774 {
775 	bnep_sock_cleanup();
776 }
777 
778 module_init(bnep_init);
779 module_exit(bnep_exit);
780 
781 module_param(compress_src, bool, 0644);
782 MODULE_PARM_DESC(compress_src, "Compress sources headers");
783 
784 module_param(compress_dst, bool, 0644);
785 MODULE_PARM_DESC(compress_dst, "Compress destination headers");
786 
787 MODULE_AUTHOR("Marcel Holtmann <marcel@holtmann.org>");
788 MODULE_DESCRIPTION("Bluetooth BNEP ver " VERSION);
789 MODULE_VERSION(VERSION);
790 MODULE_LICENSE("GPL");
791 MODULE_ALIAS("bt-proto-4");
792