aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--net/atm/lec.c1783
1 files changed, 899 insertions, 884 deletions
diff --git a/net/atm/lec.c b/net/atm/lec.c
index 543960c86fa8..d2b44e91badf 100644
--- a/net/atm/lec.c
+++ b/net/atm/lec.c
@@ -1418,7 +1418,6 @@ static void lane2_associate_ind(struct net_device *dev, u8 *mac_addr,
1418 * 1418 *
1419 * lec_arpc.c was added here when making 1419 * lec_arpc.c was added here when making
1420 * lane client modular. October 1997 1420 * lane client modular. October 1997
1421 *
1422 */ 1421 */
1423 1422
1424#include <linux/types.h> 1423#include <linux/types.h>
@@ -1429,7 +1428,6 @@ static void lane2_associate_ind(struct net_device *dev, u8 *mac_addr,
1429#include <linux/inetdevice.h> 1428#include <linux/inetdevice.h>
1430#include <net/route.h> 1429#include <net/route.h>
1431 1430
1432
1433#if 0 1431#if 0
1434#define DPRINTK(format,args...) 1432#define DPRINTK(format,args...)
1435/* 1433/*
@@ -1452,296 +1450,294 @@ static void lec_arp_expire_arp(unsigned long data);
1452/* 1450/*
1453 * Initialization of arp-cache 1451 * Initialization of arp-cache
1454 */ 1452 */
1455static void 1453static void lec_arp_init(struct lec_priv *priv)
1456lec_arp_init(struct lec_priv *priv)
1457{ 1454{
1458 unsigned short i; 1455 unsigned short i;
1459 1456
1460 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) { 1457 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
1461 priv->lec_arp_tables[i] = NULL; 1458 priv->lec_arp_tables[i] = NULL;
1462 } 1459 }
1463 spin_lock_init(&priv->lec_arp_lock); 1460 spin_lock_init(&priv->lec_arp_lock);
1464 init_timer(&priv->lec_arp_timer); 1461 init_timer(&priv->lec_arp_timer);
1465 priv->lec_arp_timer.expires = jiffies + LEC_ARP_REFRESH_INTERVAL; 1462 priv->lec_arp_timer.expires = jiffies + LEC_ARP_REFRESH_INTERVAL;
1466 priv->lec_arp_timer.data = (unsigned long)priv; 1463 priv->lec_arp_timer.data = (unsigned long)priv;
1467 priv->lec_arp_timer.function = lec_arp_check_expire; 1464 priv->lec_arp_timer.function = lec_arp_check_expire;
1468 add_timer(&priv->lec_arp_timer); 1465 add_timer(&priv->lec_arp_timer);
1469} 1466}
1470 1467
1471static void 1468static void lec_arp_clear_vccs(struct lec_arp_table *entry)
1472lec_arp_clear_vccs(struct lec_arp_table *entry)
1473{ 1469{
1474 if (entry->vcc) { 1470 if (entry->vcc) {
1475 struct atm_vcc *vcc = entry->vcc; 1471 struct atm_vcc *vcc = entry->vcc;
1476 struct lec_vcc_priv *vpriv = LEC_VCC_PRIV(vcc); 1472 struct lec_vcc_priv *vpriv = LEC_VCC_PRIV(vcc);
1477 struct net_device *dev = (struct net_device*) vcc->proto_data; 1473 struct net_device *dev = (struct net_device *)vcc->proto_data;
1478 1474
1479 vcc->pop = vpriv->old_pop; 1475 vcc->pop = vpriv->old_pop;
1480 if (vpriv->xoff) 1476 if (vpriv->xoff)
1481 netif_wake_queue(dev); 1477 netif_wake_queue(dev);
1482 kfree(vpriv); 1478 kfree(vpriv);
1483 vcc->user_back = NULL; 1479 vcc->user_back = NULL;
1484 vcc->push = entry->old_push; 1480 vcc->push = entry->old_push;
1485 vcc_release_async(vcc, -EPIPE); 1481 vcc_release_async(vcc, -EPIPE);
1486 vcc = NULL; 1482 vcc = NULL;
1487 } 1483 }
1488 if (entry->recv_vcc) { 1484 if (entry->recv_vcc) {
1489 entry->recv_vcc->push = entry->old_recv_push; 1485 entry->recv_vcc->push = entry->old_recv_push;
1490 vcc_release_async(entry->recv_vcc, -EPIPE); 1486 vcc_release_async(entry->recv_vcc, -EPIPE);
1491 entry->recv_vcc = NULL; 1487 entry->recv_vcc = NULL;
1492 } 1488 }
1493} 1489}
1494 1490
1495/* 1491/*
1496 * Insert entry to lec_arp_table 1492 * Insert entry to lec_arp_table
1497 * LANE2: Add to the end of the list to satisfy 8.1.13 1493 * LANE2: Add to the end of the list to satisfy 8.1.13
1498 */ 1494 */
1499static inline void 1495static inline void
1500lec_arp_add(struct lec_priv *priv, struct lec_arp_table *to_add) 1496lec_arp_add(struct lec_priv *priv, struct lec_arp_table *to_add)
1501{ 1497{
1502 unsigned short place; 1498 unsigned short place;
1503 struct lec_arp_table *tmp; 1499 struct lec_arp_table *tmp;
1504 1500
1505 place = HASH(to_add->mac_addr[ETH_ALEN-1]); 1501 place = HASH(to_add->mac_addr[ETH_ALEN - 1]);
1506 tmp = priv->lec_arp_tables[place]; 1502 tmp = priv->lec_arp_tables[place];
1507 to_add->next = NULL; 1503 to_add->next = NULL;
1508 if (tmp == NULL) 1504 if (tmp == NULL)
1509 priv->lec_arp_tables[place] = to_add; 1505 priv->lec_arp_tables[place] = to_add;
1510 1506
1511 else { /* add to the end */ 1507 else { /* add to the end */
1512 while (tmp->next) 1508 while (tmp->next)
1513 tmp = tmp->next; 1509 tmp = tmp->next;
1514 tmp->next = to_add; 1510 tmp->next = to_add;
1515 } 1511 }
1516 1512
1517 DPRINTK("LEC_ARP: Added entry:%2.2x %2.2x %2.2x %2.2x %2.2x %2.2x\n", 1513 DPRINTK("LEC_ARP: Added entry:%2.2x %2.2x %2.2x %2.2x %2.2x %2.2x\n",
1518 0xff&to_add->mac_addr[0], 0xff&to_add->mac_addr[1], 1514 0xff & to_add->mac_addr[0], 0xff & to_add->mac_addr[1],
1519 0xff&to_add->mac_addr[2], 0xff&to_add->mac_addr[3], 1515 0xff & to_add->mac_addr[2], 0xff & to_add->mac_addr[3],
1520 0xff&to_add->mac_addr[4], 0xff&to_add->mac_addr[5]); 1516 0xff & to_add->mac_addr[4], 0xff & to_add->mac_addr[5]);
1521} 1517}
1522 1518
1523/* 1519/*
1524 * Remove entry from lec_arp_table 1520 * Remove entry from lec_arp_table
1525 */ 1521 */
1526static int 1522static int
1527lec_arp_remove(struct lec_priv *priv, 1523lec_arp_remove(struct lec_priv *priv, struct lec_arp_table *to_remove)
1528 struct lec_arp_table *to_remove)
1529{ 1524{
1530 unsigned short place; 1525 unsigned short place;
1531 struct lec_arp_table *tmp; 1526 struct lec_arp_table *tmp;
1532 int remove_vcc=1; 1527 int remove_vcc = 1;
1533 1528
1534 if (!to_remove) { 1529 if (!to_remove) {
1535 return -1; 1530 return -1;
1536 } 1531 }
1537 place = HASH(to_remove->mac_addr[ETH_ALEN-1]); 1532 place = HASH(to_remove->mac_addr[ETH_ALEN - 1]);
1538 tmp = priv->lec_arp_tables[place]; 1533 tmp = priv->lec_arp_tables[place];
1539 if (tmp == to_remove) { 1534 if (tmp == to_remove) {
1540 priv->lec_arp_tables[place] = tmp->next; 1535 priv->lec_arp_tables[place] = tmp->next;
1541 } else { 1536 } else {
1542 while(tmp && tmp->next != to_remove) { 1537 while (tmp && tmp->next != to_remove) {
1543 tmp = tmp->next; 1538 tmp = tmp->next;
1544 } 1539 }
1545 if (!tmp) {/* Entry was not found */ 1540 if (!tmp) { /* Entry was not found */
1546 return -1; 1541 return -1;
1547 } 1542 }
1548 } 1543 }
1549 tmp->next = to_remove->next; 1544 tmp->next = to_remove->next;
1550 del_timer(&to_remove->timer); 1545 del_timer(&to_remove->timer);
1551 1546
1552 /* If this is the only MAC connected to this VCC, also tear down 1547 /* If this is the only MAC connected to this VCC, also tear down
1553 the VCC */ 1548 the VCC */
1554 if (to_remove->status >= ESI_FLUSH_PENDING) { 1549 if (to_remove->status >= ESI_FLUSH_PENDING) {
1555 /* 1550 /*
1556 * ESI_FLUSH_PENDING, ESI_FORWARD_DIRECT 1551 * ESI_FLUSH_PENDING, ESI_FORWARD_DIRECT
1557 */ 1552 */
1558 for(place = 0; place < LEC_ARP_TABLE_SIZE; place++) { 1553 for (place = 0; place < LEC_ARP_TABLE_SIZE; place++) {
1559 for(tmp = priv->lec_arp_tables[place]; tmp != NULL; tmp = tmp->next) { 1554 for (tmp = priv->lec_arp_tables[place]; tmp != NULL;
1560 if (memcmp(tmp->atm_addr, to_remove->atm_addr, 1555 tmp = tmp->next) {
1561 ATM_ESA_LEN)==0) { 1556 if (memcmp
1562 remove_vcc=0; 1557 (tmp->atm_addr, to_remove->atm_addr,
1563 break; 1558 ATM_ESA_LEN) == 0) {
1564 } 1559 remove_vcc = 0;
1565 } 1560 break;
1566 } 1561 }
1567 if (remove_vcc) 1562 }
1568 lec_arp_clear_vccs(to_remove); 1563 }
1569 } 1564 if (remove_vcc)
1570 skb_queue_purge(&to_remove->tx_wait); /* FIXME: good place for this? */ 1565 lec_arp_clear_vccs(to_remove);
1571 1566 }
1572 DPRINTK("LEC_ARP: Removed entry:%2.2x %2.2x %2.2x %2.2x %2.2x %2.2x\n", 1567 skb_queue_purge(&to_remove->tx_wait); /* FIXME: good place for this? */
1573 0xff&to_remove->mac_addr[0], 0xff&to_remove->mac_addr[1], 1568
1574 0xff&to_remove->mac_addr[2], 0xff&to_remove->mac_addr[3], 1569 DPRINTK("LEC_ARP: Removed entry:%2.2x %2.2x %2.2x %2.2x %2.2x %2.2x\n",
1575 0xff&to_remove->mac_addr[4], 0xff&to_remove->mac_addr[5]); 1570 0xff & to_remove->mac_addr[0], 0xff & to_remove->mac_addr[1],
1576 return 0; 1571 0xff & to_remove->mac_addr[2], 0xff & to_remove->mac_addr[3],
1572 0xff & to_remove->mac_addr[4], 0xff & to_remove->mac_addr[5]);
1573 return 0;
1577} 1574}
1578 1575
1579#if DEBUG_ARP_TABLE 1576#if DEBUG_ARP_TABLE
1580static char* 1577static char *get_status_string(unsigned char st)
1581get_status_string(unsigned char st)
1582{ 1578{
1583 switch(st) { 1579 switch (st) {
1584 case ESI_UNKNOWN: 1580 case ESI_UNKNOWN:
1585 return "ESI_UNKNOWN"; 1581 return "ESI_UNKNOWN";
1586 case ESI_ARP_PENDING: 1582 case ESI_ARP_PENDING:
1587 return "ESI_ARP_PENDING"; 1583 return "ESI_ARP_PENDING";
1588 case ESI_VC_PENDING: 1584 case ESI_VC_PENDING:
1589 return "ESI_VC_PENDING"; 1585 return "ESI_VC_PENDING";
1590 case ESI_FLUSH_PENDING: 1586 case ESI_FLUSH_PENDING:
1591 return "ESI_FLUSH_PENDING"; 1587 return "ESI_FLUSH_PENDING";
1592 case ESI_FORWARD_DIRECT: 1588 case ESI_FORWARD_DIRECT:
1593 return "ESI_FORWARD_DIRECT"; 1589 return "ESI_FORWARD_DIRECT";
1594 default: 1590 default:
1595 return "<UNKNOWN>"; 1591 return "<UNKNOWN>";
1596 } 1592 }
1597} 1593}
1598#endif 1594#endif
1599 1595
1600static void 1596static void dump_arp_table(struct lec_priv *priv)
1601dump_arp_table(struct lec_priv *priv)
1602{ 1597{
1603#if DEBUG_ARP_TABLE 1598#if DEBUG_ARP_TABLE
1604 int i,j, offset; 1599 int i, j, offset;
1605 struct lec_arp_table *rulla; 1600 struct lec_arp_table *rulla;
1606 char buf[1024]; 1601 char buf[1024];
1607 struct lec_arp_table **lec_arp_tables = 1602 struct lec_arp_table **lec_arp_tables =
1608 (struct lec_arp_table **)priv->lec_arp_tables; 1603 (struct lec_arp_table **)priv->lec_arp_tables;
1609 struct lec_arp_table *lec_arp_empty_ones = 1604 struct lec_arp_table *lec_arp_empty_ones =
1610 (struct lec_arp_table *)priv->lec_arp_empty_ones; 1605 (struct lec_arp_table *)priv->lec_arp_empty_ones;
1611 struct lec_arp_table *lec_no_forward = 1606 struct lec_arp_table *lec_no_forward =
1612 (struct lec_arp_table *)priv->lec_no_forward; 1607 (struct lec_arp_table *)priv->lec_no_forward;
1613 struct lec_arp_table *mcast_fwds = priv->mcast_fwds; 1608 struct lec_arp_table *mcast_fwds = priv->mcast_fwds;
1614 1609
1615 1610 printk("Dump %p:\n", priv);
1616 printk("Dump %p:\n",priv); 1611 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
1617 for (i=0;i<LEC_ARP_TABLE_SIZE;i++) { 1612 rulla = lec_arp_tables[i];
1618 rulla = lec_arp_tables[i]; 1613 offset = 0;
1619 offset = 0; 1614 offset += sprintf(buf, "%d: %p\n", i, rulla);
1620 offset += sprintf(buf,"%d: %p\n",i, rulla); 1615 while (rulla) {
1621 while (rulla) { 1616 offset += sprintf(buf + offset, "Mac:");
1622 offset += sprintf(buf+offset,"Mac:"); 1617 for (j = 0; j < ETH_ALEN; j++) {
1623 for(j=0;j<ETH_ALEN;j++) { 1618 offset += sprintf(buf + offset,
1624 offset+=sprintf(buf+offset, 1619 "%2.2x ",
1625 "%2.2x ", 1620 rulla->mac_addr[j] & 0xff);
1626 rulla->mac_addr[j]&0xff); 1621 }
1627 } 1622 offset += sprintf(buf + offset, "Atm:");
1628 offset +=sprintf(buf+offset,"Atm:"); 1623 for (j = 0; j < ATM_ESA_LEN; j++) {
1629 for(j=0;j<ATM_ESA_LEN;j++) { 1624 offset += sprintf(buf + offset,
1630 offset+=sprintf(buf+offset, 1625 "%2.2x ",
1631 "%2.2x ", 1626 rulla->atm_addr[j] & 0xff);
1632 rulla->atm_addr[j]&0xff); 1627 }
1633 } 1628 offset += sprintf(buf + offset,
1634 offset+=sprintf(buf+offset, 1629 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ",
1635 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ", 1630 rulla->vcc ? rulla->vcc->vpi : 0,
1636 rulla->vcc?rulla->vcc->vpi:0, 1631 rulla->vcc ? rulla->vcc->vci : 0,
1637 rulla->vcc?rulla->vcc->vci:0, 1632 rulla->recv_vcc ? rulla->recv_vcc->
1638 rulla->recv_vcc?rulla->recv_vcc->vpi:0, 1633 vpi : 0,
1639 rulla->recv_vcc?rulla->recv_vcc->vci:0, 1634 rulla->recv_vcc ? rulla->recv_vcc->
1640 rulla->last_used, 1635 vci : 0, rulla->last_used,
1641 rulla->timestamp, rulla->no_tries); 1636 rulla->timestamp, rulla->no_tries);
1642 offset+=sprintf(buf+offset, 1637 offset +=
1643 "Flags:%x, Packets_flooded:%x, Status: %s ", 1638 sprintf(buf + offset,
1644 rulla->flags, rulla->packets_flooded, 1639 "Flags:%x, Packets_flooded:%x, Status: %s ",
1645 get_status_string(rulla->status)); 1640 rulla->flags, rulla->packets_flooded,
1646 offset+=sprintf(buf+offset,"->%p\n",rulla->next); 1641 get_status_string(rulla->status));
1647 rulla = rulla->next; 1642 offset += sprintf(buf + offset, "->%p\n", rulla->next);
1648 } 1643 rulla = rulla->next;
1649 printk("%s",buf); 1644 }
1650 } 1645 printk("%s", buf);
1651 rulla = lec_no_forward; 1646 }
1652 if (rulla) 1647 rulla = lec_no_forward;
1653 printk("No forward\n"); 1648 if (rulla)
1654 while(rulla) { 1649 printk("No forward\n");
1655 offset=0; 1650 while (rulla) {
1656 offset += sprintf(buf+offset,"Mac:"); 1651 offset = 0;
1657 for(j=0;j<ETH_ALEN;j++) { 1652 offset += sprintf(buf + offset, "Mac:");
1658 offset+=sprintf(buf+offset,"%2.2x ", 1653 for (j = 0; j < ETH_ALEN; j++) {
1659 rulla->mac_addr[j]&0xff); 1654 offset += sprintf(buf + offset, "%2.2x ",
1660 } 1655 rulla->mac_addr[j] & 0xff);
1661 offset +=sprintf(buf+offset,"Atm:"); 1656 }
1662 for(j=0;j<ATM_ESA_LEN;j++) { 1657 offset += sprintf(buf + offset, "Atm:");
1663 offset+=sprintf(buf+offset,"%2.2x ", 1658 for (j = 0; j < ATM_ESA_LEN; j++) {
1664 rulla->atm_addr[j]&0xff); 1659 offset += sprintf(buf + offset, "%2.2x ",
1665 } 1660 rulla->atm_addr[j] & 0xff);
1666 offset+=sprintf(buf+offset, 1661 }
1667 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ", 1662 offset += sprintf(buf + offset,
1668 rulla->vcc?rulla->vcc->vpi:0, 1663 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ",
1669 rulla->vcc?rulla->vcc->vci:0, 1664 rulla->vcc ? rulla->vcc->vpi : 0,
1670 rulla->recv_vcc?rulla->recv_vcc->vpi:0, 1665 rulla->vcc ? rulla->vcc->vci : 0,
1671 rulla->recv_vcc?rulla->recv_vcc->vci:0, 1666 rulla->recv_vcc ? rulla->recv_vcc->vpi : 0,
1672 rulla->last_used, 1667 rulla->recv_vcc ? rulla->recv_vcc->vci : 0,
1673 rulla->timestamp, rulla->no_tries); 1668 rulla->last_used,
1674 offset+=sprintf(buf+offset, 1669 rulla->timestamp, rulla->no_tries);
1675 "Flags:%x, Packets_flooded:%x, Status: %s ", 1670 offset += sprintf(buf + offset,
1676 rulla->flags, rulla->packets_flooded, 1671 "Flags:%x, Packets_flooded:%x, Status: %s ",
1677 get_status_string(rulla->status)); 1672 rulla->flags, rulla->packets_flooded,
1678 offset+=sprintf(buf+offset,"->%lx\n",(long)rulla->next); 1673 get_status_string(rulla->status));
1679 rulla = rulla->next; 1674 offset += sprintf(buf + offset, "->%lx\n", (long)rulla->next);
1680 printk("%s",buf); 1675 rulla = rulla->next;
1681 } 1676 printk("%s", buf);
1682 rulla = lec_arp_empty_ones; 1677 }
1683 if (rulla) 1678 rulla = lec_arp_empty_ones;
1684 printk("Empty ones\n"); 1679 if (rulla)
1685 while(rulla) { 1680 printk("Empty ones\n");
1686 offset=0; 1681 while (rulla) {
1687 offset += sprintf(buf+offset,"Mac:"); 1682 offset = 0;
1688 for(j=0;j<ETH_ALEN;j++) { 1683 offset += sprintf(buf + offset, "Mac:");
1689 offset+=sprintf(buf+offset,"%2.2x ", 1684 for (j = 0; j < ETH_ALEN; j++) {
1690 rulla->mac_addr[j]&0xff); 1685 offset += sprintf(buf + offset, "%2.2x ",
1691 } 1686 rulla->mac_addr[j] & 0xff);
1692 offset +=sprintf(buf+offset,"Atm:"); 1687 }
1693 for(j=0;j<ATM_ESA_LEN;j++) { 1688 offset += sprintf(buf + offset, "Atm:");
1694 offset+=sprintf(buf+offset,"%2.2x ", 1689 for (j = 0; j < ATM_ESA_LEN; j++) {
1695 rulla->atm_addr[j]&0xff); 1690 offset += sprintf(buf + offset, "%2.2x ",
1696 } 1691 rulla->atm_addr[j] & 0xff);
1697 offset+=sprintf(buf+offset, 1692 }
1698 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ", 1693 offset += sprintf(buf + offset,
1699 rulla->vcc?rulla->vcc->vpi:0, 1694 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ",
1700 rulla->vcc?rulla->vcc->vci:0, 1695 rulla->vcc ? rulla->vcc->vpi : 0,
1701 rulla->recv_vcc?rulla->recv_vcc->vpi:0, 1696 rulla->vcc ? rulla->vcc->vci : 0,
1702 rulla->recv_vcc?rulla->recv_vcc->vci:0, 1697 rulla->recv_vcc ? rulla->recv_vcc->vpi : 0,
1703 rulla->last_used, 1698 rulla->recv_vcc ? rulla->recv_vcc->vci : 0,
1704 rulla->timestamp, rulla->no_tries); 1699 rulla->last_used,
1705 offset+=sprintf(buf+offset, 1700 rulla->timestamp, rulla->no_tries);
1706 "Flags:%x, Packets_flooded:%x, Status: %s ", 1701 offset += sprintf(buf + offset,
1707 rulla->flags, rulla->packets_flooded, 1702 "Flags:%x, Packets_flooded:%x, Status: %s ",
1708 get_status_string(rulla->status)); 1703 rulla->flags, rulla->packets_flooded,
1709 offset+=sprintf(buf+offset,"->%lx\n",(long)rulla->next); 1704 get_status_string(rulla->status));
1710 rulla = rulla->next; 1705 offset += sprintf(buf + offset, "->%lx\n", (long)rulla->next);
1711 printk("%s",buf); 1706 rulla = rulla->next;
1712 } 1707 printk("%s", buf);
1713 1708 }
1714 rulla = mcast_fwds; 1709
1715 if (rulla) 1710 rulla = mcast_fwds;
1716 printk("Multicast Forward VCCs\n"); 1711 if (rulla)
1717 while(rulla) { 1712 printk("Multicast Forward VCCs\n");
1718 offset=0; 1713 while (rulla) {
1719 offset += sprintf(buf+offset,"Mac:"); 1714 offset = 0;
1720 for(j=0;j<ETH_ALEN;j++) { 1715 offset += sprintf(buf + offset, "Mac:");
1721 offset+=sprintf(buf+offset,"%2.2x ", 1716 for (j = 0; j < ETH_ALEN; j++) {
1722 rulla->mac_addr[j]&0xff); 1717 offset += sprintf(buf + offset, "%2.2x ",
1723 } 1718 rulla->mac_addr[j] & 0xff);
1724 offset +=sprintf(buf+offset,"Atm:"); 1719 }
1725 for(j=0;j<ATM_ESA_LEN;j++) { 1720 offset += sprintf(buf + offset, "Atm:");
1726 offset+=sprintf(buf+offset,"%2.2x ", 1721 for (j = 0; j < ATM_ESA_LEN; j++) {
1727 rulla->atm_addr[j]&0xff); 1722 offset += sprintf(buf + offset, "%2.2x ",
1728 } 1723 rulla->atm_addr[j] & 0xff);
1729 offset+=sprintf(buf+offset, 1724 }
1730 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ", 1725 offset += sprintf(buf + offset,
1731 rulla->vcc?rulla->vcc->vpi:0, 1726 "Vcc vpi:%d vci:%d, Recv_vcc vpi:%d vci:%d Last_used:%lx, Timestamp:%lx, No_tries:%d ",
1732 rulla->vcc?rulla->vcc->vci:0, 1727 rulla->vcc ? rulla->vcc->vpi : 0,
1733 rulla->recv_vcc?rulla->recv_vcc->vpi:0, 1728 rulla->vcc ? rulla->vcc->vci : 0,
1734 rulla->recv_vcc?rulla->recv_vcc->vci:0, 1729 rulla->recv_vcc ? rulla->recv_vcc->vpi : 0,
1735 rulla->last_used, 1730 rulla->recv_vcc ? rulla->recv_vcc->vci : 0,
1736 rulla->timestamp, rulla->no_tries); 1731 rulla->last_used,
1737 offset+=sprintf(buf+offset, 1732 rulla->timestamp, rulla->no_tries);
1738 "Flags:%x, Packets_flooded:%x, Status: %s ", 1733 offset += sprintf(buf + offset,
1739 rulla->flags, rulla->packets_flooded, 1734 "Flags:%x, Packets_flooded:%x, Status: %s ",
1740 get_status_string(rulla->status)); 1735 rulla->flags, rulla->packets_flooded,
1741 offset+=sprintf(buf+offset,"->%lx\n",(long)rulla->next); 1736 get_status_string(rulla->status));
1742 rulla = rulla->next; 1737 offset += sprintf(buf + offset, "->%lx\n", (long)rulla->next);
1743 printk("%s",buf); 1738 rulla = rulla->next;
1744 } 1739 printk("%s", buf);
1740 }
1745 1741
1746#endif 1742#endif
1747} 1743}
@@ -1749,177 +1745,168 @@ dump_arp_table(struct lec_priv *priv)
1749/* 1745/*
1750 * Destruction of arp-cache 1746 * Destruction of arp-cache
1751 */ 1747 */
1752static void 1748static void lec_arp_destroy(struct lec_priv *priv)
1753lec_arp_destroy(struct lec_priv *priv)
1754{ 1749{
1755 unsigned long flags; 1750 unsigned long flags;
1756 struct lec_arp_table *entry, *next; 1751 struct lec_arp_table *entry, *next;
1757 int i; 1752 int i;
1753
1754 del_timer_sync(&priv->lec_arp_timer);
1758 1755
1759 del_timer_sync(&priv->lec_arp_timer); 1756 /*
1760 1757 * Remove all entries
1761 /* 1758 */
1762 * Remove all entries
1763 */
1764 1759
1765 spin_lock_irqsave(&priv->lec_arp_lock, flags); 1760 spin_lock_irqsave(&priv->lec_arp_lock, flags);
1766 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) { 1761 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
1767 for(entry = priv->lec_arp_tables[i]; entry != NULL; entry=next) { 1762 for (entry = priv->lec_arp_tables[i]; entry != NULL;
1768 next = entry->next; 1763 entry = next) {
1769 lec_arp_remove(priv, entry); 1764 next = entry->next;
1770 kfree(entry); 1765 lec_arp_remove(priv, entry);
1771 } 1766 kfree(entry);
1772 } 1767 }
1773 entry = priv->lec_arp_empty_ones; 1768 }
1774 while(entry) { 1769 entry = priv->lec_arp_empty_ones;
1775 next = entry->next; 1770 while (entry) {
1776 del_timer_sync(&entry->timer); 1771 next = entry->next;
1777 lec_arp_clear_vccs(entry); 1772 del_timer_sync(&entry->timer);
1778 kfree(entry); 1773 lec_arp_clear_vccs(entry);
1779 entry = next; 1774 kfree(entry);
1780 } 1775 entry = next;
1781 priv->lec_arp_empty_ones = NULL; 1776 }
1782 entry = priv->lec_no_forward; 1777 priv->lec_arp_empty_ones = NULL;
1783 while(entry) { 1778 entry = priv->lec_no_forward;
1784 next = entry->next; 1779 while (entry) {
1785 del_timer_sync(&entry->timer); 1780 next = entry->next;
1786 lec_arp_clear_vccs(entry); 1781 del_timer_sync(&entry->timer);
1787 kfree(entry); 1782 lec_arp_clear_vccs(entry);
1788 entry = next; 1783 kfree(entry);
1789 } 1784 entry = next;
1790 priv->lec_no_forward = NULL; 1785 }
1791 entry = priv->mcast_fwds; 1786 priv->lec_no_forward = NULL;
1792 while(entry) { 1787 entry = priv->mcast_fwds;
1793 next = entry->next; 1788 while (entry) {
1794 /* No timer, LANEv2 7.1.20 and 2.3.5.3 */ 1789 next = entry->next;
1795 lec_arp_clear_vccs(entry); 1790 /* No timer, LANEv2 7.1.20 and 2.3.5.3 */
1796 kfree(entry); 1791 lec_arp_clear_vccs(entry);
1797 entry = next; 1792 kfree(entry);
1798 } 1793 entry = next;
1799 priv->mcast_fwds = NULL; 1794 }
1800 priv->mcast_vcc = NULL; 1795 priv->mcast_fwds = NULL;
1801 memset(priv->lec_arp_tables, 0, 1796 priv->mcast_vcc = NULL;
1802 sizeof(struct lec_arp_table *) * LEC_ARP_TABLE_SIZE); 1797 memset(priv->lec_arp_tables, 0,
1798 sizeof(struct lec_arp_table *) * LEC_ARP_TABLE_SIZE);
1803 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 1799 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
1804} 1800}
1805 1801
1806
1807/* 1802/*
1808 * Find entry by mac_address 1803 * Find entry by mac_address
1809 */ 1804 */
1810static struct lec_arp_table* 1805static struct lec_arp_table *lec_arp_find(struct lec_priv *priv,
1811lec_arp_find(struct lec_priv *priv, 1806 unsigned char *mac_addr)
1812 unsigned char *mac_addr)
1813{ 1807{
1814 unsigned short place; 1808 unsigned short place;
1815 struct lec_arp_table *to_return; 1809 struct lec_arp_table *to_return;
1816 1810
1817 DPRINTK("LEC_ARP: lec_arp_find :%2.2x %2.2x %2.2x %2.2x %2.2x %2.2x\n", 1811 DPRINTK("LEC_ARP: lec_arp_find :%2.2x %2.2x %2.2x %2.2x %2.2x %2.2x\n",
1818 mac_addr[0]&0xff, mac_addr[1]&0xff, mac_addr[2]&0xff, 1812 mac_addr[0] & 0xff, mac_addr[1] & 0xff, mac_addr[2] & 0xff,
1819 mac_addr[3]&0xff, mac_addr[4]&0xff, mac_addr[5]&0xff); 1813 mac_addr[3] & 0xff, mac_addr[4] & 0xff, mac_addr[5] & 0xff);
1820 place = HASH(mac_addr[ETH_ALEN-1]); 1814 place = HASH(mac_addr[ETH_ALEN - 1]);
1821 1815
1822 to_return = priv->lec_arp_tables[place]; 1816 to_return = priv->lec_arp_tables[place];
1823 while(to_return) { 1817 while (to_return) {
1824 if (!compare_ether_addr(mac_addr, to_return->mac_addr)) { 1818 if (!compare_ether_addr(mac_addr, to_return->mac_addr)) {
1825 return to_return; 1819 return to_return;
1826 } 1820 }
1827 to_return = to_return->next; 1821 to_return = to_return->next;
1828 } 1822 }
1829 return NULL; 1823 return NULL;
1830} 1824}
1831 1825
1832static struct lec_arp_table* 1826static struct lec_arp_table *make_entry(struct lec_priv *priv,
1833make_entry(struct lec_priv *priv, unsigned char *mac_addr) 1827 unsigned char *mac_addr)
1834{ 1828{
1835 struct lec_arp_table *to_return; 1829 struct lec_arp_table *to_return;
1836 1830
1837 to_return = kzalloc(sizeof(struct lec_arp_table), GFP_ATOMIC); 1831 to_return = kzalloc(sizeof(struct lec_arp_table), GFP_ATOMIC);
1838 if (!to_return) { 1832 if (!to_return) {
1839 printk("LEC: Arp entry kmalloc failed\n"); 1833 printk("LEC: Arp entry kmalloc failed\n");
1840 return NULL; 1834 return NULL;
1841 } 1835 }
1842 memcpy(to_return->mac_addr, mac_addr, ETH_ALEN); 1836 memcpy(to_return->mac_addr, mac_addr, ETH_ALEN);
1843 init_timer(&to_return->timer); 1837 init_timer(&to_return->timer);
1844 to_return->timer.function = lec_arp_expire_arp; 1838 to_return->timer.function = lec_arp_expire_arp;
1845 to_return->timer.data = (unsigned long) to_return; 1839 to_return->timer.data = (unsigned long)to_return;
1846 to_return->last_used = jiffies; 1840 to_return->last_used = jiffies;
1847 to_return->priv = priv; 1841 to_return->priv = priv;
1848 skb_queue_head_init(&to_return->tx_wait); 1842 skb_queue_head_init(&to_return->tx_wait);
1849 return to_return; 1843 return to_return;
1850} 1844}
1851 1845
1852/* 1846/* Arp sent timer expired */
1853 * 1847static void lec_arp_expire_arp(unsigned long data)
1854 * Arp sent timer expired
1855 *
1856 */
1857static void
1858lec_arp_expire_arp(unsigned long data)
1859{ 1848{
1860 struct lec_arp_table *entry; 1849 struct lec_arp_table *entry;
1861 1850
1862 entry = (struct lec_arp_table *)data; 1851 entry = (struct lec_arp_table *)data;
1863 1852
1864 DPRINTK("lec_arp_expire_arp\n"); 1853 DPRINTK("lec_arp_expire_arp\n");
1865 if (entry->status == ESI_ARP_PENDING) { 1854 if (entry->status == ESI_ARP_PENDING) {
1866 if (entry->no_tries <= entry->priv->max_retry_count) { 1855 if (entry->no_tries <= entry->priv->max_retry_count) {
1867 if (entry->is_rdesc) 1856 if (entry->is_rdesc)
1868 send_to_lecd(entry->priv, l_rdesc_arp_xmt, entry->mac_addr, NULL, NULL); 1857 send_to_lecd(entry->priv, l_rdesc_arp_xmt,
1869 else 1858 entry->mac_addr, NULL, NULL);
1870 send_to_lecd(entry->priv, l_arp_xmt, entry->mac_addr, NULL, NULL); 1859 else
1871 entry->no_tries++; 1860 send_to_lecd(entry->priv, l_arp_xmt,
1872 } 1861 entry->mac_addr, NULL, NULL);
1873 mod_timer(&entry->timer, jiffies + (1*HZ)); 1862 entry->no_tries++;
1874 } 1863 }
1864 mod_timer(&entry->timer, jiffies + (1 * HZ));
1865 }
1875} 1866}
1876 1867
1877/* 1868/* Unknown/unused vcc expire, remove associated entry */
1878 * 1869static void lec_arp_expire_vcc(unsigned long data)
1879 * Unknown/unused vcc expire, remove associated entry
1880 *
1881 */
1882static void
1883lec_arp_expire_vcc(unsigned long data)
1884{ 1870{
1885 unsigned long flags; 1871 unsigned long flags;
1886 struct lec_arp_table *to_remove = (struct lec_arp_table*)data; 1872 struct lec_arp_table *to_remove = (struct lec_arp_table *)data;
1887 struct lec_priv *priv = (struct lec_priv *)to_remove->priv; 1873 struct lec_priv *priv = (struct lec_priv *)to_remove->priv;
1888 struct lec_arp_table *entry = NULL; 1874 struct lec_arp_table *entry = NULL;
1889 1875
1890 del_timer(&to_remove->timer); 1876 del_timer(&to_remove->timer);
1891 1877
1892 DPRINTK("LEC_ARP %p %p: lec_arp_expire_vcc vpi:%d vci:%d\n", 1878 DPRINTK("LEC_ARP %p %p: lec_arp_expire_vcc vpi:%d vci:%d\n",
1893 to_remove, priv, 1879 to_remove, priv,
1894 to_remove->vcc?to_remove->recv_vcc->vpi:0, 1880 to_remove->vcc ? to_remove->recv_vcc->vpi : 0,
1895 to_remove->vcc?to_remove->recv_vcc->vci:0); 1881 to_remove->vcc ? to_remove->recv_vcc->vci : 0);
1896 DPRINTK("eo:%p nf:%p\n",priv->lec_arp_empty_ones,priv->lec_no_forward); 1882 DPRINTK("eo:%p nf:%p\n", priv->lec_arp_empty_ones,
1883 priv->lec_no_forward);
1897 1884
1898 spin_lock_irqsave(&priv->lec_arp_lock, flags); 1885 spin_lock_irqsave(&priv->lec_arp_lock, flags);
1899 if (to_remove == priv->lec_arp_empty_ones) 1886 if (to_remove == priv->lec_arp_empty_ones)
1900 priv->lec_arp_empty_ones = to_remove->next; 1887 priv->lec_arp_empty_ones = to_remove->next;
1901 else { 1888 else {
1902 entry = priv->lec_arp_empty_ones; 1889 entry = priv->lec_arp_empty_ones;
1903 while (entry && entry->next != to_remove) 1890 while (entry && entry->next != to_remove)
1904 entry = entry->next; 1891 entry = entry->next;
1905 if (entry) 1892 if (entry)
1906 entry->next = to_remove->next; 1893 entry->next = to_remove->next;
1907 } 1894 }
1908 if (!entry) { 1895 if (!entry) {
1909 if (to_remove == priv->lec_no_forward) { 1896 if (to_remove == priv->lec_no_forward) {
1910 priv->lec_no_forward = to_remove->next; 1897 priv->lec_no_forward = to_remove->next;
1911 } else { 1898 } else {
1912 entry = priv->lec_no_forward; 1899 entry = priv->lec_no_forward;
1913 while (entry && entry->next != to_remove) 1900 while (entry && entry->next != to_remove)
1914 entry = entry->next; 1901 entry = entry->next;
1915 if (entry) 1902 if (entry)
1916 entry->next = to_remove->next; 1903 entry->next = to_remove->next;
1917 } 1904 }
1918 } 1905 }
1919 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 1906 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
1920 1907
1921 lec_arp_clear_vccs(to_remove); 1908 lec_arp_clear_vccs(to_remove);
1922 kfree(to_remove); 1909 kfree(to_remove);
1923} 1910}
1924 1911
1925/* 1912/*
@@ -1938,64 +1925,68 @@ lec_arp_expire_vcc(unsigned long data)
1938 * to ESI_FORWARD_DIRECT. This causes the flush period to end 1925 * to ESI_FORWARD_DIRECT. This causes the flush period to end
1939 * regardless of the progress of the flush protocol. 1926 * regardless of the progress of the flush protocol.
1940 */ 1927 */
1941static void 1928static void lec_arp_check_expire(unsigned long data)
1942lec_arp_check_expire(unsigned long data)
1943{ 1929{
1944 unsigned long flags; 1930 unsigned long flags;
1945 struct lec_priv *priv = (struct lec_priv *)data; 1931 struct lec_priv *priv = (struct lec_priv *)data;
1946 struct lec_arp_table *entry, *next; 1932 struct lec_arp_table *entry, *next;
1947 unsigned long now; 1933 unsigned long now;
1948 unsigned long time_to_check; 1934 unsigned long time_to_check;
1949 int i; 1935 int i;
1950 1936
1951 DPRINTK("lec_arp_check_expire %p\n",priv); 1937 DPRINTK("lec_arp_check_expire %p\n", priv);
1952 DPRINTK("expire: eo:%p nf:%p\n",priv->lec_arp_empty_ones, 1938 DPRINTK("expire: eo:%p nf:%p\n", priv->lec_arp_empty_ones,
1953 priv->lec_no_forward); 1939 priv->lec_no_forward);
1954 now = jiffies; 1940 now = jiffies;
1955 spin_lock_irqsave(&priv->lec_arp_lock, flags); 1941 spin_lock_irqsave(&priv->lec_arp_lock, flags);
1956 for(i = 0; i < LEC_ARP_TABLE_SIZE; i++) { 1942 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
1957 for(entry = priv->lec_arp_tables[i]; entry != NULL; ) { 1943 for (entry = priv->lec_arp_tables[i]; entry != NULL;) {
1958 if ((entry->flags) & LEC_REMOTE_FLAG && 1944 if ((entry->flags) & LEC_REMOTE_FLAG &&
1959 priv->topology_change) 1945 priv->topology_change)
1960 time_to_check = priv->forward_delay_time; 1946 time_to_check = priv->forward_delay_time;
1961 else 1947 else
1962 time_to_check = priv->aging_time; 1948 time_to_check = priv->aging_time;
1963 1949
1964 DPRINTK("About to expire: %lx - %lx > %lx\n", 1950 DPRINTK("About to expire: %lx - %lx > %lx\n",
1965 now,entry->last_used, time_to_check); 1951 now, entry->last_used, time_to_check);
1966 if( time_after(now, entry->last_used+ 1952 if (time_after(now, entry->last_used + time_to_check)
1967 time_to_check) && 1953 && !(entry->flags & LEC_PERMANENT_FLAG)
1968 !(entry->flags & LEC_PERMANENT_FLAG) && 1954 && !(entry->mac_addr[0] & 0x01)) { /* LANE2: 7.1.20 */
1969 !(entry->mac_addr[0] & 0x01) ) { /* LANE2: 7.1.20 */
1970 /* Remove entry */ 1955 /* Remove entry */
1971 DPRINTK("LEC:Entry timed out\n"); 1956 DPRINTK("LEC:Entry timed out\n");
1972 next = entry->next; 1957 next = entry->next;
1973 lec_arp_remove(priv, entry); 1958 lec_arp_remove(priv, entry);
1974 kfree(entry); 1959 kfree(entry);
1975 entry = next; 1960 entry = next;
1976 } else { 1961 } else {
1977 /* Something else */ 1962 /* Something else */
1978 if ((entry->status == ESI_VC_PENDING || 1963 if ((entry->status == ESI_VC_PENDING ||
1979 entry->status == ESI_ARP_PENDING) 1964 entry->status == ESI_ARP_PENDING)
1980 && time_after_eq(now, 1965 && time_after_eq(now,
1981 entry->timestamp + 1966 entry->timestamp +
1982 priv->max_unknown_frame_time)) { 1967 priv->
1968 max_unknown_frame_time)) {
1983 entry->timestamp = jiffies; 1969 entry->timestamp = jiffies;
1984 entry->packets_flooded = 0; 1970 entry->packets_flooded = 0;
1985 if (entry->status == ESI_VC_PENDING) 1971 if (entry->status == ESI_VC_PENDING)
1986 send_to_lecd(priv, l_svc_setup, entry->mac_addr, entry->atm_addr, NULL); 1972 send_to_lecd(priv, l_svc_setup,
1973 entry->mac_addr,
1974 entry->atm_addr,
1975 NULL);
1987 } 1976 }
1988 if (entry->status == ESI_FLUSH_PENDING 1977 if (entry->status == ESI_FLUSH_PENDING
1989 && 1978 &&
1990 time_after_eq(now, entry->timestamp+ 1979 time_after_eq(now, entry->timestamp +
1991 priv->path_switching_delay)) { 1980 priv->path_switching_delay)) {
1992 struct sk_buff *skb; 1981 struct sk_buff *skb;
1993 1982
1994 while ((skb = skb_dequeue(&entry->tx_wait)) != NULL) 1983 while ((skb =
1995 lec_send(entry->vcc, skb, entry->priv); 1984 skb_dequeue(&entry->tx_wait)) !=
1985 NULL)
1986 lec_send(entry->vcc, skb,
1987 entry->priv);
1996 entry->last_used = jiffies; 1988 entry->last_used = jiffies;
1997 entry->status = 1989 entry->status = ESI_FORWARD_DIRECT;
1998 ESI_FORWARD_DIRECT;
1999 } 1990 }
2000 entry = entry->next; 1991 entry = entry->next;
2001 } 1992 }
@@ -2003,93 +1994,101 @@ lec_arp_check_expire(unsigned long data)
2003 } 1994 }
2004 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 1995 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2005 1996
2006 mod_timer(&priv->lec_arp_timer, jiffies + LEC_ARP_REFRESH_INTERVAL); 1997 mod_timer(&priv->lec_arp_timer, jiffies + LEC_ARP_REFRESH_INTERVAL);
2007} 1998}
1999
2008/* 2000/*
2009 * Try to find vcc where mac_address is attached. 2001 * Try to find vcc where mac_address is attached.
2010 * 2002 *
2011 */ 2003 */
2012static struct atm_vcc* 2004static struct atm_vcc *lec_arp_resolve(struct lec_priv *priv,
2013lec_arp_resolve(struct lec_priv *priv, unsigned char *mac_to_find, 2005 unsigned char *mac_to_find, int is_rdesc,
2014 int is_rdesc, struct lec_arp_table **ret_entry) 2006 struct lec_arp_table **ret_entry)
2015{ 2007{
2016 unsigned long flags; 2008 unsigned long flags;
2017 struct lec_arp_table *entry; 2009 struct lec_arp_table *entry;
2018 struct atm_vcc *found; 2010 struct atm_vcc *found;
2019 2011
2020 if (mac_to_find[0] & 0x01) { 2012 if (mac_to_find[0] & 0x01) {
2021 switch (priv->lane_version) { 2013 switch (priv->lane_version) {
2022 case 1: 2014 case 1:
2023 return priv->mcast_vcc; 2015 return priv->mcast_vcc;
2024 break; 2016 break;
2025 case 2: /* LANE2 wants arp for multicast addresses */ 2017 case 2: /* LANE2 wants arp for multicast addresses */
2026 if (!compare_ether_addr(mac_to_find, bus_mac)) 2018 if (!compare_ether_addr(mac_to_find, bus_mac))
2027 return priv->mcast_vcc; 2019 return priv->mcast_vcc;
2028 break; 2020 break;
2029 default: 2021 default:
2030 break; 2022 break;
2031 } 2023 }
2032 } 2024 }
2033 2025
2034 spin_lock_irqsave(&priv->lec_arp_lock, flags); 2026 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2035 entry = lec_arp_find(priv, mac_to_find); 2027 entry = lec_arp_find(priv, mac_to_find);
2036 2028
2037 if (entry) { 2029 if (entry) {
2038 if (entry->status == ESI_FORWARD_DIRECT) { 2030 if (entry->status == ESI_FORWARD_DIRECT) {
2039 /* Connection Ok */ 2031 /* Connection Ok */
2040 entry->last_used = jiffies; 2032 entry->last_used = jiffies;
2041 *ret_entry = entry; 2033 *ret_entry = entry;
2042 found = entry->vcc; 2034 found = entry->vcc;
2043 goto out; 2035 goto out;
2044 } 2036 }
2045 /* If the LE_ARP cache entry is still pending, reset count to 0 2037 /*
2038 * If the LE_ARP cache entry is still pending, reset count to 0
2046 * so another LE_ARP request can be made for this frame. 2039 * so another LE_ARP request can be made for this frame.
2047 */ 2040 */
2048 if (entry->status == ESI_ARP_PENDING) { 2041 if (entry->status == ESI_ARP_PENDING) {
2049 entry->no_tries = 0; 2042 entry->no_tries = 0;
2050 } 2043 }
2051 /* Data direct VC not yet set up, check to see if the unknown 2044 /*
2052 frame count is greater than the limit. If the limit has 2045 * Data direct VC not yet set up, check to see if the unknown
2053 not been reached, allow the caller to send packet to 2046 * frame count is greater than the limit. If the limit has
2054 BUS. */ 2047 * not been reached, allow the caller to send packet to
2055 if (entry->status != ESI_FLUSH_PENDING && 2048 * BUS.
2056 entry->packets_flooded<priv->maximum_unknown_frame_count) { 2049 */
2057 entry->packets_flooded++; 2050 if (entry->status != ESI_FLUSH_PENDING &&
2058 DPRINTK("LEC_ARP: Flooding..\n"); 2051 entry->packets_flooded <
2059 found = priv->mcast_vcc; 2052 priv->maximum_unknown_frame_count) {
2053 entry->packets_flooded++;
2054 DPRINTK("LEC_ARP: Flooding..\n");
2055 found = priv->mcast_vcc;
2060 goto out; 2056 goto out;
2061 } 2057 }
2062 /* We got here because entry->status == ESI_FLUSH_PENDING 2058 /*
2059 * We got here because entry->status == ESI_FLUSH_PENDING
2063 * or BUS flood limit was reached for an entry which is 2060 * or BUS flood limit was reached for an entry which is
2064 * in ESI_ARP_PENDING or ESI_VC_PENDING state. 2061 * in ESI_ARP_PENDING or ESI_VC_PENDING state.
2065 */ 2062 */
2066 *ret_entry = entry; 2063 *ret_entry = entry;
2067 DPRINTK("lec: entry->status %d entry->vcc %p\n", entry->status, entry->vcc); 2064 DPRINTK("lec: entry->status %d entry->vcc %p\n", entry->status,
2068 found = NULL; 2065 entry->vcc);
2069 } else { 2066 found = NULL;
2070 /* No matching entry was found */ 2067 } else {
2071 entry = make_entry(priv, mac_to_find); 2068 /* No matching entry was found */
2072 DPRINTK("LEC_ARP: Making entry\n"); 2069 entry = make_entry(priv, mac_to_find);
2073 if (!entry) { 2070 DPRINTK("LEC_ARP: Making entry\n");
2074 found = priv->mcast_vcc; 2071 if (!entry) {
2072 found = priv->mcast_vcc;
2075 goto out; 2073 goto out;
2076 } 2074 }
2077 lec_arp_add(priv, entry); 2075 lec_arp_add(priv, entry);
2078 /* We want arp-request(s) to be sent */ 2076 /* We want arp-request(s) to be sent */
2079 entry->packets_flooded =1; 2077 entry->packets_flooded = 1;
2080 entry->status = ESI_ARP_PENDING; 2078 entry->status = ESI_ARP_PENDING;
2081 entry->no_tries = 1; 2079 entry->no_tries = 1;
2082 entry->last_used = entry->timestamp = jiffies; 2080 entry->last_used = entry->timestamp = jiffies;
2083 entry->is_rdesc = is_rdesc; 2081 entry->is_rdesc = is_rdesc;
2084 if (entry->is_rdesc) 2082 if (entry->is_rdesc)
2085 send_to_lecd(priv, l_rdesc_arp_xmt, mac_to_find, NULL, NULL); 2083 send_to_lecd(priv, l_rdesc_arp_xmt, mac_to_find, NULL,
2086 else 2084 NULL);
2087 send_to_lecd(priv, l_arp_xmt, mac_to_find, NULL, NULL); 2085 else
2088 entry->timer.expires = jiffies + (1*HZ); 2086 send_to_lecd(priv, l_arp_xmt, mac_to_find, NULL, NULL);
2089 entry->timer.function = lec_arp_expire_arp; 2087 entry->timer.expires = jiffies + (1 * HZ);
2090 add_timer(&entry->timer); 2088 entry->timer.function = lec_arp_expire_arp;
2091 found = priv->mcast_vcc; 2089 add_timer(&entry->timer);
2092 } 2090 found = priv->mcast_vcc;
2091 }
2093 2092
2094out: 2093out:
2095 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 2094 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
@@ -2097,30 +2096,31 @@ out:
2097} 2096}
2098 2097
2099static int 2098static int
2100lec_addr_delete(struct lec_priv *priv, unsigned char *atm_addr, 2099lec_addr_delete(struct lec_priv *priv, unsigned char *atm_addr,
2101 unsigned long permanent) 2100 unsigned long permanent)
2102{ 2101{
2103 unsigned long flags; 2102 unsigned long flags;
2104 struct lec_arp_table *entry, *next; 2103 struct lec_arp_table *entry, *next;
2105 int i; 2104 int i;
2106 2105
2107 DPRINTK("lec_addr_delete\n"); 2106 DPRINTK("lec_addr_delete\n");
2108 spin_lock_irqsave(&priv->lec_arp_lock, flags); 2107 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2109 for(i = 0; i < LEC_ARP_TABLE_SIZE; i++) { 2108 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
2110 for(entry = priv->lec_arp_tables[i]; entry != NULL; entry = next) { 2109 for (entry = priv->lec_arp_tables[i]; entry != NULL;
2111 next = entry->next; 2110 entry = next) {
2112 if (!memcmp(atm_addr, entry->atm_addr, ATM_ESA_LEN) 2111 next = entry->next;
2113 && (permanent || 2112 if (!memcmp(atm_addr, entry->atm_addr, ATM_ESA_LEN)
2114 !(entry->flags & LEC_PERMANENT_FLAG))) { 2113 && (permanent ||
2114 !(entry->flags & LEC_PERMANENT_FLAG))) {
2115 lec_arp_remove(priv, entry); 2115 lec_arp_remove(priv, entry);
2116 kfree(entry); 2116 kfree(entry);
2117 } 2117 }
2118 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 2118 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2119 return 0; 2119 return 0;
2120 } 2120 }
2121 } 2121 }
2122 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 2122 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2123 return -1; 2123 return -1;
2124} 2124}
2125 2125
2126/* 2126/*
@@ -2128,109 +2128,109 @@ lec_addr_delete(struct lec_priv *priv, unsigned char *atm_addr,
2128 */ 2128 */
2129static void 2129static void
2130lec_arp_update(struct lec_priv *priv, unsigned char *mac_addr, 2130lec_arp_update(struct lec_priv *priv, unsigned char *mac_addr,
2131 unsigned char *atm_addr, unsigned long remoteflag, 2131 unsigned char *atm_addr, unsigned long remoteflag,
2132 unsigned int targetless_le_arp) 2132 unsigned int targetless_le_arp)
2133{ 2133{
2134 unsigned long flags; 2134 unsigned long flags;
2135 struct lec_arp_table *entry, *tmp; 2135 struct lec_arp_table *entry, *tmp;
2136 int i; 2136 int i;
2137 2137
2138 DPRINTK("lec:%s", (targetless_le_arp) ? "targetless ": " "); 2138 DPRINTK("lec:%s", (targetless_le_arp) ? "targetless " : " ");
2139 DPRINTK("lec_arp_update mac:%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x\n", 2139 DPRINTK("lec_arp_update mac:%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x\n",
2140 mac_addr[0],mac_addr[1],mac_addr[2],mac_addr[3], 2140 mac_addr[0], mac_addr[1], mac_addr[2], mac_addr[3],
2141 mac_addr[4],mac_addr[5]); 2141 mac_addr[4], mac_addr[5]);
2142 2142
2143 spin_lock_irqsave(&priv->lec_arp_lock, flags); 2143 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2144 entry = lec_arp_find(priv, mac_addr); 2144 entry = lec_arp_find(priv, mac_addr);
2145 if (entry == NULL && targetless_le_arp) 2145 if (entry == NULL && targetless_le_arp)
2146 goto out; /* LANE2: ignore targetless LE_ARPs for which 2146 goto out; /*
2147 * we have no entry in the cache. 7.1.30 2147 * LANE2: ignore targetless LE_ARPs for which
2148 */ 2148 * we have no entry in the cache. 7.1.30
2149 if (priv->lec_arp_empty_ones) { 2149 */
2150 entry = priv->lec_arp_empty_ones; 2150 if (priv->lec_arp_empty_ones) {
2151 if (!memcmp(entry->atm_addr, atm_addr, ATM_ESA_LEN)) { 2151 entry = priv->lec_arp_empty_ones;
2152 priv->lec_arp_empty_ones = entry->next; 2152 if (!memcmp(entry->atm_addr, atm_addr, ATM_ESA_LEN)) {
2153 } else { 2153 priv->lec_arp_empty_ones = entry->next;
2154 while(entry->next && memcmp(entry->next->atm_addr, 2154 } else {
2155 atm_addr, ATM_ESA_LEN)) 2155 while (entry->next && memcmp(entry->next->atm_addr,
2156 entry = entry->next; 2156 atm_addr, ATM_ESA_LEN))
2157 if (entry->next) { 2157 entry = entry->next;
2158 tmp = entry; 2158 if (entry->next) {
2159 entry = entry->next; 2159 tmp = entry;
2160 tmp->next = entry->next; 2160 entry = entry->next;
2161 } else 2161 tmp->next = entry->next;
2162 entry = NULL; 2162 } else
2163 2163 entry = NULL;
2164 } 2164
2165 if (entry) { 2165 }
2166 del_timer(&entry->timer); 2166 if (entry) {
2167 tmp = lec_arp_find(priv, mac_addr); 2167 del_timer(&entry->timer);
2168 if (tmp) { 2168 tmp = lec_arp_find(priv, mac_addr);
2169 del_timer(&tmp->timer); 2169 if (tmp) {
2170 tmp->status = ESI_FORWARD_DIRECT; 2170 del_timer(&tmp->timer);
2171 memcpy(tmp->atm_addr, atm_addr, ATM_ESA_LEN); 2171 tmp->status = ESI_FORWARD_DIRECT;
2172 tmp->vcc = entry->vcc; 2172 memcpy(tmp->atm_addr, atm_addr, ATM_ESA_LEN);
2173 tmp->old_push = entry->old_push; 2173 tmp->vcc = entry->vcc;
2174 tmp->last_used = jiffies; 2174 tmp->old_push = entry->old_push;
2175 del_timer(&entry->timer); 2175 tmp->last_used = jiffies;
2176 kfree(entry); 2176 del_timer(&entry->timer);
2177 entry=tmp; 2177 kfree(entry);
2178 } else { 2178 entry = tmp;
2179 entry->status = ESI_FORWARD_DIRECT; 2179 } else {
2180 memcpy(entry->mac_addr, mac_addr, ETH_ALEN); 2180 entry->status = ESI_FORWARD_DIRECT;
2181 entry->last_used = jiffies; 2181 memcpy(entry->mac_addr, mac_addr, ETH_ALEN);
2182 lec_arp_add(priv, entry); 2182 entry->last_used = jiffies;
2183 } 2183 lec_arp_add(priv, entry);
2184 if (remoteflag) 2184 }
2185 entry->flags|=LEC_REMOTE_FLAG; 2185 if (remoteflag)
2186 else 2186 entry->flags |= LEC_REMOTE_FLAG;
2187 entry->flags&=~LEC_REMOTE_FLAG; 2187 else
2188 DPRINTK("After update\n"); 2188 entry->flags &= ~LEC_REMOTE_FLAG;
2189 dump_arp_table(priv); 2189 DPRINTK("After update\n");
2190 goto out; 2190 dump_arp_table(priv);
2191 }
2192 }
2193 entry = lec_arp_find(priv, mac_addr);
2194 if (!entry) {
2195 entry = make_entry(priv, mac_addr);
2196 if (!entry)
2197 goto out; 2191 goto out;
2198 entry->status = ESI_UNKNOWN; 2192 }
2199 lec_arp_add(priv, entry); 2193 }
2200 /* Temporary, changes before end of function */ 2194 entry = lec_arp_find(priv, mac_addr);
2201 } 2195 if (!entry) {
2202 memcpy(entry->atm_addr, atm_addr, ATM_ESA_LEN); 2196 entry = make_entry(priv, mac_addr);
2203 del_timer(&entry->timer); 2197 if (!entry)
2204 for(i = 0; i < LEC_ARP_TABLE_SIZE; i++) { 2198 goto out;
2205 for(tmp = priv->lec_arp_tables[i]; tmp; tmp=tmp->next) { 2199 entry->status = ESI_UNKNOWN;
2206 if (entry != tmp && 2200 lec_arp_add(priv, entry);
2207 !memcmp(tmp->atm_addr, atm_addr, 2201 /* Temporary, changes before end of function */
2208 ATM_ESA_LEN)) { 2202 }
2209 /* Vcc to this host exists */ 2203 memcpy(entry->atm_addr, atm_addr, ATM_ESA_LEN);
2210 if (tmp->status > ESI_VC_PENDING) { 2204 del_timer(&entry->timer);
2211 /* 2205 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
2212 * ESI_FLUSH_PENDING, 2206 for (tmp = priv->lec_arp_tables[i]; tmp; tmp = tmp->next) {
2213 * ESI_FORWARD_DIRECT 2207 if (entry != tmp &&
2214 */ 2208 !memcmp(tmp->atm_addr, atm_addr, ATM_ESA_LEN)) {
2215 entry->vcc = tmp->vcc; 2209 /* Vcc to this host exists */
2216 entry->old_push=tmp->old_push; 2210 if (tmp->status > ESI_VC_PENDING) {
2217 } 2211 /*
2218 entry->status=tmp->status; 2212 * ESI_FLUSH_PENDING,
2219 break; 2213 * ESI_FORWARD_DIRECT
2220 } 2214 */
2221 } 2215 entry->vcc = tmp->vcc;
2222 } 2216 entry->old_push = tmp->old_push;
2223 if (remoteflag) 2217 }
2224 entry->flags|=LEC_REMOTE_FLAG; 2218 entry->status = tmp->status;
2225 else 2219 break;
2226 entry->flags&=~LEC_REMOTE_FLAG; 2220 }
2227 if (entry->status == ESI_ARP_PENDING || 2221 }
2228 entry->status == ESI_UNKNOWN) { 2222 }
2229 entry->status = ESI_VC_PENDING; 2223 if (remoteflag)
2230 send_to_lecd(priv, l_svc_setup, entry->mac_addr, atm_addr, NULL); 2224 entry->flags |= LEC_REMOTE_FLAG;
2231 } 2225 else
2232 DPRINTK("After update2\n"); 2226 entry->flags &= ~LEC_REMOTE_FLAG;
2233 dump_arp_table(priv); 2227 if (entry->status == ESI_ARP_PENDING || entry->status == ESI_UNKNOWN) {
2228 entry->status = ESI_VC_PENDING;
2229 send_to_lecd(priv, l_svc_setup, entry->mac_addr, atm_addr,
2230 NULL);
2231 }
2232 DPRINTK("After update2\n");
2233 dump_arp_table(priv);
2234out: 2234out:
2235 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 2235 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2236} 2236}
@@ -2240,299 +2240,312 @@ out:
2240 */ 2240 */
2241static void 2241static void
2242lec_vcc_added(struct lec_priv *priv, struct atmlec_ioc *ioc_data, 2242lec_vcc_added(struct lec_priv *priv, struct atmlec_ioc *ioc_data,
2243 struct atm_vcc *vcc, 2243 struct atm_vcc *vcc,
2244 void (*old_push)(struct atm_vcc *vcc, struct sk_buff *skb)) 2244 void (*old_push) (struct atm_vcc *vcc, struct sk_buff *skb))
2245{ 2245{
2246 unsigned long flags; 2246 unsigned long flags;
2247 struct lec_arp_table *entry; 2247 struct lec_arp_table *entry;
2248 int i, found_entry=0; 2248 int i, found_entry = 0;
2249 2249
2250 spin_lock_irqsave(&priv->lec_arp_lock, flags); 2250 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2251 if (ioc_data->receive == 2) { 2251 if (ioc_data->receive == 2) {
2252 /* Vcc for Multicast Forward. No timer, LANEv2 7.1.20 and 2.3.5.3 */ 2252 /* Vcc for Multicast Forward. No timer, LANEv2 7.1.20 and 2.3.5.3 */
2253 2253
2254 DPRINTK("LEC_ARP: Attaching mcast forward\n"); 2254 DPRINTK("LEC_ARP: Attaching mcast forward\n");
2255#if 0 2255#if 0
2256 entry = lec_arp_find(priv, bus_mac); 2256 entry = lec_arp_find(priv, bus_mac);
2257 if (!entry) { 2257 if (!entry) {
2258 printk("LEC_ARP: Multicast entry not found!\n"); 2258 printk("LEC_ARP: Multicast entry not found!\n");
2259 goto out; 2259 goto out;
2260 } 2260 }
2261 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN); 2261 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN);
2262 entry->recv_vcc = vcc; 2262 entry->recv_vcc = vcc;
2263 entry->old_recv_push = old_push; 2263 entry->old_recv_push = old_push;
2264#endif 2264#endif
2265 entry = make_entry(priv, bus_mac); 2265 entry = make_entry(priv, bus_mac);
2266 if (entry == NULL) 2266 if (entry == NULL)
2267 goto out; 2267 goto out;
2268 del_timer(&entry->timer); 2268 del_timer(&entry->timer);
2269 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN); 2269 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN);
2270 entry->recv_vcc = vcc; 2270 entry->recv_vcc = vcc;
2271 entry->old_recv_push = old_push; 2271 entry->old_recv_push = old_push;
2272 entry->next = priv->mcast_fwds; 2272 entry->next = priv->mcast_fwds;
2273 priv->mcast_fwds = entry; 2273 priv->mcast_fwds = entry;
2274 goto out; 2274 goto out;
2275 } else if (ioc_data->receive == 1) { 2275 } else if (ioc_data->receive == 1) {
2276 /* Vcc which we don't want to make default vcc, attach it 2276 /*
2277 anyway. */ 2277 * Vcc which we don't want to make default vcc,
2278 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", 2278 * attach it anyway.
2279 ioc_data->atm_addr[0],ioc_data->atm_addr[1], 2279 */
2280 ioc_data->atm_addr[2],ioc_data->atm_addr[3], 2280 DPRINTK
2281 ioc_data->atm_addr[4],ioc_data->atm_addr[5], 2281 ("LEC_ARP:Attaching data direct, not default: "
2282 ioc_data->atm_addr[6],ioc_data->atm_addr[7], 2282 "%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",
2283 ioc_data->atm_addr[8],ioc_data->atm_addr[9], 2283 ioc_data->atm_addr[0], ioc_data->atm_addr[1],
2284 ioc_data->atm_addr[10],ioc_data->atm_addr[11], 2284 ioc_data->atm_addr[2], ioc_data->atm_addr[3],
2285 ioc_data->atm_addr[12],ioc_data->atm_addr[13], 2285 ioc_data->atm_addr[4], ioc_data->atm_addr[5],
2286 ioc_data->atm_addr[14],ioc_data->atm_addr[15], 2286 ioc_data->atm_addr[6], ioc_data->atm_addr[7],
2287 ioc_data->atm_addr[16],ioc_data->atm_addr[17], 2287 ioc_data->atm_addr[8], ioc_data->atm_addr[9],
2288 ioc_data->atm_addr[18],ioc_data->atm_addr[19]); 2288 ioc_data->atm_addr[10], ioc_data->atm_addr[11],
2289 entry = make_entry(priv, bus_mac); 2289 ioc_data->atm_addr[12], ioc_data->atm_addr[13],
2290 if (entry == NULL) 2290 ioc_data->atm_addr[14], ioc_data->atm_addr[15],
2291 ioc_data->atm_addr[16], ioc_data->atm_addr[17],
2292 ioc_data->atm_addr[18], ioc_data->atm_addr[19]);
2293 entry = make_entry(priv, bus_mac);
2294 if (entry == NULL)
2291 goto out; 2295 goto out;
2292 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN); 2296 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN);
2293 memset(entry->mac_addr, 0, ETH_ALEN); 2297 memset(entry->mac_addr, 0, ETH_ALEN);
2294 entry->recv_vcc = vcc; 2298 entry->recv_vcc = vcc;
2295 entry->old_recv_push = old_push; 2299 entry->old_recv_push = old_push;
2296 entry->status = ESI_UNKNOWN; 2300 entry->status = ESI_UNKNOWN;
2297 entry->timer.expires = jiffies + priv->vcc_timeout_period; 2301 entry->timer.expires = jiffies + priv->vcc_timeout_period;
2298 entry->timer.function = lec_arp_expire_vcc; 2302 entry->timer.function = lec_arp_expire_vcc;
2299 add_timer(&entry->timer); 2303 add_timer(&entry->timer);
2300 entry->next = priv->lec_no_forward; 2304 entry->next = priv->lec_no_forward;
2301 priv->lec_no_forward = entry; 2305 priv->lec_no_forward = entry;
2302 dump_arp_table(priv); 2306 dump_arp_table(priv);
2303 goto out; 2307 goto out;
2304 } 2308 }
2305 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", 2309 DPRINTK
2306 ioc_data->atm_addr[0],ioc_data->atm_addr[1], 2310 ("LEC_ARP:Attaching data direct, default: "
2307 ioc_data->atm_addr[2],ioc_data->atm_addr[3], 2311 "%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",
2308 ioc_data->atm_addr[4],ioc_data->atm_addr[5], 2312 ioc_data->atm_addr[0], ioc_data->atm_addr[1],
2309 ioc_data->atm_addr[6],ioc_data->atm_addr[7], 2313 ioc_data->atm_addr[2], ioc_data->atm_addr[3],
2310 ioc_data->atm_addr[8],ioc_data->atm_addr[9], 2314 ioc_data->atm_addr[4], ioc_data->atm_addr[5],
2311 ioc_data->atm_addr[10],ioc_data->atm_addr[11], 2315 ioc_data->atm_addr[6], ioc_data->atm_addr[7],
2312 ioc_data->atm_addr[12],ioc_data->atm_addr[13], 2316 ioc_data->atm_addr[8], ioc_data->atm_addr[9],
2313 ioc_data->atm_addr[14],ioc_data->atm_addr[15], 2317 ioc_data->atm_addr[10], ioc_data->atm_addr[11],
2314 ioc_data->atm_addr[16],ioc_data->atm_addr[17], 2318 ioc_data->atm_addr[12], ioc_data->atm_addr[13],
2315 ioc_data->atm_addr[18],ioc_data->atm_addr[19]); 2319 ioc_data->atm_addr[14], ioc_data->atm_addr[15],
2316 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) { 2320 ioc_data->atm_addr[16], ioc_data->atm_addr[17],
2317 for (entry = priv->lec_arp_tables[i]; entry; entry=entry->next) { 2321 ioc_data->atm_addr[18], ioc_data->atm_addr[19]);
2318 if (memcmp(ioc_data->atm_addr, entry->atm_addr, 2322 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
2319 ATM_ESA_LEN)==0) { 2323 for (entry = priv->lec_arp_tables[i]; entry;
2320 DPRINTK("LEC_ARP: Attaching data direct\n"); 2324 entry = entry->next) {
2321 DPRINTK("Currently -> Vcc: %d, Rvcc:%d\n", 2325 if (memcmp
2322 entry->vcc?entry->vcc->vci:0, 2326 (ioc_data->atm_addr, entry->atm_addr,
2323 entry->recv_vcc?entry->recv_vcc->vci:0); 2327 ATM_ESA_LEN) == 0) {
2324 found_entry=1; 2328 DPRINTK("LEC_ARP: Attaching data direct\n");
2325 del_timer(&entry->timer); 2329 DPRINTK("Currently -> Vcc: %d, Rvcc:%d\n",
2326 entry->vcc = vcc; 2330 entry->vcc ? entry->vcc->vci : 0,
2327 entry->old_push = old_push; 2331 entry->recv_vcc ? entry->recv_vcc->
2328 if (entry->status == ESI_VC_PENDING) { 2332 vci : 0);
2329 if(priv->maximum_unknown_frame_count 2333 found_entry = 1;
2330 ==0) 2334 del_timer(&entry->timer);
2331 entry->status = 2335 entry->vcc = vcc;
2332 ESI_FORWARD_DIRECT; 2336 entry->old_push = old_push;
2333 else { 2337 if (entry->status == ESI_VC_PENDING) {
2334 entry->timestamp = jiffies; 2338 if (priv->maximum_unknown_frame_count
2335 entry->status = 2339 == 0)
2336 ESI_FLUSH_PENDING; 2340 entry->status =
2341 ESI_FORWARD_DIRECT;
2342 else {
2343 entry->timestamp = jiffies;
2344 entry->status =
2345 ESI_FLUSH_PENDING;
2337#if 0 2346#if 0
2338 send_to_lecd(priv,l_flush_xmt, 2347 send_to_lecd(priv, l_flush_xmt,
2339 NULL, 2348 NULL,
2340 entry->atm_addr, 2349 entry->atm_addr,
2341 NULL); 2350 NULL);
2342#endif 2351#endif
2343 } 2352 }
2344 } else { 2353 } else {
2345 /* They were forming a connection 2354 /*
2346 to us, and we to them. Our 2355 * They were forming a connection
2347 ATM address is numerically lower 2356 * to us, and we to them. Our
2348 than theirs, so we make connection 2357 * ATM address is numerically lower
2349 we formed into default VCC (8.1.11). 2358 * than theirs, so we make connection
2350 Connection they made gets torn 2359 * we formed into default VCC (8.1.11).
2351 down. This might confuse some 2360 * Connection they made gets torn
2352 clients. Can be changed if 2361 * down. This might confuse some
2353 someone reports trouble... */ 2362 * clients. Can be changed if
2354 ; 2363 * someone reports trouble...
2355 } 2364 */
2356 } 2365 ;
2357 } 2366 }
2358 } 2367 }
2359 if (found_entry) { 2368 }
2360 DPRINTK("After vcc was added\n"); 2369 }
2361 dump_arp_table(priv); 2370 if (found_entry) {
2371 DPRINTK("After vcc was added\n");
2372 dump_arp_table(priv);
2362 goto out; 2373 goto out;
2363 } 2374 }
2364 /* Not found, snatch address from first data packet that arrives from 2375 /*
2365 this vcc */ 2376 * Not found, snatch address from first data packet that arrives
2366 entry = make_entry(priv, bus_mac); 2377 * from this vcc
2367 if (!entry) 2378 */
2379 entry = make_entry(priv, bus_mac);
2380 if (!entry)
2368 goto out; 2381 goto out;
2369 entry->vcc = vcc; 2382 entry->vcc = vcc;
2370 entry->old_push = old_push; 2383 entry->old_push = old_push;
2371 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN); 2384 memcpy(entry->atm_addr, ioc_data->atm_addr, ATM_ESA_LEN);
2372 memset(entry->mac_addr, 0, ETH_ALEN); 2385 memset(entry->mac_addr, 0, ETH_ALEN);
2373 entry->status = ESI_UNKNOWN; 2386 entry->status = ESI_UNKNOWN;
2374 entry->next = priv->lec_arp_empty_ones; 2387 entry->next = priv->lec_arp_empty_ones;
2375 priv->lec_arp_empty_ones = entry; 2388 priv->lec_arp_empty_ones = entry;
2376 entry->timer.expires = jiffies + priv->vcc_timeout_period; 2389 entry->timer.expires = jiffies + priv->vcc_timeout_period;
2377 entry->timer.function = lec_arp_expire_vcc; 2390 entry->timer.function = lec_arp_expire_vcc;
2378 add_timer(&entry->timer); 2391 add_timer(&entry->timer);
2379 DPRINTK("After vcc was added\n"); 2392 DPRINTK("After vcc was added\n");
2380 dump_arp_table(priv); 2393 dump_arp_table(priv);
2381out: 2394out:
2382 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 2395 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2383} 2396}
2384 2397
2385static void 2398static void lec_flush_complete(struct lec_priv *priv, unsigned long tran_id)
2386lec_flush_complete(struct lec_priv *priv, unsigned long tran_id)
2387{ 2399{
2388 unsigned long flags; 2400 unsigned long flags;
2389 struct lec_arp_table *entry; 2401 struct lec_arp_table *entry;
2390 int i; 2402 int i;
2391
2392 DPRINTK("LEC:lec_flush_complete %lx\n",tran_id);
2393 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2394 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
2395 for (entry = priv->lec_arp_tables[i]; entry; entry=entry->next) {
2396 if (entry->flush_tran_id == tran_id &&
2397 entry->status == ESI_FLUSH_PENDING) {
2398 struct sk_buff *skb;
2399 2403
2400 while ((skb = skb_dequeue(&entry->tx_wait)) != NULL) 2404 DPRINTK("LEC:lec_flush_complete %lx\n", tran_id);
2405 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2406 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
2407 for (entry = priv->lec_arp_tables[i]; entry;
2408 entry = entry->next) {
2409 if (entry->flush_tran_id == tran_id
2410 && entry->status == ESI_FLUSH_PENDING) {
2411 struct sk_buff *skb;
2412
2413 while ((skb =
2414 skb_dequeue(&entry->tx_wait)) != NULL)
2401 lec_send(entry->vcc, skb, entry->priv); 2415 lec_send(entry->vcc, skb, entry->priv);
2402 entry->status = ESI_FORWARD_DIRECT; 2416 entry->status = ESI_FORWARD_DIRECT;
2403 DPRINTK("LEC_ARP: Flushed\n"); 2417 DPRINTK("LEC_ARP: Flushed\n");
2404 } 2418 }
2405 } 2419 }
2406 } 2420 }
2407 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 2421 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2408 dump_arp_table(priv); 2422 dump_arp_table(priv);
2409} 2423}
2410 2424
2411static void 2425static void
2412lec_set_flush_tran_id(struct lec_priv *priv, 2426lec_set_flush_tran_id(struct lec_priv *priv,
2413 unsigned char *atm_addr, unsigned long tran_id) 2427 unsigned char *atm_addr, unsigned long tran_id)
2414{ 2428{
2415 unsigned long flags; 2429 unsigned long flags;
2416 struct lec_arp_table *entry; 2430 struct lec_arp_table *entry;
2417 int i; 2431 int i;
2418 2432
2419 spin_lock_irqsave(&priv->lec_arp_lock, flags); 2433 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2420 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) 2434 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++)
2421 for(entry = priv->lec_arp_tables[i]; entry; entry=entry->next) 2435 for (entry = priv->lec_arp_tables[i]; entry;
2422 if (!memcmp(atm_addr, entry->atm_addr, ATM_ESA_LEN)) { 2436 entry = entry->next)
2423 entry->flush_tran_id = tran_id; 2437 if (!memcmp(atm_addr, entry->atm_addr, ATM_ESA_LEN)) {
2424 DPRINTK("Set flush transaction id to %lx for %p\n",tran_id,entry); 2438 entry->flush_tran_id = tran_id;
2425 } 2439 DPRINTK
2440 ("Set flush transaction id to %lx for %p\n",
2441 tran_id, entry);
2442 }
2426 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 2443 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2427} 2444}
2428 2445
2429static int 2446static int lec_mcast_make(struct lec_priv *priv, struct atm_vcc *vcc)
2430lec_mcast_make(struct lec_priv *priv, struct atm_vcc *vcc)
2431{ 2447{
2432 unsigned long flags; 2448 unsigned long flags;
2433 unsigned char mac_addr[] = { 2449 unsigned char mac_addr[] = {
2434 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; 2450 0xff, 0xff, 0xff, 0xff, 0xff, 0xff
2435 struct lec_arp_table *to_add; 2451 };
2452 struct lec_arp_table *to_add;
2436 struct lec_vcc_priv *vpriv; 2453 struct lec_vcc_priv *vpriv;
2437 int err = 0; 2454 int err = 0;
2438 2455
2439 if (!(vpriv = kmalloc(sizeof(struct lec_vcc_priv), GFP_KERNEL))) 2456 if (!(vpriv = kmalloc(sizeof(struct lec_vcc_priv), GFP_KERNEL)))
2440 return -ENOMEM; 2457 return -ENOMEM;
2441 vpriv->xoff = 0; 2458 vpriv->xoff = 0;
2442 vpriv->old_pop = vcc->pop; 2459 vpriv->old_pop = vcc->pop;
2443 vcc->user_back = vpriv; 2460 vcc->user_back = vpriv;
2444 vcc->pop = lec_pop; 2461 vcc->pop = lec_pop;
2445 spin_lock_irqsave(&priv->lec_arp_lock, flags); 2462 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2446 to_add = make_entry(priv, mac_addr); 2463 to_add = make_entry(priv, mac_addr);
2447 if (!to_add) { 2464 if (!to_add) {
2448 vcc->pop = vpriv->old_pop; 2465 vcc->pop = vpriv->old_pop;
2449 kfree(vpriv); 2466 kfree(vpriv);
2450 err = -ENOMEM; 2467 err = -ENOMEM;
2451 goto out; 2468 goto out;
2452 } 2469 }
2453 memcpy(to_add->atm_addr, vcc->remote.sas_addr.prv, ATM_ESA_LEN); 2470 memcpy(to_add->atm_addr, vcc->remote.sas_addr.prv, ATM_ESA_LEN);
2454 to_add->status = ESI_FORWARD_DIRECT; 2471 to_add->status = ESI_FORWARD_DIRECT;
2455 to_add->flags |= LEC_PERMANENT_FLAG; 2472 to_add->flags |= LEC_PERMANENT_FLAG;
2456 to_add->vcc = vcc; 2473 to_add->vcc = vcc;
2457 to_add->old_push = vcc->push; 2474 to_add->old_push = vcc->push;
2458 vcc->push = lec_push; 2475 vcc->push = lec_push;
2459 priv->mcast_vcc = vcc; 2476 priv->mcast_vcc = vcc;
2460 lec_arp_add(priv, to_add); 2477 lec_arp_add(priv, to_add);
2461out: 2478out:
2462 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 2479 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2463 return err; 2480 return err;
2464} 2481}
2465 2482
2466static void 2483static void lec_vcc_close(struct lec_priv *priv, struct atm_vcc *vcc)
2467lec_vcc_close(struct lec_priv *priv, struct atm_vcc *vcc)
2468{ 2484{
2469 unsigned long flags; 2485 unsigned long flags;
2470 struct lec_arp_table *entry, *next; 2486 struct lec_arp_table *entry, *next;
2471 int i; 2487 int i;
2472 2488
2473 DPRINTK("LEC_ARP: lec_vcc_close vpi:%d vci:%d\n",vcc->vpi,vcc->vci); 2489 DPRINTK("LEC_ARP: lec_vcc_close vpi:%d vci:%d\n", vcc->vpi, vcc->vci);
2474 dump_arp_table(priv); 2490 dump_arp_table(priv);
2475 spin_lock_irqsave(&priv->lec_arp_lock, flags); 2491 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2476 for(i=0;i<LEC_ARP_TABLE_SIZE;i++) { 2492 for (i = 0; i < LEC_ARP_TABLE_SIZE; i++) {
2477 for(entry = priv->lec_arp_tables[i];entry; entry=next) { 2493 for (entry = priv->lec_arp_tables[i]; entry; entry = next) {
2478 next = entry->next; 2494 next = entry->next;
2479 if (vcc == entry->vcc) { 2495 if (vcc == entry->vcc) {
2480 lec_arp_remove(priv, entry); 2496 lec_arp_remove(priv, entry);
2481 kfree(entry); 2497 kfree(entry);
2482 if (priv->mcast_vcc == vcc) { 2498 if (priv->mcast_vcc == vcc) {
2483 priv->mcast_vcc = NULL; 2499 priv->mcast_vcc = NULL;
2484 } 2500 }
2485 } 2501 }
2486 } 2502 }
2487 } 2503 }
2488 2504
2489 entry = priv->lec_arp_empty_ones; 2505 entry = priv->lec_arp_empty_ones;
2490 priv->lec_arp_empty_ones = NULL; 2506 priv->lec_arp_empty_ones = NULL;
2491 while (entry != NULL) { 2507 while (entry != NULL) {
2492 next = entry->next; 2508 next = entry->next;
2493 if (entry->vcc == vcc) { /* leave it out from the list */ 2509 if (entry->vcc == vcc) { /* leave it out from the list */
2494 lec_arp_clear_vccs(entry); 2510 lec_arp_clear_vccs(entry);
2495 del_timer(&entry->timer); 2511 del_timer(&entry->timer);
2496 kfree(entry); 2512 kfree(entry);
2497 } 2513 } else { /* put it back to the list */
2498 else { /* put it back to the list */ 2514 entry->next = priv->lec_arp_empty_ones;
2499 entry->next = priv->lec_arp_empty_ones; 2515 priv->lec_arp_empty_ones = entry;
2500 priv->lec_arp_empty_ones = entry; 2516 }
2501 } 2517 entry = next;
2502 entry = next; 2518 }
2503 } 2519
2504 2520 entry = priv->lec_no_forward;
2505 entry = priv->lec_no_forward; 2521 priv->lec_no_forward = NULL;
2506 priv->lec_no_forward = NULL; 2522 while (entry != NULL) {
2507 while (entry != NULL) { 2523 next = entry->next;
2508 next = entry->next; 2524 if (entry->recv_vcc == vcc) {
2509 if (entry->recv_vcc == vcc) { 2525 lec_arp_clear_vccs(entry);
2510 lec_arp_clear_vccs(entry); 2526 del_timer(&entry->timer);
2511 del_timer(&entry->timer); 2527 kfree(entry);
2512 kfree(entry); 2528 } else {
2513 } 2529 entry->next = priv->lec_no_forward;
2514 else { 2530 priv->lec_no_forward = entry;
2515 entry->next = priv->lec_no_forward; 2531 }
2516 priv->lec_no_forward = entry; 2532 entry = next;
2517 } 2533 }
2518 entry = next; 2534
2519 } 2535 entry = priv->mcast_fwds;
2520 2536 priv->mcast_fwds = NULL;
2521 entry = priv->mcast_fwds; 2537 while (entry != NULL) {
2522 priv->mcast_fwds = NULL; 2538 next = entry->next;
2523 while (entry != NULL) { 2539 if (entry->recv_vcc == vcc) {
2524 next = entry->next; 2540 lec_arp_clear_vccs(entry);
2525 if (entry->recv_vcc == vcc) { 2541 /* No timer, LANEv2 7.1.20 and 2.3.5.3 */
2526 lec_arp_clear_vccs(entry); 2542 kfree(entry);
2527 /* No timer, LANEv2 7.1.20 and 2.3.5.3 */ 2543 } else {
2528 kfree(entry); 2544 entry->next = priv->mcast_fwds;
2529 } 2545 priv->mcast_fwds = entry;
2530 else { 2546 }
2531 entry->next = priv->mcast_fwds; 2547 entry = next;
2532 priv->mcast_fwds = entry; 2548 }
2533 }
2534 entry = next;
2535 }
2536 2549
2537 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 2550 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2538 dump_arp_table(priv); 2551 dump_arp_table(priv);
@@ -2540,57 +2553,59 @@ lec_vcc_close(struct lec_priv *priv, struct atm_vcc *vcc)
2540 2553
2541static void 2554static void
2542lec_arp_check_empties(struct lec_priv *priv, 2555lec_arp_check_empties(struct lec_priv *priv,
2543 struct atm_vcc *vcc, struct sk_buff *skb) 2556 struct atm_vcc *vcc, struct sk_buff *skb)
2544{ 2557{
2545 unsigned long flags; 2558 unsigned long flags;
2546 struct lec_arp_table *entry, *prev; 2559 struct lec_arp_table *entry, *prev;
2547 struct lecdatahdr_8023 *hdr = (struct lecdatahdr_8023 *)skb->data; 2560 struct lecdatahdr_8023 *hdr = (struct lecdatahdr_8023 *)skb->data;
2548 unsigned char *src; 2561 unsigned char *src;
2549#ifdef CONFIG_TR 2562#ifdef CONFIG_TR
2550 struct lecdatahdr_8025 *tr_hdr = (struct lecdatahdr_8025 *)skb->data; 2563 struct lecdatahdr_8025 *tr_hdr = (struct lecdatahdr_8025 *)skb->data;
2551 2564
2552 if (priv->is_trdev) src = tr_hdr->h_source; 2565 if (priv->is_trdev)
2553 else 2566 src = tr_hdr->h_source;
2567 else
2554#endif 2568#endif
2555 src = hdr->h_source; 2569 src = hdr->h_source;
2556 2570
2557 spin_lock_irqsave(&priv->lec_arp_lock, flags); 2571 spin_lock_irqsave(&priv->lec_arp_lock, flags);
2558 entry = priv->lec_arp_empty_ones; 2572 entry = priv->lec_arp_empty_ones;
2559 if (vcc == entry->vcc) { 2573 if (vcc == entry->vcc) {
2560 del_timer(&entry->timer); 2574 del_timer(&entry->timer);
2561 memcpy(entry->mac_addr, src, ETH_ALEN); 2575 memcpy(entry->mac_addr, src, ETH_ALEN);
2562 entry->status = ESI_FORWARD_DIRECT; 2576 entry->status = ESI_FORWARD_DIRECT;
2563 entry->last_used = jiffies; 2577 entry->last_used = jiffies;
2564 priv->lec_arp_empty_ones = entry->next; 2578 priv->lec_arp_empty_ones = entry->next;
2565 /* We might have got an entry */ 2579 /* We might have got an entry */
2566 if ((prev = lec_arp_find(priv,src))) { 2580 if ((prev = lec_arp_find(priv, src))) {
2567 lec_arp_remove(priv, prev); 2581 lec_arp_remove(priv, prev);
2568 kfree(prev); 2582 kfree(prev);
2569 } 2583 }
2570 lec_arp_add(priv, entry); 2584 lec_arp_add(priv, entry);
2571 goto out; 2585 goto out;
2572 } 2586 }
2573 prev = entry; 2587 prev = entry;
2574 entry = entry->next; 2588 entry = entry->next;
2575 while (entry && entry->vcc != vcc) { 2589 while (entry && entry->vcc != vcc) {
2576 prev= entry; 2590 prev = entry;
2577 entry = entry->next; 2591 entry = entry->next;
2578 } 2592 }
2579 if (!entry) { 2593 if (!entry) {
2580 DPRINTK("LEC_ARP: Arp_check_empties: entry not found!\n"); 2594 DPRINTK("LEC_ARP: Arp_check_empties: entry not found!\n");
2581 goto out; 2595 goto out;
2582 } 2596 }
2583 del_timer(&entry->timer); 2597 del_timer(&entry->timer);
2584 memcpy(entry->mac_addr, src, ETH_ALEN); 2598 memcpy(entry->mac_addr, src, ETH_ALEN);
2585 entry->status = ESI_FORWARD_DIRECT; 2599 entry->status = ESI_FORWARD_DIRECT;
2586 entry->last_used = jiffies; 2600 entry->last_used = jiffies;
2587 prev->next = entry->next; 2601 prev->next = entry->next;
2588 if ((prev = lec_arp_find(priv, src))) { 2602 if ((prev = lec_arp_find(priv, src))) {
2589 lec_arp_remove(priv, prev); 2603 lec_arp_remove(priv, prev);
2590 kfree(prev); 2604 kfree(prev);
2591 } 2605 }
2592 lec_arp_add(priv, entry); 2606 lec_arp_add(priv, entry);
2593out: 2607out:
2594 spin_unlock_irqrestore(&priv->lec_arp_lock, flags); 2608 spin_unlock_irqrestore(&priv->lec_arp_lock, flags);
2595} 2609}
2610
2596MODULE_LICENSE("GPL"); 2611MODULE_LICENSE("GPL");