This source file includes following definitions.
- nr_clear_queues
- nr_frames_acked
- nr_requeue_frames
- nr_validate_nr
- nr_in_rx_window
- nr_write_internal
- nr_transmit_dm
- nr_calculate_t1
- nr_calculate_rtt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 #include <linux/config.h>
21 #ifdef CONFIG_NETROM
22 #include <linux/errno.h>
23 #include <linux/types.h>
24 #include <linux/socket.h>
25 #include <linux/in.h>
26 #include <linux/kernel.h>
27 #include <linux/sched.h>
28 #include <linux/timer.h>
29 #include <linux/string.h>
30 #include <linux/sockios.h>
31 #include <linux/net.h>
32 #include <net/ax25.h>
33 #include <linux/inet.h>
34 #include <linux/netdevice.h>
35 #include <linux/skbuff.h>
36 #include <net/sock.h>
37 #include <asm/segment.h>
38 #include <asm/system.h>
39 #include <linux/fcntl.h>
40 #include <linux/mm.h>
41 #include <linux/interrupt.h>
42 #include <net/netrom.h>
43
44
45
46
47 void nr_clear_queues(struct sock *sk)
48 {
49 struct sk_buff *skb;
50
51 while ((skb = skb_dequeue(&sk->write_queue)) != NULL) {
52 skb->sk = sk;
53 skb->free = 1;
54 kfree_skb(skb, FREE_WRITE);
55 }
56
57 while ((skb = skb_dequeue(&sk->nr->ack_queue)) != NULL) {
58 skb->sk = sk;
59 skb->free = 1;
60 kfree_skb(skb, FREE_WRITE);
61 }
62
63 while ((skb = skb_dequeue(&sk->nr->reseq_queue)) != NULL) {
64 kfree_skb(skb, FREE_READ);
65 }
66
67 while ((skb = skb_dequeue(&sk->nr->frag_queue)) != NULL) {
68 kfree_skb(skb, FREE_READ);
69 }
70 }
71
72
73
74
75
76
77 void nr_frames_acked(struct sock *sk, unsigned short nr)
78 {
79 struct sk_buff *skb;
80
81
82
83
84 if (sk->nr->va != nr) {
85 while (skb_peek(&sk->nr->ack_queue) != NULL && sk->nr->va != nr) {
86 skb = skb_dequeue(&sk->nr->ack_queue);
87 skb->sk = sk;
88 skb->free = 1;
89 kfree_skb(skb, FREE_WRITE);
90 sk->nr->va = (sk->nr->va + 1) % NR_MODULUS;
91 }
92 }
93 }
94
95
96
97
98
99
100 void nr_requeue_frames(struct sock *sk)
101 {
102 struct sk_buff *skb, *skb_prev = NULL;
103
104 while ((skb = skb_dequeue(&sk->nr->ack_queue)) != NULL) {
105 if (skb_prev == NULL)
106 skb_queue_head(&sk->write_queue, skb);
107 else
108 skb_append(skb_prev, skb);
109 skb_prev = skb;
110 }
111 }
112
113
114
115
116
117 int nr_validate_nr(struct sock *sk, unsigned short nr)
118 {
119 unsigned short vc = sk->nr->va;
120
121 while (vc != sk->nr->vs) {
122 if (nr == vc) return 1;
123 vc = (vc + 1) % NR_MODULUS;
124 }
125
126 if (nr == sk->nr->vs) return 1;
127
128 return 0;
129 }
130
131
132
133
134 int nr_in_rx_window(struct sock *sk, unsigned short ns)
135 {
136 unsigned short vc = sk->nr->vl;
137 unsigned short vt = (sk->nr->vl + sk->window) % NR_MODULUS;
138
139 while (vc != vt) {
140 if (ns == vc) return 1;
141 vc = (vc + 1) % NR_MODULUS;
142 }
143
144 if (ns == vt) return 1;
145
146 return 0;
147 }
148
149
150
151
152
153 void nr_write_internal(struct sock *sk, int frametype)
154 {
155 struct sk_buff *skb;
156 unsigned char *dptr;
157 int len, timeout;
158
159 len = AX25_BPQ_HEADER_LEN + AX25_MAX_HEADER_LEN + 3 + NR_NETWORK_LEN + NR_TRANSPORT_LEN;
160
161 switch (frametype & 0x0F) {
162 case NR_CONNREQ:
163 len += 17;
164 break;
165 case NR_CONNACK:
166 len += (sk->nr->bpqext) ? 2 : 1;
167 break;
168 case NR_DISCREQ:
169 case NR_DISCACK:
170 case NR_INFOACK:
171 break;
172 default:
173 printk("nr_write_internal: invalid frame type %d\n", frametype);
174 return;
175 }
176
177 if ((skb = alloc_skb(len, GFP_ATOMIC)) == NULL)
178 return;
179
180
181
182
183 skb_reserve(skb, AX25_BPQ_HEADER_LEN + AX25_MAX_HEADER_LEN + 2 + NR_NETWORK_LEN);
184
185 dptr = skb_put(skb, skb_tailroom(skb));
186
187 switch (frametype & 0x0F) {
188
189 case NR_CONNREQ:
190 timeout = (sk->nr->rtt / PR_SLOWHZ) * 2;
191 *dptr++ = sk->nr->my_index;
192 *dptr++ = sk->nr->my_id;
193 *dptr++ = 0;
194 *dptr++ = 0;
195 *dptr++ = frametype;
196 *dptr++ = sk->window;
197 memcpy(dptr, &sk->nr->user_addr, sizeof(ax25_address));
198 dptr[6] &= ~LAPB_C;
199 dptr[6] &= ~LAPB_E;
200 dptr[6] |= SSSID_SPARE;
201 dptr += AX25_ADDR_LEN;
202 memcpy(dptr, &sk->nr->source_addr, sizeof(ax25_address));
203 dptr[6] &= ~LAPB_C;
204 dptr[6] &= ~LAPB_E;
205 dptr[6] |= SSSID_SPARE;
206 dptr += AX25_ADDR_LEN;
207 *dptr++ = timeout % 256;
208 *dptr++ = timeout / 256;
209 break;
210
211 case NR_CONNACK:
212 *dptr++ = sk->nr->your_index;
213 *dptr++ = sk->nr->your_id;
214 *dptr++ = sk->nr->my_index;
215 *dptr++ = sk->nr->my_id;
216 *dptr++ = frametype;
217 *dptr++ = sk->window;
218 if (sk->nr->bpqext) *dptr++ = nr_default.ttl;
219 break;
220
221 case NR_DISCREQ:
222 case NR_DISCACK:
223 *dptr++ = sk->nr->your_index;
224 *dptr++ = sk->nr->your_id;
225 *dptr++ = 0;
226 *dptr++ = 0;
227 *dptr++ = frametype;
228 break;
229
230 case NR_INFOACK:
231 *dptr++ = sk->nr->your_index;
232 *dptr++ = sk->nr->your_id;
233 *dptr++ = 0;
234 *dptr++ = sk->nr->vr;
235 *dptr++ = frametype;
236 break;
237 }
238
239 skb->free = 1;
240
241 nr_transmit_buffer(sk, skb);
242 }
243
244
245
246
247
248 void nr_transmit_dm(struct sk_buff *skb)
249 {
250 struct sk_buff *skbn;
251 unsigned char *dptr;
252 int len;
253
254 len = AX25_BPQ_HEADER_LEN + AX25_MAX_HEADER_LEN + 3 + NR_NETWORK_LEN + NR_TRANSPORT_LEN + 1;
255
256 if ((skbn = alloc_skb(len, GFP_ATOMIC)) == NULL)
257 return;
258
259 skb_reserve(skbn, AX25_BPQ_HEADER_LEN + AX25_MAX_HEADER_LEN + 2);
260
261 dptr = skb_put(skbn, NR_NETWORK_LEN + NR_TRANSPORT_LEN);
262
263 memcpy(dptr, skb->data + 7, AX25_ADDR_LEN);
264 dptr[6] &= ~LAPB_C;
265 dptr[6] &= ~LAPB_E;
266 dptr[6] |= SSSID_SPARE;
267 dptr += AX25_ADDR_LEN;
268
269 memcpy(dptr, skb->data + 0, AX25_ADDR_LEN);
270 dptr[6] &= ~LAPB_C;
271 dptr[6] |= LAPB_E;
272 dptr[6] |= SSSID_SPARE;
273 dptr += AX25_ADDR_LEN;
274
275 *dptr++ = nr_default.ttl;
276
277 *dptr++ = skb->data[15];
278 *dptr++ = skb->data[16];
279 *dptr++ = 0;
280 *dptr++ = 0;
281 *dptr++ = NR_CONNACK | NR_CHOKE_FLAG;
282 *dptr++ = 0;
283
284 skbn->free = 1;
285 skbn->sk = NULL;
286
287 if (!nr_route_frame(skbn, NULL))
288 kfree_skb(skbn, FREE_WRITE);
289 }
290
291
292
293
294 unsigned short nr_calculate_t1(struct sock *sk)
295 {
296 int n, t;
297
298 for (t = 2, n = 0; n < sk->nr->n2count; n++)
299 t *= 2;
300
301 if (t > 8) t = 8;
302
303 return t * sk->nr->rtt;
304 }
305
306
307
308
309 void nr_calculate_rtt(struct sock *sk)
310 {
311 if (sk->nr->t1timer > 0 && sk->nr->n2count == 0)
312 sk->nr->rtt = (9 * sk->nr->rtt + sk->nr->t1 - sk->nr->t1timer) / 10;
313
314
315 if (sk->nr->rtt < 1 * PR_SLOWHZ)
316 sk->nr->rtt = 1 * PR_SLOWHZ;
317 }
318
319 #endif