This source file includes following definitions.
- wait_for_packet
- skb_recv_datagram
- skb_free_datagram
- skb_copy_datagram
- skb_copy_datagram_iovec
- datagram_select
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24 #include <linux/types.h>
25 #include <linux/kernel.h>
26 #include <asm/segment.h>
27 #include <asm/system.h>
28 #include <linux/mm.h>
29 #include <linux/interrupt.h>
30 #include <linux/in.h>
31 #include <linux/errno.h>
32 #include <linux/sched.h>
33 #include <linux/inet.h>
34 #include <linux/netdevice.h>
35 #include <net/ip.h>
36 #include <net/protocol.h>
37 #include <net/route.h>
38 #include <net/tcp.h>
39 #include <net/udp.h>
40 #include <linux/skbuff.h>
41 #include <net/sock.h>
42
43
44
45
46
47
48
49
50 static inline void wait_for_packet(struct sock * sk)
51 {
52 unsigned long flags;
53
54 release_sock(sk);
55 save_flags(flags);
56 cli();
57 if (skb_peek(&sk->receive_queue) == NULL)
58 interruptible_sleep_on(sk->sleep);
59 restore_flags(flags);
60 lock_sock(sk);
61 }
62
63
64
65
66
67
68
69
70
71
72
73
74
75 struct sk_buff *skb_recv_datagram(struct sock *sk, unsigned flags, int noblock, int *err)
76 {
77 int error;
78 struct sk_buff *skb;
79
80 lock_sock(sk);
81 restart:
82 while(skb_peek(&sk->receive_queue) == NULL)
83 {
84
85 error = sock_error(sk);
86 if (error)
87 goto no_packet;
88
89
90 if (sk->shutdown & RCV_SHUTDOWN)
91 goto no_packet;
92
93
94 error = -ENOTCONN;
95 if(sk->type==SOCK_SEQPACKET && sk->state!=TCP_ESTABLISHED)
96 goto no_packet;
97
98
99 error = -EAGAIN;
100 if (noblock)
101 goto no_packet;
102
103
104 error = -ERESTARTSYS;
105 if (current->signal & ~current->blocked)
106 goto no_packet;
107
108 wait_for_packet(sk);
109 }
110
111
112
113 if (flags & MSG_PEEK)
114 {
115 unsigned long flags;
116 save_flags(flags);
117 cli();
118 skb=skb_peek(&sk->receive_queue);
119 if(skb!=NULL)
120 skb->users++;
121 restore_flags(flags);
122 if(skb==NULL)
123 goto restart;
124 return skb;
125 }
126 skb = skb_dequeue(&sk->receive_queue);
127 if (!skb)
128 goto restart;
129 skb->users++;
130 return skb;
131
132 no_packet:
133 release_sock(sk);
134 *err = error;
135 return NULL;
136 }
137
138 void skb_free_datagram(struct sock * sk, struct sk_buff *skb)
139 {
140 unsigned long flags;
141
142 save_flags(flags);
143 cli();
144 skb->users--;
145 if(skb->users>0)
146 {
147 restore_flags(flags);
148 return;
149 }
150
151 if(!skb->next && !skb->prev)
152 kfree_skb(skb,FREE_READ);
153 restore_flags(flags);
154 release_sock(sk);
155 }
156
157
158
159
160
161 void skb_copy_datagram(struct sk_buff *skb, int offset, char *to, int size)
162 {
163 memcpy_tofs(to,skb->h.raw+offset,size);
164 }
165
166
167
168
169
170
171 void skb_copy_datagram_iovec(struct sk_buff *skb, int offset, struct iovec *to, int size)
172 {
173 memcpy_toiovec(to,skb->h.raw+offset,size);
174 }
175
176
177
178
179
180
181 int datagram_select(struct sock *sk, int sel_type, select_table *wait)
182 {
183 select_wait(sk->sleep, wait);
184 switch(sel_type)
185 {
186 case SEL_IN:
187 if (sk->err)
188 return 1;
189 if (sk->shutdown & RCV_SHUTDOWN)
190 return 1;
191 if (sk->type==SOCK_SEQPACKET && sk->state==TCP_CLOSE)
192 {
193
194 return(1);
195 }
196 if (skb_peek(&sk->receive_queue) != NULL)
197 {
198
199 return(1);
200 }
201 return(0);
202
203 case SEL_OUT:
204 if (sk->err)
205 return 1;
206 if (sk->shutdown & SEND_SHUTDOWN)
207 return 1;
208 if (sk->type==SOCK_SEQPACKET && sk->state==TCP_SYN_SENT)
209 {
210
211 break;
212 }
213 if (sk->prot && sock_wspace(sk) >= MIN_WRITE_SPACE)
214 {
215 return(1);
216 }
217 if (sk->prot==NULL && sk->sndbuf-sk->wmem_alloc >= MIN_WRITE_SPACE)
218 {
219 return(1);
220 }
221 return(0);
222
223 case SEL_EX:
224 if (sk->err)
225 return(1);
226 return(0);
227 }
228 return(0);
229 }