]> bbs.cooldavid.org Git - net-next-2.6.git/blame - net/atm/lec.c
[PATCH] capable/capability.h (net/)
[net-next-2.6.git] / net / atm / lec.c
CommitLineData
1da177e4
LT
1/*
2 * lec.c: Lan Emulation driver
3 * Marko Kiiskila mkiiskila@yahoo.com
4 *
5 */
6
7#include <linux/config.h>
8#include <linux/kernel.h>
9#include <linux/bitops.h>
4fc268d2 10#include <linux/capability.h>
1da177e4
LT
11
12/* We are ethernet device */
13#include <linux/if_ether.h>
14#include <linux/netdevice.h>
15#include <linux/etherdevice.h>
16#include <net/sock.h>
17#include <linux/skbuff.h>
18#include <linux/ip.h>
19#include <asm/byteorder.h>
20#include <asm/uaccess.h>
21#include <net/arp.h>
22#include <net/dst.h>
23#include <linux/proc_fs.h>
24#include <linux/spinlock.h>
25#include <linux/proc_fs.h>
26#include <linux/seq_file.h>
27
28/* TokenRing if needed */
29#ifdef CONFIG_TR
30#include <linux/trdevice.h>
31#endif
32
33/* And atm device */
34#include <linux/atmdev.h>
35#include <linux/atmlec.h>
36
37/* Proxy LEC knows about bridging */
38#if defined(CONFIG_BRIDGE) || defined(CONFIG_BRIDGE_MODULE)
39#include <linux/if_bridge.h>
40#include "../bridge/br_private.h"
41
42static unsigned char bridge_ula_lec[] = {0x01, 0x80, 0xc2, 0x00, 0x00};
43#endif
44
45/* Modular too */
46#include <linux/module.h>
47#include <linux/init.h>
48
49#include "lec.h"
50#include "lec_arpc.h"
51#include "resources.h"
52
53#if 0
54#define DPRINTK printk
55#else
56#define DPRINTK(format,args...)
57#endif
58
59#define DUMP_PACKETS 0 /* 0 = None,
60 * 1 = 30 first bytes
61 * 2 = Whole packet
62 */
63
64#define LEC_UNRES_QUE_LEN 8 /* number of tx packets to queue for a
65 single destination while waiting for SVC */
66
67static int lec_open(struct net_device *dev);
68static int lec_start_xmit(struct sk_buff *skb, struct net_device *dev);
69static int lec_close(struct net_device *dev);
70static struct net_device_stats *lec_get_stats(struct net_device *dev);
71static void lec_init(struct net_device *dev);
72static struct lec_arp_table* lec_arp_find(struct lec_priv *priv,
73 unsigned char *mac_addr);
74static int lec_arp_remove(struct lec_priv *priv,
75 struct lec_arp_table *to_remove);
76/* LANE2 functions */
77static void lane2_associate_ind (struct net_device *dev, u8 *mac_address,
78 u8 *tlvs, u32 sizeoftlvs);
79static int lane2_resolve(struct net_device *dev, u8 *dst_mac, int force,
80 u8 **tlvs, u32 *sizeoftlvs);
81static int lane2_associate_req (struct net_device *dev, u8 *lan_dst,
82 u8 *tlvs, u32 sizeoftlvs);
83
84static int lec_addr_delete(struct lec_priv *priv, unsigned char *atm_addr,
85 unsigned long permanent);
86static void lec_arp_check_empties(struct lec_priv *priv,
87 struct atm_vcc *vcc, struct sk_buff *skb);
88static void lec_arp_destroy(struct lec_priv *priv);
89static void lec_arp_init(struct lec_priv *priv);
90static struct atm_vcc* lec_arp_resolve(struct lec_priv *priv,
91 unsigned char *mac_to_find,
92 int is_rdesc,
93 struct lec_arp_table **ret_entry);
94static void lec_arp_update(struct lec_priv *priv, unsigned char *mac_addr,
95 unsigned char *atm_addr, unsigned long remoteflag,
96 unsigned int targetless_le_arp);
97static void lec_flush_complete(struct lec_priv *priv, unsigned long tran_id);
98static int lec_mcast_make(struct lec_priv *priv, struct atm_vcc *vcc);
99static void lec_set_flush_tran_id(struct lec_priv *priv,
100 unsigned char *atm_addr,
101 unsigned long tran_id);
102static void lec_vcc_added(struct lec_priv *priv, struct atmlec_ioc *ioc_data,
103 struct atm_vcc *vcc,
104 void (*old_push)(struct atm_vcc *vcc, struct sk_buff *skb));
105static void lec_vcc_close(struct lec_priv *priv, struct atm_vcc *vcc);
106
107static struct lane2_ops lane2_ops = {
108 lane2_resolve, /* resolve, spec 3.1.3 */
109 lane2_associate_req, /* associate_req, spec 3.1.4 */
110 NULL /* associate indicator, spec 3.1.5 */
111};
112
113static unsigned char bus_mac[ETH_ALEN] = {0xff,0xff,0xff,0xff,0xff,0xff};
114
115/* Device structures */
116static struct net_device *dev_lec[MAX_LEC_ITF];
117
118#if defined(CONFIG_BRIDGE) || defined(CONFIG_BRIDGE_MODULE)
119static void lec_handle_bridge(struct sk_buff *skb, struct net_device *dev)
120{
121 struct ethhdr *eth;
122 char *buff;
123 struct lec_priv *priv;
124
125 /* Check if this is a BPDU. If so, ask zeppelin to send
126 * LE_TOPOLOGY_REQUEST with the same value of Topology Change bit
127 * as the Config BPDU has */
128 eth = (struct ethhdr *)skb->data;
129 buff = skb->data + skb->dev->hard_header_len;
130 if (*buff++ == 0x42 && *buff++ == 0x42 && *buff++ == 0x03) {
131 struct sock *sk;
132 struct sk_buff *skb2;
133 struct atmlec_msg *mesg;
134
135 skb2 = alloc_skb(sizeof(struct atmlec_msg), GFP_ATOMIC);
136 if (skb2 == NULL) return;
137 skb2->len = sizeof(struct atmlec_msg);
138 mesg = (struct atmlec_msg *)skb2->data;
139 mesg->type = l_topology_change;
140 buff += 4;
141 mesg->content.normal.flag = *buff & 0x01; /* 0x01 is topology change */
142
143 priv = (struct lec_priv *)dev->priv;
144 atm_force_charge(priv->lecd, skb2->truesize);
145 sk = sk_atm(priv->lecd);
146 skb_queue_tail(&sk->sk_receive_queue, skb2);
147 sk->sk_data_ready(sk, skb2->len);
148 }
149
150 return;
151}
152#endif /* defined(CONFIG_BRIDGE) || defined(CONFIG_BRIDGE_MODULE) */
153
154/*
155 * Modelled after tr_type_trans
156 * All multicast and ARE or STE frames go to BUS.
157 * Non source routed frames go by destination address.
158 * Last hop source routed frames go by destination address.
159 * Not last hop source routed frames go by _next_ route descriptor.
160 * Returns pointer to destination MAC address or fills in rdesc
161 * and returns NULL.
162 */
163#ifdef CONFIG_TR
164static unsigned char *get_tr_dst(unsigned char *packet, unsigned char *rdesc)
165{
166 struct trh_hdr *trh;
167 int riflen, num_rdsc;
168
169 trh = (struct trh_hdr *)packet;
170 if (trh->daddr[0] & (uint8_t)0x80)
171 return bus_mac; /* multicast */
172
173 if (trh->saddr[0] & TR_RII) {
174 riflen = (ntohs(trh->rcf) & TR_RCF_LEN_MASK) >> 8;
175 if ((ntohs(trh->rcf) >> 13) != 0)
176 return bus_mac; /* ARE or STE */
177 }
178 else
179 return trh->daddr; /* not source routed */
180
181 if (riflen < 6)
182 return trh->daddr; /* last hop, source routed */
183
184 /* riflen is 6 or more, packet has more than one route descriptor */
185 num_rdsc = (riflen/2) - 1;
186 memset(rdesc, 0, ETH_ALEN);
187 /* offset 4 comes from LAN destination field in LE control frames */
188 if (trh->rcf & htons((uint16_t)TR_RCF_DIR_BIT))
189 memcpy(&rdesc[4], &trh->rseg[num_rdsc-2], sizeof(uint16_t));
190 else {
191 memcpy(&rdesc[4], &trh->rseg[1], sizeof(uint16_t));
192 rdesc[5] = ((ntohs(trh->rseg[0]) & 0x000f) | (rdesc[5] & 0xf0));
193 }
194
195 return NULL;
196}
197#endif /* CONFIG_TR */
198
199/*
200 * Open/initialize the netdevice. This is called (in the current kernel)
201 * sometime after booting when the 'ifconfig' program is run.
202 *
203 * This routine should set everything up anew at each open, even
204 * registers that "should" only need to be set once at boot, so that
205 * there is non-reboot way to recover if something goes wrong.
206 */
207
208static int
209lec_open(struct net_device *dev)
210{
211 struct lec_priv *priv = (struct lec_priv *)dev->priv;
212
213 netif_start_queue(dev);
214 memset(&priv->stats,0,sizeof(struct net_device_stats));
215
216 return 0;
217}
218
219static __inline__ void
220lec_send(struct atm_vcc *vcc, struct sk_buff *skb, struct lec_priv *priv)
221{
222 ATM_SKB(skb)->vcc = vcc;
223 ATM_SKB(skb)->atm_options = vcc->atm_options;
224
225 atomic_add(skb->truesize, &sk_atm(vcc)->sk_wmem_alloc);
226 if (vcc->send(vcc, skb) < 0) {
227 priv->stats.tx_dropped++;
228 return;
229 }
230
231 priv->stats.tx_packets++;
232 priv->stats.tx_bytes += skb->len;
233}
234
235static void
236lec_tx_timeout(struct net_device *dev)
237{
238 printk(KERN_INFO "%s: tx timeout\n", dev->name);
239 dev->trans_start = jiffies;
240 netif_wake_queue(dev);
241}
242
243static int
244lec_start_xmit(struct sk_buff *skb, struct net_device *dev)
245{
246 struct sk_buff *skb2;
247 struct lec_priv *priv = (struct lec_priv *)dev->priv;
248 struct lecdatahdr_8023 *lec_h;
249 struct atm_vcc *vcc;
250 struct lec_arp_table *entry;
251 unsigned char *dst;
252 int min_frame_size;
253#ifdef CONFIG_TR
254 unsigned char rdesc[ETH_ALEN]; /* Token Ring route descriptor */
255#endif
256 int is_rdesc;
257#if DUMP_PACKETS > 0
258 char buf[300];
259 int i=0;
260#endif /* DUMP_PACKETS >0 */
261
262 DPRINTK("lec_start_xmit called\n");
263 if (!priv->lecd) {
264 printk("%s:No lecd attached\n",dev->name);
265 priv->stats.tx_errors++;
266 netif_stop_queue(dev);
267 return -EUNATCH;
268 }
269
270 DPRINTK("skbuff head:%lx data:%lx tail:%lx end:%lx\n",
271 (long)skb->head, (long)skb->data, (long)skb->tail,
272 (long)skb->end);
273#if defined(CONFIG_BRIDGE) || defined(CONFIG_BRIDGE_MODULE)
274 if (memcmp(skb->data, bridge_ula_lec, sizeof(bridge_ula_lec)) == 0)
275 lec_handle_bridge(skb, dev);
276#endif
277
278 /* Make sure we have room for lec_id */
279 if (skb_headroom(skb) < 2) {
280
281 DPRINTK("lec_start_xmit: reallocating skb\n");
282 skb2 = skb_realloc_headroom(skb, LEC_HEADER_LEN);
283 kfree_skb(skb);
284 if (skb2 == NULL) return 0;
285 skb = skb2;
286 }
287 skb_push(skb, 2);
288
289 /* Put le header to place, works for TokenRing too */
290 lec_h = (struct lecdatahdr_8023*)skb->data;
291 lec_h->le_header = htons(priv->lecid);
292
293#ifdef CONFIG_TR
294 /* Ugly. Use this to realign Token Ring packets for
295 * e.g. PCA-200E driver. */
296 if (priv->is_trdev) {
297 skb2 = skb_realloc_headroom(skb, LEC_HEADER_LEN);
298 kfree_skb(skb);
299 if (skb2 == NULL) return 0;
300 skb = skb2;
301 }
302#endif
303
304#if DUMP_PACKETS > 0
305 printk("%s: send datalen:%ld lecid:%4.4x\n", dev->name,
306 skb->len, priv->lecid);
307#if DUMP_PACKETS >= 2
308 for(i=0;i<skb->len && i <99;i++) {
309 sprintf(buf+i*3,"%2.2x ",0xff&skb->data[i]);
310 }
311#elif DUMP_PACKETS >= 1
312 for(i=0;i<skb->len && i < 30;i++) {
313 sprintf(buf+i*3,"%2.2x ", 0xff&skb->data[i]);
314 }
315#endif /* DUMP_PACKETS >= 1 */
316 if (i==skb->len)
317 printk("%s\n",buf);
318 else
319 printk("%s...\n",buf);
320#endif /* DUMP_PACKETS > 0 */
321
322 /* Minimum ethernet-frame size */
323#ifdef CONFIG_TR
324 if (priv->is_trdev)
325 min_frame_size = LEC_MINIMUM_8025_SIZE;
326 else
327#endif
328 min_frame_size = LEC_MINIMUM_8023_SIZE;
329 if (skb->len < min_frame_size) {
330 if ((skb->len + skb_tailroom(skb)) < min_frame_size) {
331 skb2 = skb_copy_expand(skb, 0,
332 min_frame_size - skb->truesize, GFP_ATOMIC);
333 dev_kfree_skb(skb);
334 if (skb2 == NULL) {
335 priv->stats.tx_dropped++;
336 return 0;
337 }
338 skb = skb2;
339 }
340 skb_put(skb, min_frame_size - skb->len);
341 }
342
343 /* Send to right vcc */
344 is_rdesc = 0;
345 dst = lec_h->h_dest;
346#ifdef CONFIG_TR
347 if (priv->is_trdev) {
348 dst = get_tr_dst(skb->data+2, rdesc);
349 if (dst == NULL) {
350 dst = rdesc;
351 is_rdesc = 1;
352 }
353 }
354#endif
355 entry = NULL;
356 vcc = lec_arp_resolve(priv, dst, is_rdesc, &entry);
357 DPRINTK("%s:vcc:%p vcc_flags:%x, entry:%p\n", dev->name,
358 vcc, vcc?vcc->flags:0, entry);
359 if (!vcc || !test_bit(ATM_VF_READY,&vcc->flags)) {
360 if (entry && (entry->tx_wait.qlen < LEC_UNRES_QUE_LEN)) {
361 DPRINTK("%s:lec_start_xmit: queuing packet, ", dev->name);
362 DPRINTK("MAC address 0x%02x:%02x:%02x:%02x:%02x:%02x\n",
363 lec_h->h_dest[0], lec_h->h_dest[1], lec_h->h_dest[2],
364 lec_h->h_dest[3], lec_h->h_dest[4], lec_h->h_dest[5]);
365 skb_queue_tail(&entry->tx_wait, skb);
366 } else {
367 DPRINTK("%s:lec_start_xmit: tx queue full or no arp entry, dropping, ", dev->name);
368 DPRINTK("MAC address 0x%02x:%02x:%02x:%02x:%02x:%02x\n",
369 lec_h->h_dest[0], lec_h->h_dest[1], lec_h->h_dest[2],
370 lec_h->h_dest[3], lec_h->h_dest[4], lec_h->h_dest[5]);
371 priv->stats.tx_dropped++;
372 dev_kfree_skb(skb);
373 }
374 return 0;
375 }
376
377#if DUMP_PACKETS > 0
378 printk("%s:sending to vpi:%d vci:%d\n", dev->name,
379 vcc->vpi, vcc->vci);
380#endif /* DUMP_PACKETS > 0 */
381
382 while (entry && (skb2 = skb_dequeue(&entry->tx_wait))) {
383 DPRINTK("lec.c: emptying tx queue, ");
384 DPRINTK("MAC address 0x%02x:%02x:%02x:%02x:%02x:%02x\n",
385 lec_h->h_dest[0], lec_h->h_dest[1], lec_h->h_dest[2],
386 lec_h->h_dest[3], lec_h->h_dest[4], lec_h->h_dest[5]);
387 lec_send(vcc, skb2, priv);
388 }
389
390 lec_send(vcc, skb, priv);
391
392 if (!atm_may_send(vcc, 0)) {
393 struct lec_vcc_priv *vpriv = LEC_VCC_PRIV(vcc);
394
395 vpriv->xoff = 1;
396 netif_stop_queue(dev);
397
398 /*
399 * vcc->pop() might have occurred in between, making
400 * the vcc usuable again. Since xmit is serialized,
401 * this is the only situation we have to re-test.
402 */
403
404 if (atm_may_send(vcc, 0))
405 netif_wake_queue(dev);
406 }
407
408 dev->trans_start = jiffies;
409 return 0;
410}
411
412/* The inverse routine to net_open(). */
413static int
414lec_close(struct net_device *dev)
415{
416 netif_stop_queue(dev);
417 return 0;
418}
419
420/*
421 * Get the current statistics.
422 * This may be called with the card open or closed.
423 */
424static struct net_device_stats *
425lec_get_stats(struct net_device *dev)
426{
427 return &((struct lec_priv *)dev->priv)->stats;
428}
429
430static int
431lec_atm_send(struct atm_vcc *vcc, struct sk_buff *skb)
432{
433 unsigned long flags;
434 struct net_device *dev = (struct net_device*)vcc->proto_data;
435 struct lec_priv *priv = (struct lec_priv*)dev->priv;
436 struct atmlec_msg *mesg;
437 struct lec_arp_table *entry;
438 int i;
439 char *tmp; /* FIXME */
440
441 atomic_sub(skb->truesize, &sk_atm(vcc)->sk_wmem_alloc);
442 mesg = (struct atmlec_msg *)skb->data;
443 tmp = skb->data;
444 tmp += sizeof(struct atmlec_msg);
445 DPRINTK("%s: msg from zeppelin:%d\n", dev->name, mesg->type);
446 switch(mesg->type) {
447 case l_set_mac_addr:
448 for (i=0;i<6;i++) {
449 dev->dev_addr[i] = mesg->content.normal.mac_addr[i];
450 }
451 break;
452 case l_del_mac_addr:
453 for(i=0;i<6;i++) {
454 dev->dev_addr[i] = 0;
455 }
456 break;
457 case l_addr_delete:
458 lec_addr_delete(priv, mesg->content.normal.atm_addr,
459 mesg->content.normal.flag);
460 break;
461 case l_topology_change:
462 priv->topology_change = mesg->content.normal.flag;
463 break;
464 case l_flush_complete:
465 lec_flush_complete(priv, mesg->content.normal.flag);
466 break;
467 case l_narp_req: /* LANE2: see 7.1.35 in the lane2 spec */
468 spin_lock_irqsave(&priv->lec_arp_lock, flags);
469 entry = lec_arp_find(priv, mesg->content.normal.mac_addr);
470 lec_arp_remove(priv, entry);
471 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
472
473 if (mesg->content.normal.no_source_le_narp)
474 break;
475 /* FALL THROUGH */
476 case l_arp_update:
477 lec_arp_update(priv, mesg->content.normal.mac_addr,
478 mesg->content.normal.atm_addr,
479 mesg->content.normal.flag,
480 mesg->content.normal.targetless_le_arp);
481 DPRINTK("lec: in l_arp_update\n");
482 if (mesg->sizeoftlvs != 0) { /* LANE2 3.1.5 */
483 DPRINTK("lec: LANE2 3.1.5, got tlvs, size %d\n", mesg->sizeoftlvs);
484 lane2_associate_ind(dev,
485 mesg->content.normal.mac_addr,
486 tmp, mesg->sizeoftlvs);
487 }
488 break;
489 case l_config:
490 priv->maximum_unknown_frame_count =
491 mesg->content.config.maximum_unknown_frame_count;
492 priv->max_unknown_frame_time =
493 (mesg->content.config.max_unknown_frame_time*HZ);
494 priv->max_retry_count =
495 mesg->content.config.max_retry_count;
496 priv->aging_time = (mesg->content.config.aging_time*HZ);
497 priv->forward_delay_time =
498 (mesg->content.config.forward_delay_time*HZ);
499 priv->arp_response_time =
500 (mesg->content.config.arp_response_time*HZ);
501 priv->flush_timeout = (mesg->content.config.flush_timeout*HZ);
502 priv->path_switching_delay =
503 (mesg->content.config.path_switching_delay*HZ);
504 priv->lane_version = mesg->content.config.lane_version; /* LANE2 */
505 priv->lane2_ops = NULL;
506 if (priv->lane_version > 1)
507 priv->lane2_ops = &lane2_ops;
508 if (dev->change_mtu(dev, mesg->content.config.mtu))
509 printk("%s: change_mtu to %d failed\n", dev->name,
510 mesg->content.config.mtu);
511 priv->is_proxy = mesg->content.config.is_proxy;
512 break;
513 case l_flush_tran_id:
514 lec_set_flush_tran_id(priv, mesg->content.normal.atm_addr,
515 mesg->content.normal.flag);
516 break;
517 case l_set_lecid:
518 priv->lecid=(unsigned short)(0xffff&mesg->content.normal.flag);
519 break;
520 case l_should_bridge: {
521#if defined(CONFIG_BRIDGE) || defined(CONFIG_BRIDGE_MODULE)
522 struct net_bridge_fdb_entry *f;
523
524 DPRINTK("%s: bridge zeppelin asks about 0x%02x:%02x:%02x:%02x:%02x:%02x\n",
525 dev->name,
526 mesg->content.proxy.mac_addr[0], mesg->content.proxy.mac_addr[1],
527 mesg->content.proxy.mac_addr[2], mesg->content.proxy.mac_addr[3],
528 mesg->content.proxy.mac_addr[4], mesg->content.proxy.mac_addr[5]);
529
530 if (br_fdb_get_hook == NULL || dev->br_port == NULL)
531 break;
532
533 f = br_fdb_get_hook(dev->br_port->br, mesg->content.proxy.mac_addr);
534 if (f != NULL &&
535 f->dst->dev != dev &&
536 f->dst->state == BR_STATE_FORWARDING) {
537 /* hit from bridge table, send LE_ARP_RESPONSE */
538 struct sk_buff *skb2;
539 struct sock *sk;
540
541 DPRINTK("%s: entry found, responding to zeppelin\n", dev->name);
542 skb2 = alloc_skb(sizeof(struct atmlec_msg), GFP_ATOMIC);
543 if (skb2 == NULL) {
544 br_fdb_put_hook(f);
545 break;
546 }
547 skb2->len = sizeof(struct atmlec_msg);
548 memcpy(skb2->data, mesg, sizeof(struct atmlec_msg));
549 atm_force_charge(priv->lecd, skb2->truesize);
550 sk = sk_atm(priv->lecd);
551 skb_queue_tail(&sk->sk_receive_queue, skb2);
552 sk->sk_data_ready(sk, skb2->len);
553 }
554 if (f != NULL) br_fdb_put_hook(f);
555#endif /* defined(CONFIG_BRIDGE) || defined(CONFIG_BRIDGE_MODULE) */
556 }
557 break;
558 default:
559 printk("%s: Unknown message type %d\n", dev->name, mesg->type);
560 dev_kfree_skb(skb);
561 return -EINVAL;
562 }
563 dev_kfree_skb(skb);
564 return 0;
565}
566
567static void
568lec_atm_close(struct atm_vcc *vcc)
569{
570 struct sk_buff *skb;
571 struct net_device *dev = (struct net_device *)vcc->proto_data;
572 struct lec_priv *priv = (struct lec_priv *)dev->priv;
573
574 priv->lecd = NULL;
575 /* Do something needful? */
576
577 netif_stop_queue(dev);
578 lec_arp_destroy(priv);
579
580 if (skb_peek(&sk_atm(vcc)->sk_receive_queue))
581 printk("%s lec_atm_close: closing with messages pending\n",
582 dev->name);
583 while ((skb = skb_dequeue(&sk_atm(vcc)->sk_receive_queue)) != NULL) {
584 atm_return(vcc, skb->truesize);
585 dev_kfree_skb(skb);
586 }
587
588 printk("%s: Shut down!\n", dev->name);
589 module_put(THIS_MODULE);
590}
591
592static struct atmdev_ops lecdev_ops = {
593 .close = lec_atm_close,
594 .send = lec_atm_send
595};
596
597static struct atm_dev lecatm_dev = {
598 .ops = &lecdev_ops,
599 .type = "lec",
600 .number = 999, /* dummy device number */
601 .lock = SPIN_LOCK_UNLOCKED
602};
603
604/*
605 * LANE2: new argument struct sk_buff *data contains
606 * the LE_ARP based TLVs introduced in the LANE2 spec
607 */
608static int
609send_to_lecd(struct lec_priv *priv, atmlec_msg_type type,
610 unsigned char *mac_addr, unsigned char *atm_addr,
611 struct sk_buff *data)
612{
613 struct sock *sk;
614 struct sk_buff *skb;
615 struct atmlec_msg *mesg;
616
617 if (!priv || !priv->lecd) {
618 return -1;
619 }
620 skb = alloc_skb(sizeof(struct atmlec_msg), GFP_ATOMIC);
621 if (!skb)
622 return -1;
623 skb->len = sizeof(struct atmlec_msg);
624 mesg = (struct atmlec_msg *)skb->data;
625 memset(mesg, 0, sizeof(struct atmlec_msg));
626 mesg->type = type;
627 if (data != NULL)
628 mesg->sizeoftlvs = data->len;
629 if (mac_addr)
630 memcpy(&mesg->content.normal.mac_addr, mac_addr, ETH_ALEN);
631 else
632 mesg->content.normal.targetless_le_arp = 1;
633 if (atm_addr)
634 memcpy(&mesg->content.normal.atm_addr, atm_addr, ATM_ESA_LEN);
635
636 atm_force_charge(priv->lecd, skb->truesize);
637 sk = sk_atm(priv->lecd);
638 skb_queue_tail(&sk->sk_receive_queue, skb);
639 sk->sk_data_ready(sk, skb->len);
640
641 if (data != NULL) {
642 DPRINTK("lec: about to send %d bytes of data\n", data->len);
643 atm_force_charge(priv->lecd, data->truesize);
644 skb_queue_tail(&sk->sk_receive_queue, data);
645 sk->sk_data_ready(sk, skb->len);
646 }
647
648 return 0;
649}
650
651/* shamelessly stolen from drivers/net/net_init.c */
652static int lec_change_mtu(struct net_device *dev, int new_mtu)
653{
654 if ((new_mtu < 68) || (new_mtu > 18190))
655 return -EINVAL;
656 dev->mtu = new_mtu;
657 return 0;
658}
659
660static void lec_set_multicast_list(struct net_device *dev)
661{
662 /* by default, all multicast frames arrive over the bus.
663 * eventually support selective multicast service
664 */
665 return;
666}
667
668static void
669lec_init(struct net_device *dev)
670{
671 dev->change_mtu = lec_change_mtu;
672 dev->open = lec_open;
673 dev->stop = lec_close;
674 dev->hard_start_xmit = lec_start_xmit;
675 dev->tx_timeout = lec_tx_timeout;
676
677 dev->get_stats = lec_get_stats;
678 dev->set_multicast_list = lec_set_multicast_list;
679 dev->do_ioctl = NULL;
680 printk("%s: Initialized!\n",dev->name);
681 return;
682}
683
684static unsigned char lec_ctrl_magic[] = {
685 0xff,
686 0x00,
687 0x01,
688 0x01 };
689
4a7097fc
ST
690#define LEC_DATA_DIRECT_8023 2
691#define LEC_DATA_DIRECT_8025 3
692
693static int lec_is_data_direct(struct atm_vcc *vcc)
694{
695 return ((vcc->sap.blli[0].l3.tr9577.snap[4] == LEC_DATA_DIRECT_8023) ||
696 (vcc->sap.blli[0].l3.tr9577.snap[4] == LEC_DATA_DIRECT_8025));
697}
698
1da177e4
LT
699static void
700lec_push(struct atm_vcc *vcc, struct sk_buff *skb)
701{
4a7097fc 702 unsigned long flags;
1da177e4
LT
703 struct net_device *dev = (struct net_device *)vcc->proto_data;
704 struct lec_priv *priv = (struct lec_priv *)dev->priv;
705
706#if DUMP_PACKETS >0
707 int i=0;
708 char buf[300];
709
710 printk("%s: lec_push vcc vpi:%d vci:%d\n", dev->name,
711 vcc->vpi, vcc->vci);
712#endif
713 if (!skb) {
714 DPRINTK("%s: null skb\n",dev->name);
715 lec_vcc_close(priv, vcc);
716 return;
717 }
718#if DUMP_PACKETS > 0
719 printk("%s: rcv datalen:%ld lecid:%4.4x\n", dev->name,
720 skb->len, priv->lecid);
721#if DUMP_PACKETS >= 2
722 for(i=0;i<skb->len && i <99;i++) {
723 sprintf(buf+i*3,"%2.2x ",0xff&skb->data[i]);
724 }
725#elif DUMP_PACKETS >= 1
726 for(i=0;i<skb->len && i < 30;i++) {
727 sprintf(buf+i*3,"%2.2x ", 0xff&skb->data[i]);
728 }
729#endif /* DUMP_PACKETS >= 1 */
730 if (i==skb->len)
731 printk("%s\n",buf);
732 else
733 printk("%s...\n",buf);
734#endif /* DUMP_PACKETS > 0 */
735 if (memcmp(skb->data, lec_ctrl_magic, 4) ==0) { /* Control frame, to daemon*/
736 struct sock *sk = sk_atm(vcc);
737
738 DPRINTK("%s: To daemon\n",dev->name);
739 skb_queue_tail(&sk->sk_receive_queue, skb);
740 sk->sk_data_ready(sk, skb->len);
741 } else { /* Data frame, queue to protocol handlers */
4a7097fc
ST
742 struct lec_arp_table *entry;
743 unsigned char *src, *dst;
1da177e4
LT
744
745 atm_return(vcc,skb->truesize);
746 if (*(uint16_t *)skb->data == htons(priv->lecid) ||
747 !priv->lecd ||
748 !(dev->flags & IFF_UP)) {
749 /* Probably looping back, or if lecd is missing,
750 lecd has gone down */
751 DPRINTK("Ignoring frame...\n");
752 dev_kfree_skb(skb);
753 return;
754 }
755#ifdef CONFIG_TR
4a7097fc
ST
756 if (priv->is_trdev)
757 dst = ((struct lecdatahdr_8025 *) skb->data)->h_dest;
1da177e4
LT
758 else
759#endif
4a7097fc
ST
760 dst = ((struct lecdatahdr_8023 *) skb->data)->h_dest;
761
762 /* If this is a Data Direct VCC, and the VCC does not match
763 * the LE_ARP cache entry, delete the LE_ARP cache entry.
764 */
765 spin_lock_irqsave(&priv->lec_arp_lock, flags);
766 if (lec_is_data_direct(vcc)) {
767#ifdef CONFIG_TR
768 if (priv->is_trdev)
769 src = ((struct lecdatahdr_8025 *) skb->data)->h_source;
770 else
771#endif
772 src = ((struct lecdatahdr_8023 *) skb->data)->h_source;
773 entry = lec_arp_find(priv, src);
774 if (entry && entry->vcc != vcc) {
775 lec_arp_remove(priv, entry);
776 kfree(entry);
777 }
778 }
779 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
1da177e4
LT
780
781 if (!(dst[0]&0x01) && /* Never filter Multi/Broadcast */
782 !priv->is_proxy && /* Proxy wants all the packets */
783 memcmp(dst, dev->dev_addr, dev->addr_len)) {
784 dev_kfree_skb(skb);
785 return;
786 }
787 if (priv->lec_arp_empty_ones) {
788 lec_arp_check_empties(priv, vcc, skb);
789 }
790 skb->dev = dev;
791 skb_pull(skb, 2); /* skip lec_id */
792#ifdef CONFIG_TR
793 if (priv->is_trdev) skb->protocol = tr_type_trans(skb, dev);
794 else
795#endif
796 skb->protocol = eth_type_trans(skb, dev);
797 priv->stats.rx_packets++;
798 priv->stats.rx_bytes += skb->len;
799 memset(ATM_SKB(skb), 0, sizeof(struct atm_skb_data));
800 netif_rx(skb);
801 }
802}
803
804static void
805lec_pop(struct atm_vcc *vcc, struct sk_buff *skb)
806{
807 struct lec_vcc_priv *vpriv = LEC_VCC_PRIV(vcc);
808 struct net_device *dev = skb->dev;
809
810 if (vpriv == NULL) {
811 printk("lec_pop(): vpriv = NULL!?!?!?\n");
812 return;
813 }
814
815 vpriv->old_pop(vcc, skb);
816
817 if (vpriv->xoff && atm_may_send(vcc, 0)) {
818 vpriv->xoff = 0;
819 if (netif_running(dev) && netif_queue_stopped(dev))
820 netif_wake_queue(dev);
821 }
822}
823
824static int
825lec_vcc_attach(struct atm_vcc *vcc, void __user *arg)
826{
827 struct lec_vcc_priv *vpriv;
828 int bytes_left;
829 struct atmlec_ioc ioc_data;
830
831 /* Lecd must be up in this case */
832 bytes_left = copy_from_user(&ioc_data, arg, sizeof(struct atmlec_ioc));
833 if (bytes_left != 0) {
834 printk("lec: lec_vcc_attach, copy from user failed for %d bytes\n",
835 bytes_left);
836 }
837 if (ioc_data.dev_num < 0 || ioc_data.dev_num >= MAX_LEC_ITF ||
838 !dev_lec[ioc_data.dev_num])
839 return -EINVAL;
840 if (!(vpriv = kmalloc(sizeof(struct lec_vcc_priv), GFP_KERNEL)))
841 return -ENOMEM;
842 vpriv->xoff = 0;
843 vpriv->old_pop = vcc->pop;
844 vcc->user_back = vpriv;
845 vcc->pop = lec_pop;
846 lec_vcc_added(dev_lec[ioc_data.dev_num]->priv,
847 &ioc_data, vcc, vcc->push);
848 vcc->proto_data = dev_lec[ioc_data.dev_num];
849 vcc->push = lec_push;
850 return 0;
851}
852
853static int
854lec_mcast_attach(struct atm_vcc *vcc, int arg)
855{
856 if (arg <0 || arg >= MAX_LEC_ITF || !dev_lec[arg])
857 return -EINVAL;
858 vcc->proto_data = dev_lec[arg];
859 return (lec_mcast_make((struct lec_priv*)dev_lec[arg]->priv, vcc));
860}
861
862/* Initialize device. */
863static int
864lecd_attach(struct atm_vcc *vcc, int arg)
865{
866 int i;
867 struct lec_priv *priv;
868
869 if (arg<0)
870 i = 0;
871 else
872 i = arg;
873#ifdef CONFIG_TR
874 if (arg >= MAX_LEC_ITF)
875 return -EINVAL;
876#else /* Reserve the top NUM_TR_DEVS for TR */
877 if (arg >= (MAX_LEC_ITF-NUM_TR_DEVS))
878 return -EINVAL;
879#endif
880 if (!dev_lec[i]) {
881 int is_trdev, size;
882
883 is_trdev = 0;
884 if (i >= (MAX_LEC_ITF - NUM_TR_DEVS))
885 is_trdev = 1;
886
887 size = sizeof(struct lec_priv);
888#ifdef CONFIG_TR
889 if (is_trdev)
890 dev_lec[i] = alloc_trdev(size);
891 else
892#endif
893 dev_lec[i] = alloc_etherdev(size);
894 if (!dev_lec[i])
895 return -ENOMEM;
896 snprintf(dev_lec[i]->name, IFNAMSIZ, "lec%d", i);
897 if (register_netdev(dev_lec[i])) {
898 free_netdev(dev_lec[i]);
899 return -EINVAL;
900 }
901
902 priv = dev_lec[i]->priv;
903 priv->is_trdev = is_trdev;
904 lec_init(dev_lec[i]);
905 } else {
906 priv = dev_lec[i]->priv;
907 if (priv->lecd)
908 return -EADDRINUSE;
909 }
910 lec_arp_init(priv);
911 priv->itfnum = i; /* LANE2 addition */
912 priv->lecd = vcc;
913 vcc->dev = &lecatm_dev;
914 vcc_insert_socket(sk_atm(vcc));
915
916 vcc->proto_data = dev_lec[i];
917 set_bit(ATM_VF_META,&vcc->flags);
918 set_bit(ATM_VF_READY,&vcc->flags);
919
920 /* Set default values to these variables */
921 priv->maximum_unknown_frame_count = 1;
922 priv->max_unknown_frame_time = (1*HZ);
923 priv->vcc_timeout_period = (1200*HZ);
924 priv->max_retry_count = 1;
925 priv->aging_time = (300*HZ);
926 priv->forward_delay_time = (15*HZ);
927 priv->topology_change = 0;
928 priv->arp_response_time = (1*HZ);
929 priv->flush_timeout = (4*HZ);
930 priv->path_switching_delay = (6*HZ);
931
932 if (dev_lec[i]->flags & IFF_UP) {
933 netif_start_queue(dev_lec[i]);
934 }
935 __module_get(THIS_MODULE);
936 return i;
937}
938
939#ifdef CONFIG_PROC_FS
940static char* lec_arp_get_status_string(unsigned char status)
941{
942 static char *lec_arp_status_string[] = {
943 "ESI_UNKNOWN ",
944 "ESI_ARP_PENDING ",
945 "ESI_VC_PENDING ",
946 "<Undefined> ",
947 "ESI_FLUSH_PENDING ",
948 "ESI_FORWARD_DIRECT"
949 };
950
951 if (status > ESI_FORWARD_DIRECT)
952 status = 3; /* ESI_UNDEFINED */
953 return lec_arp_status_string[status];
954}
955
956static void lec_info(struct seq_file *seq, struct lec_arp_table *entry)
957{
958 int i;
959
960 for (i = 0; i < ETH_ALEN; i++)
961 seq_printf(seq, "%2.2x", entry->mac_addr[i] & 0xff);
962 seq_printf(seq, " ");
963 for (i = 0; i < ATM_ESA_LEN; i++)
964 seq_printf(seq, "%2.2x", entry->atm_addr[i] & 0xff);
965 seq_printf(seq, " %s %4.4x", lec_arp_get_status_string(entry->status),
966 entry->flags & 0xffff);
967 if (entry->vcc)
968 seq_printf(seq, "%3d %3d ", entry->vcc->vpi, entry->vcc->vci);
969 else
970 seq_printf(seq, " ");
971 if (entry->recv_vcc) {
972 seq_printf(seq, " %3d %3d", entry->recv_vcc->vpi,
973 entry->recv_vcc->vci);
974 }
975 seq_putc(seq, '\n');
976}
977
978
979struct lec_state {
980 unsigned long flags;
981 struct lec_priv *locked;
982 struct lec_arp_table *entry;
983 struct net_device *dev;
984 int itf;
985 int arp_table;
986 int misc_table;
987};
988
989static void *lec_tbl_walk(struct lec_state *state, struct lec_arp_table *tbl,
990 loff_t *l)
991{
992 struct lec_arp_table *e = state->entry;
993
994 if (!e)
995 e = tbl;
996 if (e == (void *)1) {
997 e = tbl;
998 --*l;
999 }
1000 for (; e; e = e->next) {
1001 if (--*l < 0)
1002 break;
1003 }
1004 state->entry = e;
1005 return (*l < 0) ? state : NULL;
1006}
1007
1008static void *lec_arp_walk(struct lec_state *state, loff_t *l,
1009 struct lec_priv *priv)
1010{
1011 void *v = NULL;
1012 int p;
1013
1014 for (p = state->arp_table; p < LEC_ARP_TABLE_SIZE; p++) {
1015 v = lec_tbl_walk(state, priv->lec_arp_tables[p], l);
1016 if (v)
1017 break;
1018 }
1019 state->arp_table = p;
1020 return v;
1021}
1022
1023static void *lec_misc_walk(struct lec_state *state, loff_t *l,
1024 struct lec_priv *priv)
1025{
1026 struct lec_arp_table *lec_misc_tables[] = {
1027 priv->lec_arp_empty_ones,
1028 priv->lec_no_forward,
1029 priv->mcast_fwds
1030 };
1031 void *v = NULL;
1032 int q;
1033
1034 for (q = state->misc_table; q < ARRAY_SIZE(lec_misc_tables); q++) {
1035 v = lec_tbl_walk(state, lec_misc_tables[q], l);
1036 if (v)
1037 break;
1038 }
1039 state->misc_table = q;
1040 return v;
1041}
1042
1043static void *lec_priv_walk(struct lec_state *state, loff_t *l,
1044 struct lec_priv *priv)
1045{
1046 if (!state->locked) {
1047 state->locked = priv;
1048 spin_lock_irqsave(&priv->lec_arp_lock, state->flags);
1049 }
1050 if (!lec_arp_walk(state, l, priv) &&
1051 !lec_misc_walk(state, l, priv)) {
1052 spin_unlock_irqrestore(&priv->lec_arp_lock, state->flags);
1053 state->locked = NULL;
1054 /* Partial state reset for the next time we get called */
1055 state->arp_table = state->misc_table = 0;
1056 }
1057 return state->locked;
1058}
1059
1060static void *lec_itf_walk(struct lec_state *state, loff_t *l)
1061{
1062 struct net_device *dev;
1063 void *v;
1064
1065 dev = state->dev ? state->dev : dev_lec[state->itf];
1066 v = (dev && dev->priv) ? lec_priv_walk(state, l, dev->priv) : NULL;
1067 if (!v && dev) {
1068 dev_put(dev);
1069 /* Partial state reset for the next time we get called */
1070 dev = NULL;
1071 }
1072 state->dev = dev;
1073 return v;
1074}
1075
1076static void *lec_get_idx(struct lec_state *state, loff_t l)
1077{
1078 void *v = NULL;
1079
1080 for (; state->itf < MAX_LEC_ITF; state->itf++) {
1081 v = lec_itf_walk(state, &l);
1082 if (v)
1083 break;
1084 }
1085 return v;
1086}
1087
1088static void *lec_seq_start(struct seq_file *seq, loff_t *pos)
1089{
1090 struct lec_state *state = seq->private;
1091
1092 state->itf = 0;
1093 state->dev = NULL;
1094 state->locked = NULL;
1095 state->arp_table = 0;
1096 state->misc_table = 0;
1097 state->entry = (void *)1;
1098
1099 return *pos ? lec_get_idx(state, *pos) : (void*)1;
1100}
1101
1102static void lec_seq_stop(struct seq_file *seq, void *v)
1103{
1104 struct lec_state *state = seq->private;
1105
1106 if (state->dev) {
1107 spin_unlock_irqrestore(&state->locked->lec_arp_lock,
1108 state->flags);
1109 dev_put(state->dev);
1110 }
1111}
1112
1113static void *lec_seq_next(struct seq_file *seq, void *v, loff_t *pos)
1114{
1115 struct lec_state *state = seq->private;
1116
1117 v = lec_get_idx(state, 1);
1118 *pos += !!PTR_ERR(v);
1119 return v;
1120}
1121
1122static int lec_seq_show(struct seq_file *seq, void *v)
1123{
1124 static char lec_banner[] = "Itf MAC ATM destination"
1125 " Status Flags "
1126 "VPI/VCI Recv VPI/VCI\n";
1127
1128 if (v == (void *)1)
1129 seq_puts(seq, lec_banner);
1130 else {
1131 struct lec_state *state = seq->private;
1132 struct net_device *dev = state->dev;
1133
1134 seq_printf(seq, "%s ", dev->name);
1135 lec_info(seq, state->entry);
1136 }
1137 return 0;
1138}
1139
1140static struct seq_operations lec_seq_ops = {
1141 .start = lec_seq_start,
1142 .next = lec_seq_next,
1143 .stop = lec_seq_stop,
1144 .show = lec_seq_show,
1145};
1146
1147static int lec_seq_open(struct inode *inode, struct file *file)
1148{
1149 struct lec_state *state;
1150 struct seq_file *seq;
1151 int rc = -EAGAIN;
1152
1153 state = kmalloc(sizeof(*state), GFP_KERNEL);
1154 if (!state) {
1155 rc = -ENOMEM;
1156 goto out;
1157 }
1158
1159 rc = seq_open(file, &lec_seq_ops);
1160 if (rc)
1161 goto out_kfree;
1162 seq = file->private_data;
1163 seq->private = state;
1164out:
1165 return rc;
1166
1167out_kfree:
1168 kfree(state);
1169 goto out;
1170}
1171
1172static int lec_seq_release(struct inode *inode, struct file *file)
1173{
1174 return seq_release_private(inode, file);
1175}
1176
1177static struct file_operations lec_seq_fops = {
1178 .owner = THIS_MODULE,
1179 .open = lec_seq_open,
1180 .read = seq_read,
1181 .llseek = seq_lseek,
1182 .release = lec_seq_release,
1183};
1184#endif
1185
1186static int lane_ioctl(struct socket *sock, unsigned int cmd, unsigned long arg)
1187{
1188 struct atm_vcc *vcc = ATM_SD(sock);
1189 int err = 0;
1190
1191 switch (cmd) {
1192 case ATMLEC_CTRL:
1193 case ATMLEC_MCAST:
1194 case ATMLEC_DATA:
1195 if (!capable(CAP_NET_ADMIN))
1196 return -EPERM;
1197 break;
1198 default:
1199 return -ENOIOCTLCMD;
1200 }
1201
1202 switch (cmd) {
1203 case ATMLEC_CTRL:
1204 err = lecd_attach(vcc, (int) arg);
1205 if (err >= 0)
1206 sock->state = SS_CONNECTED;
1207 break;
1208 case ATMLEC_MCAST:
1209 err = lec_mcast_attach(vcc, (int) arg);
1210 break;
1211 case ATMLEC_DATA:
1212 err = lec_vcc_attach(vcc, (void __user *) arg);
1213 break;
1214 }
1215
1216 return err;
1217}
1218
1219static struct atm_ioctl lane_ioctl_ops = {
1220 .owner = THIS_MODULE,
1221 .ioctl = lane_ioctl,
1222};
1223
1224static int __init lane_module_init(void)
1225{
1226#ifdef CONFIG_PROC_FS
1227 struct proc_dir_entry *p;
1228
1229 p = create_proc_entry("lec", S_IRUGO, atm_proc_root);
1230 if (p)
1231 p->proc_fops = &lec_seq_fops;
1232#endif
1233
1234 register_atm_ioctl(&lane_ioctl_ops);
1235 printk("lec.c: " __DATE__ " " __TIME__ " initialized\n");
1236 return 0;
1237}
1238
1239static void __exit lane_module_cleanup(void)
1240{
1241 int i;
1242 struct lec_priv *priv;
1243
1244 remove_proc_entry("lec", atm_proc_root);
1245
1246 deregister_atm_ioctl(&lane_ioctl_ops);
1247
1248 for (i = 0; i < MAX_LEC_ITF; i++) {
1249 if (dev_lec[i] != NULL) {
1250 priv = (struct lec_priv *)dev_lec[i]->priv;
1251 unregister_netdev(dev_lec[i]);
1252 free_netdev(dev_lec[i]);
1253 dev_lec[i] = NULL;
1254 }
1255 }
1256
1257 return;
1258}
1259
1260module_init(lane_module_init);
1261module_exit(lane_module_cleanup);
1262
1263/*
1264 * LANE2: 3.1.3, LE_RESOLVE.request
1265 * Non force allocates memory and fills in *tlvs, fills in *sizeoftlvs.
1266 * If sizeoftlvs == NULL the default TLVs associated with with this
1267 * lec will be used.
1268 * If dst_mac == NULL, targetless LE_ARP will be sent
1269 */
1270static int lane2_resolve(struct net_device *dev, u8 *dst_mac, int force,
1271 u8 **tlvs, u32 *sizeoftlvs)
1272{
1273 unsigned long flags;
1274 struct lec_priv *priv = (struct lec_priv *)dev->priv;
1275 struct lec_arp_table *table;
1276 struct sk_buff *skb;
1277 int retval;
1278
1279 if (force == 0) {
1280 spin_lock_irqsave(&priv->lec_arp_lock, flags);
1281 table = lec_arp_find(priv, dst_mac);
1282 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
1283 if(table == NULL)
1284 return -1;
1285
1286 *tlvs = kmalloc(table->sizeoftlvs, GFP_ATOMIC);
1287 if (*tlvs == NULL)
1288 return -1;
1289
1290 memcpy(*tlvs, table->tlvs, table->sizeoftlvs);
1291 *sizeoftlvs = table->sizeoftlvs;
1292
1293 return 0;
1294 }
1295
1296 if (sizeoftlvs == NULL)
1297 retval = send_to_lecd(priv, l_arp_xmt, dst_mac, NULL, NULL);
1298
1299 else {
1300 skb = alloc_skb(*sizeoftlvs, GFP_ATOMIC);
1301 if (skb == NULL)
1302 return -1;
1303 skb->len = *sizeoftlvs;
1304 memcpy(skb->data, *tlvs, *sizeoftlvs);
1305 retval = send_to_lecd(priv, l_arp_xmt, dst_mac, NULL, skb);
1306 }
1307 return retval;
1308}
1309
1310
1311/*
1312 * LANE2: 3.1.4, LE_ASSOCIATE.request
1313 * Associate the *tlvs with the *lan_dst address.
1314 * Will overwrite any previous association
1315 * Returns 1 for success, 0 for failure (out of memory)
1316 *
1317 */
1318static int lane2_associate_req (struct net_device *dev, u8 *lan_dst,
1319 u8 *tlvs, u32 sizeoftlvs)
1320{
1321 int retval;
1322 struct sk_buff *skb;
1323 struct lec_priv *priv = (struct lec_priv*)dev->priv;
1324
d3f4a687 1325 if (compare_ether_addr(lan_dst, dev->dev_addr))
1da177e4
LT
1326 return (0); /* not our mac address */
1327
1328 kfree(priv->tlvs); /* NULL if there was no previous association */
1329
1330 priv->tlvs = kmalloc(sizeoftlvs, GFP_KERNEL);
1331 if (priv->tlvs == NULL)
1332 return (0);
1333 priv->sizeoftlvs = sizeoftlvs;
1334 memcpy(priv->tlvs, tlvs, sizeoftlvs);
1335
1336 skb = alloc_skb(sizeoftlvs, GFP_ATOMIC);
1337 if (skb == NULL)
1338 return 0;
1339 skb->len = sizeoftlvs;
1340 memcpy(skb->data, tlvs, sizeoftlvs);
1341 retval = send_to_lecd(priv, l_associate_req, NULL, NULL, skb);
1342 if (retval != 0)
1343 printk("lec.c: lane2_associate_req() failed\n");
1344 /* If the previous association has changed we must
1345 * somehow notify other LANE entities about the change
1346 */
1347 return (1);
1348}
1349
1350/*
1351 * LANE2: 3.1.5, LE_ASSOCIATE.indication
1352 *
1353 */
1354static void lane2_associate_ind (struct net_device *dev, u8 *mac_addr,
1355 u8 *tlvs, u32 sizeoftlvs)
1356{
1357#if 0
1358 int i = 0;
1359#endif
1360 struct lec_priv *priv = (struct lec_priv *)dev->priv;
1361#if 0 /* Why have the TLVs in LE_ARP entries since we do not use them? When you
1362 uncomment this code, make sure the TLVs get freed when entry is killed */
1363 struct lec_arp_table *entry = lec_arp_find(priv, mac_addr);
1364
1365 if (entry == NULL)
1366 return; /* should not happen */
1367
1368 kfree(entry->tlvs);
1369
1370 entry->tlvs = kmalloc(sizeoftlvs, GFP_KERNEL);
1371 if (entry->tlvs == NULL)
1372 return;
1373
1374 entry->sizeoftlvs = sizeoftlvs;
1375 memcpy(entry->tlvs, tlvs, sizeoftlvs);
1376#endif
1377#if 0
1378 printk("lec.c: lane2_associate_ind()\n");
1379 printk("dump of tlvs, sizeoftlvs=%d\n", sizeoftlvs);
1380 while (i < sizeoftlvs)
1381 printk("%02x ", tlvs[i++]);
1382
1383 printk("\n");
1384#endif
1385
1386 /* tell MPOA about the TLVs we saw */
1387 if (priv->lane2_ops && priv->lane2_ops->associate_indicator) {
1388 priv->lane2_ops->associate_indicator(dev, mac_addr,
1389 tlvs, sizeoftlvs);
1390 }
1391 return;
1392}
1393
1394/*
1395 * Here starts what used to lec_arpc.c
1396 *
1397 * lec_arpc.c was added here when making
1398 * lane client modular. October 1997
1399 *
1400 */
1401
1402#include <linux/types.h>
1403#include <linux/sched.h>
1404#include <linux/timer.h>
1405#include <asm/param.h>
1406#include <asm/atomic.h>
1407#include <linux/inetdevice.h>
1408#include <net/route.h>
1409
1410
1411#if 0
1412#define DPRINTK(format,args...)
1413/*
1414#define DPRINTK printk
1415*/
1416#endif
1417#define DEBUG_ARP_TABLE 0
1418
1419#define LEC_ARP_REFRESH_INTERVAL (3*HZ)
1420
1421static void lec_arp_check_expire(unsigned long data);
1422static void lec_arp_expire_arp(unsigned long data);
1423
1424/*
1425 * Arp table funcs
1426 */
1427
1428#define HASH(ch) (ch & (LEC_ARP_TABLE_SIZE -1))
1429
1430/*
1431 * Initialization of arp-cache
1432 */
1433static void
1434lec_arp_init(struct lec_priv *priv)
1435{
1436 unsigned short i;
1437
1438 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
1439 priv->lec_arp_tables[i] = NULL;
1440 }
1441 spin_lock_init(&priv->lec_arp_lock);
1442 init_timer(&priv->lec_arp_timer);
1443 priv->lec_arp_timer.expires = jiffies + LEC_ARP_REFRESH_INTERVAL;
1444 priv->lec_arp_timer.data = (unsigned long)priv;
1445 priv->lec_arp_timer.function = lec_arp_check_expire;
1446 add_timer(&priv->lec_arp_timer);
1447}
1448
1449static void
1450lec_arp_clear_vccs(struct lec_arp_table *entry)
1451{
1452 if (entry->vcc) {
1453 struct atm_vcc *vcc = entry->vcc;
1454 struct lec_vcc_priv *vpriv = LEC_VCC_PRIV(vcc);
1455 struct net_device *dev = (struct net_device*) vcc->proto_data;
1456
1457 vcc->pop = vpriv->old_pop;
1458 if (vpriv->xoff)
1459 netif_wake_queue(dev);
1460 kfree(vpriv);
1461 vcc->user_back = NULL;
1462 vcc->push = entry->old_push;
1463 vcc_release_async(vcc, -EPIPE);
1464 vcc = NULL;
1465 }
1466 if (entry->recv_vcc) {
1467 entry->recv_vcc->push = entry->old_recv_push;
1468 vcc_release_async(entry->recv_vcc, -EPIPE);
1469 entry->recv_vcc = NULL;
1470 }
1471}
1472
1473/*
1474 * Insert entry to lec_arp_table
1475 * LANE2: Add to the end of the list to satisfy 8.1.13
1476 */
1477static inline void
1478lec_arp_add(struct lec_priv *priv, struct lec_arp_table *to_add)
1479{
1480 unsigned short place;
1481 struct lec_arp_table *tmp;
1482
1483 place = HASH(to_add->mac_addr[ETH_ALEN-1]);
1484 tmp = priv->lec_arp_tables[place];
1485 to_add->next = NULL;
1486 if (tmp == NULL)
1487 priv->lec_arp_tables[place] = to_add;
1488
1489 else { /* add to the end */
1490 while (tmp->next)
1491 tmp = tmp->next;
1492 tmp->next = to_add;
1493 }
1494
1495 DPRINTK("LEC_ARP: Added entry:%2.2x %2.2x %2.2x %2.2x %2.2x %2.2x\n",
1496 0xff&to_add->mac_addr[0], 0xff&to_add->mac_addr[1],
1497 0xff&to_add->mac_addr[2], 0xff&to_add->mac_addr[3],
1498 0xff&to_add->mac_addr[4], 0xff&to_add->mac_addr[5]);
1499}
1500
1501/*
1502 * Remove entry from lec_arp_table
1503 */
1504static int
1505lec_arp_remove(struct lec_priv *priv,
1506 struct lec_arp_table *to_remove)
1507{
1508 unsigned short place;
1509 struct lec_arp_table *tmp;
1510 int remove_vcc=1;
1511
1512 if (!to_remove) {
1513 return -1;
1514 }
1515 place = HASH(to_remove->mac_addr[ETH_ALEN-1]);
1516 tmp = priv->lec_arp_tables[place];
1517 if (tmp == to_remove) {
1518 priv->lec_arp_tables[place] = tmp->next;
1519 } else {
1520 while(tmp && tmp->next != to_remove) {
1521 tmp = tmp->next;
1522 }
1523 if (!tmp) {/* Entry was not found */
1524 return -1;
1525 }
1526 }
1527 tmp->next = to_remove->next;
1528 del_timer(&to_remove->timer);
1529
1530 /* If this is the only MAC connected to this VCC, also tear down
1531 the VCC */
1532 if (to_remove->status >= ESI_FLUSH_PENDING) {
1533 /*
1534 * ESI_FLUSH_PENDING, ESI_FORWARD_DIRECT
1535 */
1536 for(place = 0; place < LEC_ARP_TABLE_SIZE; place++) {
1537 for(tmp = priv->lec_arp_tables[place]; tmp != NULL; tmp = tmp->next) {
1538 if (memcmp(tmp->atm_addr, to_remove->atm_addr,
1539 ATM_ESA_LEN)==0) {
1540 remove_vcc=0;
1541 break;
1542 }
1543 }
1544 }
1545 if (remove_vcc)
1546 lec_arp_clear_vccs(to_remove);
1547 }
1548 skb_queue_purge(&to_remove->tx_wait); /* FIXME: good place for this? */
1549
1550 DPRINTK("LEC_ARP: Removed entry:%2.2x %2.2x %2.2x %2.2x %2.2x %2.2x\n",
1551 0xff&to_remove->mac_addr[0], 0xff&to_remove->mac_addr[1],
1552 0xff&to_remove->mac_addr[2], 0xff&to_remove->mac_addr[3],
1553 0xff&to_remove->mac_addr[4], 0xff&to_remove->mac_addr[5]);
1554 return 0;
1555}
1556
1557#if DEBUG_ARP_TABLE
1558static char*
1559get_status_string(unsigned char st)
1560{
1561 switch(st) {
1562 case ESI_UNKNOWN:
1563 return "ESI_UNKNOWN";
1564 case ESI_ARP_PENDING:
1565 return "ESI_ARP_PENDING";
1566 case ESI_VC_PENDING:
1567 return "ESI_VC_PENDING";
1568 case ESI_FLUSH_PENDING:
1569 return "ESI_FLUSH_PENDING";
1570 case ESI_FORWARD_DIRECT:
1571 return "ESI_FORWARD_DIRECT";
1572 default:
1573 return "<UNKNOWN>";
1574 }
1575}
1576#endif
1577
1578static void
1579dump_arp_table(struct lec_priv *priv)
1580{
1581#if DEBUG_ARP_TABLE
1582 int i,j, offset;
1583 struct lec_arp_table *rulla;
1584 char buf[1024];
1585 struct lec_arp_table **lec_arp_tables =
1586 (struct lec_arp_table **)priv->lec_arp_tables;
1587 struct lec_arp_table *lec_arp_empty_ones =
1588 (struct lec_arp_table *)priv->lec_arp_empty_ones;
1589 struct lec_arp_table *lec_no_forward =
1590 (struct lec_arp_table *)priv->lec_no_forward;
1591 struct lec_arp_table *mcast_fwds = priv->mcast_fwds;
1592
1593
1594 printk("Dump %p:\n",priv);
1595 for (i=0;i<LEC_ARP_TABLE_SIZE;i++) {
1596 rulla = lec_arp_tables[i];
1597 offset = 0;
1598 offset += sprintf(buf,"%d: %p\n",i, rulla);
1599 while (rulla) {
1600 offset += sprintf(buf+offset,"Mac:");
1601 for(j=0;j<ETH_ALEN;j++) {
1602 offset+=sprintf(buf+offset,
1603 "%2.2x ",
1604 rulla->mac_addr[j]&0xff);
1605 }
1606 offset +=sprintf(buf+offset,"Atm:");
1607 for(j=0;j<ATM_ESA_LEN;j++) {
1608 offset+=sprintf(buf+offset,
1609 "%2.2x ",
1610 rulla->atm_addr[j]&0xff);
1611 }
1612 offset+=sprintf(buf+offset,
1613 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ",
1614 rulla->vcc?rulla->vcc->vpi:0,
1615 rulla->vcc?rulla->vcc->vci:0,
1616 rulla->recv_vcc?rulla->recv_vcc->vpi:0,
1617 rulla->recv_vcc?rulla->recv_vcc->vci:0,
1618 rulla->last_used,
1619 rulla->timestamp, rulla->no_tries);
1620 offset+=sprintf(buf+offset,
1621 "Flags:%x, Packets_flooded:%x, Status: %s ",
1622 rulla->flags, rulla->packets_flooded,
1623 get_status_string(rulla->status));
1624 offset+=sprintf(buf+offset,"->%p\n",rulla->next);
1625 rulla = rulla->next;
1626 }
1627 printk("%s",buf);
1628 }
1629 rulla = lec_no_forward;
1630 if (rulla)
1631 printk("No forward\n");
1632 while(rulla) {
1633 offset=0;
1634 offset += sprintf(buf+offset,"Mac:");
1635 for(j=0;j<ETH_ALEN;j++) {
1636 offset+=sprintf(buf+offset,"%2.2x ",
1637 rulla->mac_addr[j]&0xff);
1638 }
1639 offset +=sprintf(buf+offset,"Atm:");
1640 for(j=0;j<ATM_ESA_LEN;j++) {
1641 offset+=sprintf(buf+offset,"%2.2x ",
1642 rulla->atm_addr[j]&0xff);
1643 }
1644 offset+=sprintf(buf+offset,
1645 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ",
1646 rulla->vcc?rulla->vcc->vpi:0,
1647 rulla->vcc?rulla->vcc->vci:0,
1648 rulla->recv_vcc?rulla->recv_vcc->vpi:0,
1649 rulla->recv_vcc?rulla->recv_vcc->vci:0,
1650 rulla->last_used,
1651 rulla->timestamp, rulla->no_tries);
1652 offset+=sprintf(buf+offset,
1653 "Flags:%x, Packets_flooded:%x, Status: %s ",
1654 rulla->flags, rulla->packets_flooded,
1655 get_status_string(rulla->status));
1656 offset+=sprintf(buf+offset,"->%lx\n",(long)rulla->next);
1657 rulla = rulla->next;
1658 printk("%s",buf);
1659 }
1660 rulla = lec_arp_empty_ones;
1661 if (rulla)
1662 printk("Empty ones\n");
1663 while(rulla) {
1664 offset=0;
1665 offset += sprintf(buf+offset,"Mac:");
1666 for(j=0;j<ETH_ALEN;j++) {
1667 offset+=sprintf(buf+offset,"%2.2x ",
1668 rulla->mac_addr[j]&0xff);
1669 }
1670 offset +=sprintf(buf+offset,"Atm:");
1671 for(j=0;j<ATM_ESA_LEN;j++) {
1672 offset+=sprintf(buf+offset,"%2.2x ",
1673 rulla->atm_addr[j]&0xff);
1674 }
1675 offset+=sprintf(buf+offset,
1676 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ",
1677 rulla->vcc?rulla->vcc->vpi:0,
1678 rulla->vcc?rulla->vcc->vci:0,
1679 rulla->recv_vcc?rulla->recv_vcc->vpi:0,
1680 rulla->recv_vcc?rulla->recv_vcc->vci:0,
1681 rulla->last_used,
1682 rulla->timestamp, rulla->no_tries);
1683 offset+=sprintf(buf+offset,
1684 "Flags:%x, Packets_flooded:%x, Status: %s ",
1685 rulla->flags, rulla->packets_flooded,
1686 get_status_string(rulla->status));
1687 offset+=sprintf(buf+offset,"->%lx\n",(long)rulla->next);
1688 rulla = rulla->next;
1689 printk("%s",buf);
1690 }
1691
1692 rulla = mcast_fwds;
1693 if (rulla)
1694 printk("Multicast Forward VCCs\n");
1695 while(rulla) {
1696 offset=0;
1697 offset += sprintf(buf+offset,"Mac:");
1698 for(j=0;j<ETH_ALEN;j++) {
1699 offset+=sprintf(buf+offset,"%2.2x ",
1700 rulla->mac_addr[j]&0xff);
1701 }
1702 offset +=sprintf(buf+offset,"Atm:");
1703 for(j=0;j<ATM_ESA_LEN;j++) {
1704 offset+=sprintf(buf+offset,"%2.2x ",
1705 rulla->atm_addr[j]&0xff);
1706 }
1707 offset+=sprintf(buf+offset,
1708 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ",
1709 rulla->vcc?rulla->vcc->vpi:0,
1710 rulla->vcc?rulla->vcc->vci:0,
1711 rulla->recv_vcc?rulla->recv_vcc->vpi:0,
1712 rulla->recv_vcc?rulla->recv_vcc->vci:0,
1713 rulla->last_used,
1714 rulla->timestamp, rulla->no_tries);
1715 offset+=sprintf(buf+offset,
1716 "Flags:%x, Packets_flooded:%x, Status: %s ",
1717 rulla->flags, rulla->packets_flooded,
1718 get_status_string(rulla->status));
1719 offset+=sprintf(buf+offset,"->%lx\n",(long)rulla->next);
1720 rulla = rulla->next;
1721 printk("%s",buf);
1722 }
1723
1724#endif
1725}
1726
1727/*
1728 * Destruction of arp-cache
1729 */
1730static void
1731lec_arp_destroy(struct lec_priv *priv)
1732{
1733 unsigned long flags;
1734 struct lec_arp_table *entry, *next;
1735 int i;
1736
1737 del_timer_sync(&priv->lec_arp_timer);
1738
1739 /*
1740 * Remove all entries
1741 */
1742
1743 spin_lock_irqsave(&priv->lec_arp_lock, flags);
1744 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
1745 for(entry = priv->lec_arp_tables[i]; entry != NULL; entry=next) {
1746 next = entry->next;
1747 lec_arp_remove(priv, entry);
1748 kfree(entry);
1749 }
1750 }
1751 entry = priv->lec_arp_empty_ones;
1752 while(entry) {
1753 next = entry->next;
1754 del_timer_sync(&entry->timer);
1755 lec_arp_clear_vccs(entry);
1756 kfree(entry);
1757 entry = next;
1758 }
1759 priv->lec_arp_empty_ones = NULL;
1760 entry = priv->lec_no_forward;
1761 while(entry) {
1762 next = entry->next;
1763 del_timer_sync(&entry->timer);
1764 lec_arp_clear_vccs(entry);
1765 kfree(entry);
1766 entry = next;
1767 }
1768 priv->lec_no_forward = NULL;
1769 entry = priv->mcast_fwds;
1770 while(entry) {
1771 next = entry->next;
1772 /* No timer, LANEv2 7.1.20 and 2.3.5.3 */
1773 lec_arp_clear_vccs(entry);
1774 kfree(entry);
1775 entry = next;
1776 }
1777 priv->mcast_fwds = NULL;
1778 priv->mcast_vcc = NULL;
1779 memset(priv->lec_arp_tables, 0,
1780 sizeof(struct lec_arp_table *) * LEC_ARP_TABLE_SIZE);
1781 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
1782}
1783
1784
1785/*
1786 * Find entry by mac_address
1787 */
1788static struct lec_arp_table*
1789lec_arp_find(struct lec_priv *priv,
1790 unsigned char *mac_addr)
1791{
1792 unsigned short place;
1793 struct lec_arp_table *to_return;
1794
1795 DPRINTK("LEC_ARP: lec_arp_find :%2.2x %2.2x %2.2x %2.2x %2.2x %2.2x\n",
1796 mac_addr[0]&0xff, mac_addr[1]&0xff, mac_addr[2]&0xff,
1797 mac_addr[3]&0xff, mac_addr[4]&0xff, mac_addr[5]&0xff);
1798 place = HASH(mac_addr[ETH_ALEN-1]);
1799
1800 to_return = priv->lec_arp_tables[place];
1801 while(to_return) {
d3f4a687 1802 if (!compare_ether_addr(mac_addr, to_return->mac_addr)) {
1da177e4
LT
1803 return to_return;
1804 }
1805 to_return = to_return->next;
1806 }
1807 return NULL;
1808}
1809
1810static struct lec_arp_table*
1811make_entry(struct lec_priv *priv, unsigned char *mac_addr)
1812{
1813 struct lec_arp_table *to_return;
1814
8b3a7005 1815 to_return = kmalloc(sizeof(struct lec_arp_table), GFP_ATOMIC);
1da177e4
LT
1816 if (!to_return) {
1817 printk("LEC: Arp entry kmalloc failed\n");
1818 return NULL;
1819 }
1820 memset(to_return, 0, sizeof(struct lec_arp_table));
1821 memcpy(to_return->mac_addr, mac_addr, ETH_ALEN);
1822 init_timer(&to_return->timer);
1823 to_return->timer.function = lec_arp_expire_arp;
1824 to_return->timer.data = (unsigned long) to_return;
1825 to_return->last_used = jiffies;
1826 to_return->priv = priv;
1827 skb_queue_head_init(&to_return->tx_wait);
1828 return to_return;
1829}
1830
1831/*
1832 *
1833 * Arp sent timer expired
1834 *
1835 */
1836static void
1837lec_arp_expire_arp(unsigned long data)
1838{
1839 struct lec_arp_table *entry;
1840
1841 entry = (struct lec_arp_table *)data;
1842
1843 DPRINTK("lec_arp_expire_arp\n");
1844 if (entry->status == ESI_ARP_PENDING) {
1845 if (entry->no_tries <= entry->priv->max_retry_count) {
1846 if (entry->is_rdesc)
1847 send_to_lecd(entry->priv, l_rdesc_arp_xmt, entry->mac_addr, NULL, NULL);
1848 else
1849 send_to_lecd(entry->priv, l_arp_xmt, entry->mac_addr, NULL, NULL);
1850 entry->no_tries++;
1851 }
1852 mod_timer(&entry->timer, jiffies + (1*HZ));
1853 }
1854}
1855
1856/*
1857 *
1858 * Unknown/unused vcc expire, remove associated entry
1859 *
1860 */
1861static void
1862lec_arp_expire_vcc(unsigned long data)
1863{
1864 unsigned long flags;
1865 struct lec_arp_table *to_remove = (struct lec_arp_table*)data;
1866 struct lec_priv *priv = (struct lec_priv *)to_remove->priv;
1867 struct lec_arp_table *entry = NULL;
1868
1869 del_timer(&to_remove->timer);
1870
1871 DPRINTK("LEC_ARP %p %p: lec_arp_expire_vcc vpi:%d vci:%d\n",
1872 to_remove, priv,
1873 to_remove->vcc?to_remove->recv_vcc->vpi:0,
1874 to_remove->vcc?to_remove->recv_vcc->vci:0);
1875 DPRINTK("eo:%p nf:%p\n",priv->lec_arp_empty_ones,priv->lec_no_forward);
1876
1877 spin_lock_irqsave(&priv->lec_arp_lock, flags);
1878 if (to_remove == priv->lec_arp_empty_ones)
1879 priv->lec_arp_empty_ones = to_remove->next;
1880 else {
1881 entry = priv->lec_arp_empty_ones;
1882 while (entry && entry->next != to_remove)
1883 entry = entry->next;
1884 if (entry)
1885 entry->next = to_remove->next;
1886 }
1887 if (!entry) {
1888 if (to_remove == priv->lec_no_forward) {
1889 priv->lec_no_forward = to_remove->next;
1890 } else {
1891 entry = priv->lec_no_forward;
1892 while (entry && entry->next != to_remove)
1893 entry = entry->next;
1894 if (entry)
1895 entry->next = to_remove->next;
1896 }
1897 }
1898 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
1899
1900 lec_arp_clear_vccs(to_remove);
1901 kfree(to_remove);
1902}
1903
1904/*
1905 * Expire entries.
1906 * 1. Re-set timer
1907 * 2. For each entry, delete entries that have aged past the age limit.
1908 * 3. For each entry, depending on the status of the entry, perform
1909 * the following maintenance.
1910 * a. If status is ESI_VC_PENDING or ESI_ARP_PENDING then if the
1911 * tick_count is above the max_unknown_frame_time, clear
1912 * the tick_count to zero and clear the packets_flooded counter
1913 * to zero. This supports the packet rate limit per address
1914 * while flooding unknowns.
1915 * b. If the status is ESI_FLUSH_PENDING and the tick_count is greater
1916 * than or equal to the path_switching_delay, change the status
1917 * to ESI_FORWARD_DIRECT. This causes the flush period to end
1918 * regardless of the progress of the flush protocol.
1919 */
1920static void
1921lec_arp_check_expire(unsigned long data)
1922{
1923 unsigned long flags;
1924 struct lec_priv *priv = (struct lec_priv *)data;
1925 struct lec_arp_table *entry, *next;
1926 unsigned long now;
1927 unsigned long time_to_check;
1928 int i;
1929
1930 DPRINTK("lec_arp_check_expire %p\n",priv);
1931 DPRINTK("expire: eo:%p nf:%p\n",priv->lec_arp_empty_ones,
1932 priv->lec_no_forward);
1933 now = jiffies;
1934 spin_lock_irqsave(&priv->lec_arp_lock, flags);
1935 for(i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
1936 for(entry = priv->lec_arp_tables[i]; entry != NULL; ) {
1937 if ((entry->flags) & LEC_REMOTE_FLAG &&
1938 priv->topology_change)
1939 time_to_check = priv->forward_delay_time;
1940 else
1941 time_to_check = priv->aging_time;
1942
1943 DPRINTK("About to expire: %lx - %lx > %lx\n",
1944 now,entry->last_used, time_to_check);
1945 if( time_after(now, entry->last_used+
1946 time_to_check) &&
1947 !(entry->flags & LEC_PERMANENT_FLAG) &&
1948 !(entry->mac_addr[0] & 0x01) ) { /* LANE2: 7.1.20 */
1949 /* Remove entry */
1950 DPRINTK("LEC:Entry timed out\n");
1951 next = entry->next;
1952 lec_arp_remove(priv, entry);
1953 kfree(entry);
1954 entry = next;
1955 } else {
1956 /* Something else */
1957 if ((entry->status == ESI_VC_PENDING ||
1958 entry->status == ESI_ARP_PENDING)
1959 && time_after_eq(now,
1960 entry->timestamp +
1961 priv->max_unknown_frame_time)) {
1962 entry->timestamp = jiffies;
1963 entry->packets_flooded = 0;
1964 if (entry->status == ESI_VC_PENDING)
1965 send_to_lecd(priv, l_svc_setup, entry->mac_addr, entry->atm_addr, NULL);
1966 }
1967 if (entry->status == ESI_FLUSH_PENDING
1968 &&
1969 time_after_eq(now, entry->timestamp+
1970 priv->path_switching_delay)) {
1971 struct sk_buff *skb;
1972
1973 while ((skb = skb_dequeue(&entry->tx_wait)) != NULL)
1974 lec_send(entry->vcc, skb, entry->priv);
1975 entry->last_used = jiffies;
1976 entry->status =
1977 ESI_FORWARD_DIRECT;
1978 }
1979 entry = entry->next;
1980 }
1981 }
1982 }
1983 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
1984
1985 mod_timer(&priv->lec_arp_timer, jiffies + LEC_ARP_REFRESH_INTERVAL);
1986}
1987/*
1988 * Try to find vcc where mac_address is attached.
1989 *
1990 */
1991static struct atm_vcc*
1992lec_arp_resolve(struct lec_priv *priv, unsigned char *mac_to_find,
1993 int is_rdesc, struct lec_arp_table **ret_entry)
1994{
1995 unsigned long flags;
1996 struct lec_arp_table *entry;
1997 struct atm_vcc *found;
1998
1999 if (mac_to_find[0] & 0x01) {
2000 switch (priv->lane_version) {
2001 case 1:
2002 return priv->mcast_vcc;
2003 break;
2004 case 2: /* LANE2 wants arp for multicast addresses */
d3f4a687 2005 if (!compare_ether_addr(mac_to_find, bus_mac))
1da177e4
LT
2006 return priv->mcast_vcc;
2007 break;
2008 default:
2009 break;
2010 }
2011 }
2012
2013 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2014 entry = lec_arp_find(priv, mac_to_find);
2015
2016 if (entry) {
2017 if (entry->status == ESI_FORWARD_DIRECT) {
2018 /* Connection Ok */
2019 entry->last_used = jiffies;
2020 *ret_entry = entry;
2021 found = entry->vcc;
2022 goto out;
2023 }
75b895c1
ST
2024 /* If the LE_ARP cache entry is still pending, reset count to 0
2025 * so another LE_ARP request can be made for this frame.
2026 */
2027 if (entry->status == ESI_ARP_PENDING) {
2028 entry->no_tries = 0;
2029 }
1da177e4
LT
2030 /* Data direct VC not yet set up, check to see if the unknown
2031 frame count is greater than the limit. If the limit has
2032 not been reached, allow the caller to send packet to
2033 BUS. */
2034 if (entry->status != ESI_FLUSH_PENDING &&
2035 entry->packets_flooded<priv->maximum_unknown_frame_count) {
2036 entry->packets_flooded++;
2037 DPRINTK("LEC_ARP: Flooding..\n");
2038 found = priv->mcast_vcc;
2039 goto out;
2040 }
2041 /* We got here because entry->status == ESI_FLUSH_PENDING
2042 * or BUS flood limit was reached for an entry which is
2043 * in ESI_ARP_PENDING or ESI_VC_PENDING state.
2044 */
2045 *ret_entry = entry;
2046 DPRINTK("lec: entry->status %d entry->vcc %p\n", entry->status, entry->vcc);
2047 found = NULL;
2048 } else {
2049 /* No matching entry was found */
2050 entry = make_entry(priv, mac_to_find);
2051 DPRINTK("LEC_ARP: Making entry\n");
2052 if (!entry) {
2053 found = priv->mcast_vcc;
2054 goto out;
2055 }
2056 lec_arp_add(priv, entry);
2057 /* We want arp-request(s) to be sent */
2058 entry->packets_flooded =1;
2059 entry->status = ESI_ARP_PENDING;
2060 entry->no_tries = 1;
2061 entry->last_used = entry->timestamp = jiffies;
2062 entry->is_rdesc = is_rdesc;
2063 if (entry->is_rdesc)
2064 send_to_lecd(priv, l_rdesc_arp_xmt, mac_to_find, NULL, NULL);
2065 else
2066 send_to_lecd(priv, l_arp_xmt, mac_to_find, NULL, NULL);
2067 entry->timer.expires = jiffies + (1*HZ);
2068 entry->timer.function = lec_arp_expire_arp;
2069 add_timer(&entry->timer);
2070 found = priv->mcast_vcc;
2071 }
2072
2073out:
2074 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2075 return found;
2076}
2077
2078static int
2079lec_addr_delete(struct lec_priv *priv, unsigned char *atm_addr,
2080 unsigned long permanent)
2081{
2082 unsigned long flags;
2083 struct lec_arp_table *entry, *next;
2084 int i;
2085
2086 DPRINTK("lec_addr_delete\n");
2087 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2088 for(i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
2089 for(entry = priv->lec_arp_tables[i]; entry != NULL; entry = next) {
2090 next = entry->next;
2091 if (!memcmp(atm_addr, entry->atm_addr, ATM_ESA_LEN)
2092 && (permanent ||
2093 !(entry->flags & LEC_PERMANENT_FLAG))) {
2094 lec_arp_remove(priv, entry);
2095 kfree(entry);
2096 }
2097 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2098 return 0;
2099 }
2100 }
2101 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2102 return -1;
2103}
2104
2105/*
2106 * Notifies: Response to arp_request (atm_addr != NULL)
2107 */
2108static void
2109lec_arp_update(struct lec_priv *priv, unsigned char *mac_addr,
2110 unsigned char *atm_addr, unsigned long remoteflag,
2111 unsigned int targetless_le_arp)
2112{
2113 unsigned long flags;
2114 struct lec_arp_table *entry, *tmp;
2115 int i;
2116
2117 DPRINTK("lec:%s", (targetless_le_arp) ? "targetless ": " ");
2118 DPRINTK("lec_arp_update mac:%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x\n",
2119 mac_addr[0],mac_addr[1],mac_addr[2],mac_addr[3],
2120 mac_addr[4],mac_addr[5]);
2121
2122 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2123 entry = lec_arp_find(priv, mac_addr);
2124 if (entry == NULL && targetless_le_arp)
2125 goto out; /* LANE2: ignore targetless LE_ARPs for which
2126 * we have no entry in the cache. 7.1.30
2127 */
2128 if (priv->lec_arp_empty_ones) {
2129 entry = priv->lec_arp_empty_ones;
2130 if (!memcmp(entry->atm_addr, atm_addr, ATM_ESA_LEN)) {
2131 priv->lec_arp_empty_ones = entry->next;
2132 } else {
2133 while(entry->next && memcmp(entry->next->atm_addr,
2134 atm_addr, ATM_ESA_LEN))
2135 entry = entry->next;
2136 if (entry->next) {
2137 tmp = entry;
2138 entry = entry->next;
2139 tmp->next = entry->next;
2140 } else
2141 entry = NULL;
2142
2143 }
2144 if (entry) {
2145 del_timer(&entry->timer);
2146 tmp = lec_arp_find(priv, mac_addr);
2147 if (tmp) {
2148 del_timer(&tmp->timer);
2149 tmp->status = ESI_FORWARD_DIRECT;
2150 memcpy(tmp->atm_addr, atm_addr, ATM_ESA_LEN);
2151 tmp->vcc = entry->vcc;
2152 tmp->old_push = entry->old_push;
2153 tmp->last_used = jiffies;
2154 del_timer(&entry->timer);
2155 kfree(entry);
2156 entry=tmp;
2157 } else {
2158 entry->status = ESI_FORWARD_DIRECT;
2159 memcpy(entry->mac_addr, mac_addr, ETH_ALEN);
2160 entry->last_used = jiffies;
2161 lec_arp_add(priv, entry);
2162 }
2163 if (remoteflag)
2164 entry->flags|=LEC_REMOTE_FLAG;
2165 else
2166 entry->flags&=~LEC_REMOTE_FLAG;
2167 DPRINTK("After update\n");
2168 dump_arp_table(priv);
2169 goto out;
2170 }
2171 }
2172 entry = lec_arp_find(priv, mac_addr);
2173 if (!entry) {
2174 entry = make_entry(priv, mac_addr);
2175 if (!entry)
2176 goto out;
2177 entry->status = ESI_UNKNOWN;
2178 lec_arp_add(priv, entry);
2179 /* Temporary, changes before end of function */
2180 }
2181 memcpy(entry->atm_addr, atm_addr, ATM_ESA_LEN);
2182 del_timer(&entry->timer);
2183 for(i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
2184 for(tmp = priv->lec_arp_tables[i]; tmp; tmp=tmp->next) {
2185 if (entry != tmp &&
2186 !memcmp(tmp->atm_addr, atm_addr,
2187 ATM_ESA_LEN)) {
2188 /* Vcc to this host exists */
2189 if (tmp->status > ESI_VC_PENDING) {
2190 /*
2191 * ESI_FLUSH_PENDING,
2192 * ESI_FORWARD_DIRECT
2193 */
2194 entry->vcc = tmp->vcc;
2195 entry->old_push=tmp->old_push;
2196 }
2197 entry->status=tmp->status;
2198 break;
2199 }
2200 }
2201 }
2202 if (remoteflag)
2203 entry->flags|=LEC_REMOTE_FLAG;
2204 else
2205 entry->flags&=~LEC_REMOTE_FLAG;
2206 if (entry->status == ESI_ARP_PENDING ||
2207 entry->status == ESI_UNKNOWN) {
2208 entry->status = ESI_VC_PENDING;
2209 send_to_lecd(priv, l_svc_setup, entry->mac_addr, atm_addr, NULL);
2210 }
2211 DPRINTK("After update2\n");
2212 dump_arp_table(priv);
2213out:
2214 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2215}
2216
2217/*
2218 * Notifies: Vcc setup ready
2219 */
2220static void
2221lec_vcc_added(struct lec_priv *priv, struct atmlec_ioc *ioc_data,
2222 struct atm_vcc *vcc,
2223 void (*old_push)(struct atm_vcc *vcc, struct sk_buff *skb))
2224{
2225 unsigned long flags;
2226 struct lec_arp_table *entry;
2227 int i, found_entry=0;
2228
2229 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2230 if (ioc_data->receive == 2) {
2231 /* Vcc for Multicast Forward. No timer, LANEv2 7.1.20 and 2.3.5.3 */
2232
2233 DPRINTK("LEC_ARP: Attaching mcast forward\n");
2234#if 0
2235 entry = lec_arp_find(priv, bus_mac);
2236 if (!entry) {
2237 printk("LEC_ARP: Multicast entry not found!\n");
2238 goto out;
2239 }
2240 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN);
2241 entry->recv_vcc = vcc;
2242 entry->old_recv_push = old_push;
2243#endif
2244 entry = make_entry(priv, bus_mac);
2245 if (entry == NULL)
2246 goto out;
2247 del_timer(&entry->timer);
2248 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN);
2249 entry->recv_vcc = vcc;
2250 entry->old_recv_push = old_push;
2251 entry->next = priv->mcast_fwds;
2252 priv->mcast_fwds = entry;
2253 goto out;
2254 } else if (ioc_data->receive == 1) {
2255 /* Vcc which we don't want to make default vcc, attach it
2256 anyway. */
2257 DPRINTK("LEC_ARP:Attaching data direct, not default :%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x\n",
2258 ioc_data->atm_addr[0],ioc_data->atm_addr[1],
2259 ioc_data->atm_addr[2],ioc_data->atm_addr[3],
2260 ioc_data->atm_addr[4],ioc_data->atm_addr[5],
2261 ioc_data->atm_addr[6],ioc_data->atm_addr[7],
2262 ioc_data->atm_addr[8],ioc_data->atm_addr[9],
2263 ioc_data->atm_addr[10],ioc_data->atm_addr[11],
2264 ioc_data->atm_addr[12],ioc_data->atm_addr[13],
2265 ioc_data->atm_addr[14],ioc_data->atm_addr[15],
2266 ioc_data->atm_addr[16],ioc_data->atm_addr[17],
2267 ioc_data->atm_addr[18],ioc_data->atm_addr[19]);
2268 entry = make_entry(priv, bus_mac);
2269 if (entry == NULL)
2270 goto out;
2271 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN);
2272 memset(entry->mac_addr, 0, ETH_ALEN);
2273 entry->recv_vcc = vcc;
2274 entry->old_recv_push = old_push;
2275 entry->status = ESI_UNKNOWN;
2276 entry->timer.expires = jiffies + priv->vcc_timeout_period;
2277 entry->timer.function = lec_arp_expire_vcc;
2278 add_timer(&entry->timer);
2279 entry->next = priv->lec_no_forward;
2280 priv->lec_no_forward = entry;
2281 dump_arp_table(priv);
2282 goto out;
2283 }
2284 DPRINTK("LEC_ARP:Attaching data direct, default:%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x\n",
2285 ioc_data->atm_addr[0],ioc_data->atm_addr[1],
2286 ioc_data->atm_addr[2],ioc_data->atm_addr[3],
2287 ioc_data->atm_addr[4],ioc_data->atm_addr[5],
2288 ioc_data->atm_addr[6],ioc_data->atm_addr[7],
2289 ioc_data->atm_addr[8],ioc_data->atm_addr[9],
2290 ioc_data->atm_addr[10],ioc_data->atm_addr[11],
2291 ioc_data->atm_addr[12],ioc_data->atm_addr[13],
2292 ioc_data->atm_addr[14],ioc_data->atm_addr[15],
2293 ioc_data->atm_addr[16],ioc_data->atm_addr[17],
2294 ioc_data->atm_addr[18],ioc_data->atm_addr[19]);
2295 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
2296 for (entry = priv->lec_arp_tables[i]; entry; entry=entry->next) {
2297 if (memcmp(ioc_data->atm_addr, entry->atm_addr,
2298 ATM_ESA_LEN)==0) {
2299 DPRINTK("LEC_ARP: Attaching data direct\n");
2300 DPRINTK("Currently -> Vcc: %d, Rvcc:%d\n",
2301 entry->vcc?entry->vcc->vci:0,
2302 entry->recv_vcc?entry->recv_vcc->vci:0);
2303 found_entry=1;
2304 del_timer(&entry->timer);
2305 entry->vcc = vcc;
2306 entry->old_push = old_push;
2307 if (entry->status == ESI_VC_PENDING) {
2308 if(priv->maximum_unknown_frame_count
2309 ==0)
2310 entry->status =
2311 ESI_FORWARD_DIRECT;
2312 else {
2313 entry->timestamp = jiffies;
2314 entry->status =
2315 ESI_FLUSH_PENDING;
2316#if 0
2317 send_to_lecd(priv,l_flush_xmt,
2318 NULL,
2319 entry->atm_addr,
2320 NULL);
2321#endif
2322 }
2323 } else {
2324 /* They were forming a connection
2325 to us, and we to them. Our
2326 ATM address is numerically lower
2327 than theirs, so we make connection
2328 we formed into default VCC (8.1.11).
2329 Connection they made gets torn
2330 down. This might confuse some
2331 clients. Can be changed if
2332 someone reports trouble... */
2333 ;
2334 }
2335 }
2336 }
2337 }
2338 if (found_entry) {
2339 DPRINTK("After vcc was added\n");
2340 dump_arp_table(priv);
2341 goto out;
2342 }
2343 /* Not found, snatch address from first data packet that arrives from
2344 this vcc */
2345 entry = make_entry(priv, bus_mac);
2346 if (!entry)
2347 goto out;
2348 entry->vcc = vcc;
2349 entry->old_push = old_push;
2350 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN);
2351 memset(entry->mac_addr, 0, ETH_ALEN);
2352 entry->status = ESI_UNKNOWN;
2353 entry->next = priv->lec_arp_empty_ones;
2354 priv->lec_arp_empty_ones = entry;
2355 entry->timer.expires = jiffies + priv->vcc_timeout_period;
2356 entry->timer.function = lec_arp_expire_vcc;
2357 add_timer(&entry->timer);
2358 DPRINTK("After vcc was added\n");
2359 dump_arp_table(priv);
2360out:
2361 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2362}
2363
2364static void
2365lec_flush_complete(struct lec_priv *priv, unsigned long tran_id)
2366{
2367 unsigned long flags;
2368 struct lec_arp_table *entry;
2369 int i;
2370
2371 DPRINTK("LEC:lec_flush_complete %lx\n",tran_id);
2372 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2373 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
2374 for (entry = priv->lec_arp_tables[i]; entry; entry=entry->next) {
2375 if (entry->flush_tran_id == tran_id &&
2376 entry->status == ESI_FLUSH_PENDING) {
2377 struct sk_buff *skb;
2378
2379 while ((skb = skb_dequeue(&entry->tx_wait)) != NULL)
2380 lec_send(entry->vcc, skb, entry->priv);
2381 entry->status = ESI_FORWARD_DIRECT;
2382 DPRINTK("LEC_ARP: Flushed\n");
2383 }
2384 }
2385 }
2386 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2387 dump_arp_table(priv);
2388}
2389
2390static void
2391lec_set_flush_tran_id(struct lec_priv *priv,
2392 unsigned char *atm_addr, unsigned long tran_id)
2393{
2394 unsigned long flags;
2395 struct lec_arp_table *entry;
2396 int i;
2397
2398 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2399 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++)
2400 for(entry = priv->lec_arp_tables[i]; entry; entry=entry->next)
2401 if (!memcmp(atm_addr, entry->atm_addr, ATM_ESA_LEN)) {
2402 entry->flush_tran_id = tran_id;
2403 DPRINTK("Set flush transaction id to %lx for %p\n",tran_id,entry);
2404 }
2405 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2406}
2407
2408static int
2409lec_mcast_make(struct lec_priv *priv, struct atm_vcc *vcc)
2410{
2411 unsigned long flags;
2412 unsigned char mac_addr[] = {
2413 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
2414 struct lec_arp_table *to_add;
2415 struct lec_vcc_priv *vpriv;
2416 int err = 0;
2417
2418 if (!(vpriv = kmalloc(sizeof(struct lec_vcc_priv), GFP_KERNEL)))
2419 return -ENOMEM;
2420 vpriv->xoff = 0;
2421 vpriv->old_pop = vcc->pop;
2422 vcc->user_back = vpriv;
2423 vcc->pop = lec_pop;
2424 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2425 to_add = make_entry(priv, mac_addr);
2426 if (!to_add) {
2427 vcc->pop = vpriv->old_pop;
2428 kfree(vpriv);
2429 err = -ENOMEM;
2430 goto out;
2431 }
2432 memcpy(to_add->atm_addr, vcc->remote.sas_addr.prv, ATM_ESA_LEN);
2433 to_add->status = ESI_FORWARD_DIRECT;
2434 to_add->flags |= LEC_PERMANENT_FLAG;
2435 to_add->vcc = vcc;
2436 to_add->old_push = vcc->push;
2437 vcc->push = lec_push;
2438 priv->mcast_vcc = vcc;
2439 lec_arp_add(priv, to_add);
2440out:
2441 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2442 return err;
2443}
2444
2445static void
2446lec_vcc_close(struct lec_priv *priv, struct atm_vcc *vcc)
2447{
2448 unsigned long flags;
2449 struct lec_arp_table *entry, *next;
2450 int i;
2451
2452 DPRINTK("LEC_ARP: lec_vcc_close vpi:%d vci:%d\n",vcc->vpi,vcc->vci);
2453 dump_arp_table(priv);
2454 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2455 for(i=0;i<LEC_ARP_TABLE_SIZE;i++) {
2456 for(entry = priv->lec_arp_tables[i];entry; entry=next) {
2457 next = entry->next;
2458 if (vcc == entry->vcc) {
2459 lec_arp_remove(priv, entry);
2460 kfree(entry);
2461 if (priv->mcast_vcc == vcc) {
2462 priv->mcast_vcc = NULL;
2463 }
2464 }
2465 }
2466 }
2467
2468 entry = priv->lec_arp_empty_ones;
2469 priv->lec_arp_empty_ones = NULL;
2470 while (entry != NULL) {
2471 next = entry->next;
2472 if (entry->vcc == vcc) { /* leave it out from the list */
2473 lec_arp_clear_vccs(entry);
2474 del_timer(&entry->timer);
2475 kfree(entry);
2476 }
2477 else { /* put it back to the list */
2478 entry->next = priv->lec_arp_empty_ones;
2479 priv->lec_arp_empty_ones = entry;
2480 }
2481 entry = next;
2482 }
2483
2484 entry = priv->lec_no_forward;
2485 priv->lec_no_forward = NULL;
2486 while (entry != NULL) {
2487 next = entry->next;
2488 if (entry->recv_vcc == vcc) {
2489 lec_arp_clear_vccs(entry);
2490 del_timer(&entry->timer);
2491 kfree(entry);
2492 }
2493 else {
2494 entry->next = priv->lec_no_forward;
2495 priv->lec_no_forward = entry;
2496 }
2497 entry = next;
2498 }
2499
2500 entry = priv->mcast_fwds;
2501 priv->mcast_fwds = NULL;
2502 while (entry != NULL) {
2503 next = entry->next;
2504 if (entry->recv_vcc == vcc) {
2505 lec_arp_clear_vccs(entry);
2506 /* No timer, LANEv2 7.1.20 and 2.3.5.3 */
2507 kfree(entry);
2508 }
2509 else {
2510 entry->next = priv->mcast_fwds;
2511 priv->mcast_fwds = entry;
2512 }
2513 entry = next;
2514 }
2515
2516 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2517 dump_arp_table(priv);
2518}
2519
2520static void
2521lec_arp_check_empties(struct lec_priv *priv,
2522 struct atm_vcc *vcc, struct sk_buff *skb)
2523{
2524 unsigned long flags;
2525 struct lec_arp_table *entry, *prev;
2526 struct lecdatahdr_8023 *hdr = (struct lecdatahdr_8023 *)skb->data;
2527 unsigned char *src;
2528#ifdef CONFIG_TR
2529 struct lecdatahdr_8025 *tr_hdr = (struct lecdatahdr_8025 *)skb->data;
2530
2531 if (priv->is_trdev) src = tr_hdr->h_source;
2532 else
2533#endif
2534 src = hdr->h_source;
2535
2536 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2537 entry = priv->lec_arp_empty_ones;
2538 if (vcc == entry->vcc) {
2539 del_timer(&entry->timer);
2540 memcpy(entry->mac_addr, src, ETH_ALEN);
2541 entry->status = ESI_FORWARD_DIRECT;
2542 entry->last_used = jiffies;
2543 priv->lec_arp_empty_ones = entry->next;
2544 /* We might have got an entry */
2545 if ((prev = lec_arp_find(priv,src))) {
2546 lec_arp_remove(priv, prev);
2547 kfree(prev);
2548 }
2549 lec_arp_add(priv, entry);
2550 goto out;
2551 }
2552 prev = entry;
2553 entry = entry->next;
2554 while (entry && entry->vcc != vcc) {
2555 prev= entry;
2556 entry = entry->next;
2557 }
2558 if (!entry) {
2559 DPRINTK("LEC_ARP: Arp_check_empties: entry not found!\n");
2560 goto out;
2561 }
2562 del_timer(&entry->timer);
2563 memcpy(entry->mac_addr, src, ETH_ALEN);
2564 entry->status = ESI_FORWARD_DIRECT;
2565 entry->last_used = jiffies;
2566 prev->next = entry->next;
2567 if ((prev = lec_arp_find(priv, src))) {
2568 lec_arp_remove(priv, prev);
2569 kfree(prev);
2570 }
2571 lec_arp_add(priv, entry);
2572out:
2573 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2574}
2575MODULE_LICENSE("GPL");