ftp://ftp.kernel.org/pub/linux/kernel/v2.6/linux-2.6.6.tar.bz2
[linux-2.6.git] / net / atm / raw.c
1 /* net/atm/raw.c - Raw AAL0 and AAL5 transports */
2
3 /* Written 1995-2000 by Werner Almesberger, EPFL LRC/ICA */
4
5
6 #include <linux/module.h>
7 #include <linux/sched.h>
8 #include <linux/atmdev.h>
9 #include <linux/kernel.h>
10 #include <linux/skbuff.h>
11 #include <linux/mm.h>
12
13 #include "common.h"
14 #include "protocols.h"
15
16
17 #if 0
18 #define DPRINTK(format,args...) printk(KERN_DEBUG format,##args)
19 #else
20 #define DPRINTK(format,args...)
21 #endif
22
23
24 /*
25  * SKB == NULL indicates that the link is being closed
26  */
27
28 void atm_push_raw(struct atm_vcc *vcc,struct sk_buff *skb)
29 {
30         if (skb) {
31                 skb_queue_tail(&vcc->sk->sk_receive_queue, skb);
32                 vcc->sk->sk_data_ready(vcc->sk, skb->len);
33         }
34 }
35
36
37 static void atm_pop_raw(struct atm_vcc *vcc,struct sk_buff *skb)
38 {
39         DPRINTK("APopR (%d) %d -= %d\n", vcc->vci, vcc->sk->sk_wmem_alloc,
40                 skb->truesize);
41         atomic_sub(skb->truesize, &vcc->sk->sk_wmem_alloc);
42         dev_kfree_skb_any(skb);
43         vcc->sk->sk_write_space(vcc->sk);
44 }
45
46
47 static int atm_send_aal0(struct atm_vcc *vcc,struct sk_buff *skb)
48 {
49         /*
50          * Note that if vpi/vci are _ANY or _UNSPEC the below will
51          * still work
52          */
53         if (!capable(CAP_NET_ADMIN) &&
54             (((u32 *) skb->data)[0] & (ATM_HDR_VPI_MASK | ATM_HDR_VCI_MASK)) !=
55             ((vcc->vpi << ATM_HDR_VPI_SHIFT) | (vcc->vci << ATM_HDR_VCI_SHIFT)))
56             {
57                 kfree_skb(skb);
58                 return -EADDRNOTAVAIL;
59         }
60         return vcc->dev->ops->send(vcc,skb);
61 }
62
63
64 int atm_init_aal0(struct atm_vcc *vcc)
65 {
66         vcc->push = atm_push_raw;
67         vcc->pop = atm_pop_raw;
68         vcc->push_oam = NULL;
69         vcc->send = atm_send_aal0;
70         return 0;
71 }
72
73
74 int atm_init_aal34(struct atm_vcc *vcc)
75 {
76         vcc->push = atm_push_raw;
77         vcc->pop = atm_pop_raw;
78         vcc->push_oam = NULL;
79         vcc->send = vcc->dev->ops->send;
80         return 0;
81 }
82
83
84 int atm_init_aal5(struct atm_vcc *vcc)
85 {
86         vcc->push = atm_push_raw;
87         vcc->pop = atm_pop_raw;
88         vcc->push_oam = NULL;
89         vcc->send = vcc->dev->ops->send;
90         return 0;
91 }
92
93
94 EXPORT_SYMBOL(atm_init_aal5);