diff options
author | Amit Kumar Salecha <amit.salecha@qlogic.com> | 2010-10-04 00:20:09 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2010-10-05 01:46:48 -0400 |
commit | 31dee692e22eedaf2540fa543fa9c91df6ab8bda (patch) | |
tree | 10e544e30a4dfe906282b8ddfaf7a9f379bd9535 /drivers/net/qlcnic | |
parent | 21a180cda012e1f93e362dd4a9b0bfd3d8c92940 (diff) |
qlcnic: fix internal loopback test
o Loop 10 times with delay of 1 ms to rcv packet.
o Print garbage packet.
o Try send/receive MAX(16) packet, instead of exit from test,
if a packet is not received.
Signed-off-by: Amit Kumar Salecha <amit.salecha@qlogic.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/qlcnic')
-rw-r--r-- | drivers/net/qlcnic/qlcnic_ethtool.c | 26 | ||||
-rw-r--r-- | drivers/net/qlcnic/qlcnic_init.c | 19 |
2 files changed, 37 insertions, 8 deletions
diff --git a/drivers/net/qlcnic/qlcnic_ethtool.c b/drivers/net/qlcnic/qlcnic_ethtool.c index cb9463bd6b1e..550cfe9a1b1d 100644 --- a/drivers/net/qlcnic/qlcnic_ethtool.c +++ b/drivers/net/qlcnic/qlcnic_ethtool.c | |||
@@ -636,6 +636,8 @@ static int qlcnic_get_sset_count(struct net_device *dev, int sset) | |||
636 | } | 636 | } |
637 | 637 | ||
638 | #define QLC_ILB_PKT_SIZE 64 | 638 | #define QLC_ILB_PKT_SIZE 64 |
639 | #define QLC_NUM_ILB_PKT 16 | ||
640 | #define QLC_ILB_MAX_RCV_LOOP 10 | ||
639 | 641 | ||
640 | static void qlcnic_create_loopback_buff(unsigned char *data) | 642 | static void qlcnic_create_loopback_buff(unsigned char *data) |
641 | { | 643 | { |
@@ -657,24 +659,34 @@ static int qlcnic_do_ilb_test(struct qlcnic_adapter *adapter) | |||
657 | struct qlcnic_recv_context *recv_ctx = &adapter->recv_ctx; | 659 | struct qlcnic_recv_context *recv_ctx = &adapter->recv_ctx; |
658 | struct qlcnic_host_sds_ring *sds_ring = &recv_ctx->sds_rings[0]; | 660 | struct qlcnic_host_sds_ring *sds_ring = &recv_ctx->sds_rings[0]; |
659 | struct sk_buff *skb; | 661 | struct sk_buff *skb; |
660 | int i; | 662 | int i, loop, cnt = 0; |
661 | 663 | ||
662 | for (i = 0; i < 16; i++) { | 664 | for (i = 0; i < QLC_NUM_ILB_PKT; i++) { |
663 | skb = dev_alloc_skb(QLC_ILB_PKT_SIZE); | 665 | skb = dev_alloc_skb(QLC_ILB_PKT_SIZE); |
664 | qlcnic_create_loopback_buff(skb->data); | 666 | qlcnic_create_loopback_buff(skb->data); |
665 | skb_put(skb, QLC_ILB_PKT_SIZE); | 667 | skb_put(skb, QLC_ILB_PKT_SIZE); |
666 | 668 | ||
667 | adapter->diag_cnt = 0; | 669 | adapter->diag_cnt = 0; |
668 | |||
669 | qlcnic_xmit_frame(skb, adapter->netdev); | 670 | qlcnic_xmit_frame(skb, adapter->netdev); |
670 | 671 | ||
671 | msleep(5); | 672 | loop = 0; |
672 | 673 | do { | |
673 | qlcnic_process_rcv_ring_diag(sds_ring); | 674 | msleep(1); |
675 | qlcnic_process_rcv_ring_diag(sds_ring); | ||
676 | } while (loop++ < QLC_ILB_MAX_RCV_LOOP && | ||
677 | !adapter->diag_cnt); | ||
674 | 678 | ||
675 | dev_kfree_skb_any(skb); | 679 | dev_kfree_skb_any(skb); |
680 | |||
676 | if (!adapter->diag_cnt) | 681 | if (!adapter->diag_cnt) |
677 | return -1; | 682 | dev_warn(&adapter->pdev->dev, "ILB Test: %dth packet" |
683 | " not recevied\n", i + 1); | ||
684 | else | ||
685 | cnt++; | ||
686 | } | ||
687 | if (cnt != i) { | ||
688 | dev_warn(&adapter->pdev->dev, "ILB Test failed\n"); | ||
689 | return -1; | ||
678 | } | 690 | } |
679 | return 0; | 691 | return 0; |
680 | } | 692 | } |
diff --git a/drivers/net/qlcnic/qlcnic_init.c b/drivers/net/qlcnic/qlcnic_init.c index 5c33d15c874a..908a25b5597a 100644 --- a/drivers/net/qlcnic/qlcnic_init.c +++ b/drivers/net/qlcnic/qlcnic_init.c | |||
@@ -1693,6 +1693,18 @@ qlcnic_post_rx_buffers_nodb(struct qlcnic_adapter *adapter, | |||
1693 | spin_unlock(&rds_ring->lock); | 1693 | spin_unlock(&rds_ring->lock); |
1694 | } | 1694 | } |
1695 | 1695 | ||
1696 | static void dump_skb(struct sk_buff *skb) | ||
1697 | { | ||
1698 | int i; | ||
1699 | unsigned char *data = skb->data; | ||
1700 | |||
1701 | for (i = 0; i < skb->len; i++) { | ||
1702 | printk("%02x ", data[i]); | ||
1703 | if ((i & 0x0f) == 8) | ||
1704 | printk("\n"); | ||
1705 | } | ||
1706 | } | ||
1707 | |||
1696 | static struct qlcnic_rx_buffer * | 1708 | static struct qlcnic_rx_buffer * |
1697 | qlcnic_process_rcv_diag(struct qlcnic_adapter *adapter, | 1709 | qlcnic_process_rcv_diag(struct qlcnic_adapter *adapter, |
1698 | struct qlcnic_host_sds_ring *sds_ring, | 1710 | struct qlcnic_host_sds_ring *sds_ring, |
@@ -1723,13 +1735,18 @@ qlcnic_process_rcv_diag(struct qlcnic_adapter *adapter, | |||
1723 | if (!skb) | 1735 | if (!skb) |
1724 | return buffer; | 1736 | return buffer; |
1725 | 1737 | ||
1726 | skb_put(skb, rds_ring->skb_size); | 1738 | if (length > rds_ring->skb_size) |
1739 | skb_put(skb, rds_ring->skb_size); | ||
1740 | else | ||
1741 | skb_put(skb, length); | ||
1727 | 1742 | ||
1728 | if (pkt_offset) | 1743 | if (pkt_offset) |
1729 | skb_pull(skb, pkt_offset); | 1744 | skb_pull(skb, pkt_offset); |
1730 | 1745 | ||
1731 | if (!qlcnic_check_loopback_buff(skb->data)) | 1746 | if (!qlcnic_check_loopback_buff(skb->data)) |
1732 | adapter->diag_cnt++; | 1747 | adapter->diag_cnt++; |
1748 | else | ||
1749 | dump_skb(skb); | ||
1733 | 1750 | ||
1734 | dev_kfree_skb_any(skb); | 1751 | dev_kfree_skb_any(skb); |
1735 | adapter->stats.rx_pkts++; | 1752 | adapter->stats.rx_pkts++; |