net: convert print_mac to %pM
[deliverable/linux.git] / drivers / infiniband / hw / nes / nes_nic.c
index 1b0938c87774e54017dd22364520778547b40dee..3c96203e0d915ff3ffff6347bc182bfb9e89d5cb 100644 (file)
@@ -91,6 +91,7 @@ static struct nic_qp_map *nic_qp_mapping_per_function[] = {
 static const u32 default_msg = NETIF_MSG_DRV | NETIF_MSG_PROBE | NETIF_MSG_LINK
                | NETIF_MSG_IFUP | NETIF_MSG_IFDOWN;
 static int debug = -1;
+static int nics_per_function = 1;
 
 /**
  * nes_netdev_poll
@@ -201,7 +202,8 @@ static int nes_netdev_open(struct net_device *netdev)
                nes_debug(NES_DBG_NETDEV, "i=%d, perfect filter table index= %d, PERF FILTER LOW"
                                " (Addr:%08X) = %08X, HIGH = %08X.\n",
                                i, nesvnic->qp_nic_index[i],
-                               NES_IDX_PERFECT_FILTER_LOW+((nesvnic->perfect_filter_index + i) * 8),
+                               NES_IDX_PERFECT_FILTER_LOW+
+                                       (nesvnic->qp_nic_index[i] * 8),
                                macaddr_low,
                                (u32)macaddr_high | NES_MAC_ADDR_VALID |
                                ((((u32)nesvnic->nic_index) << 16)));
@@ -272,14 +274,18 @@ static int nes_netdev_stop(struct net_device *netdev)
                        break;
        }
 
-       if (first_nesvnic->netdev_open == 0)
+       if ((first_nesvnic->netdev_open == 1) && (first_nesvnic != nesvnic)  &&
+               (PCI_FUNC(first_nesvnic->nesdev->pcidev->devfn) !=
+               PCI_FUNC(nesvnic->nesdev->pcidev->devfn))) {
+                       nes_write_indexed(nesdev, NES_IDX_MAC_INT_MASK+
+                               (0x200*nesdev->mac_index), 0xffffffff);
+                       nes_write_indexed(first_nesvnic->nesdev,
+                               NES_IDX_MAC_INT_MASK+
+                               (0x200*first_nesvnic->nesdev->mac_index),
+                       ~(NES_MAC_INT_LINK_STAT_CHG | NES_MAC_INT_XGMII_EXT |
+                       NES_MAC_INT_TX_UNDERFLOW | NES_MAC_INT_TX_ERROR));
+       } else {
                nes_write_indexed(nesdev, NES_IDX_MAC_INT_MASK+(0x200*nesdev->mac_index), 0xffffffff);
-       else if ((first_nesvnic != nesvnic) &&
-                (PCI_FUNC(first_nesvnic->nesdev->pcidev->devfn) != PCI_FUNC(nesvnic->nesdev->pcidev->devfn))) {
-               nes_write_indexed(nesdev, NES_IDX_MAC_INT_MASK + (0x200 * nesdev->mac_index), 0xffffffff);
-               nes_write_indexed(first_nesvnic->nesdev, NES_IDX_MAC_INT_MASK + (0x200 * first_nesvnic->nesdev->mac_index),
-                               ~(NES_MAC_INT_LINK_STAT_CHG | NES_MAC_INT_XGMII_EXT |
-                               NES_MAC_INT_TX_UNDERFLOW | NES_MAC_INT_TX_ERROR));
        }
 
        nic_active_mask = ~((u32)(1 << nesvnic->nic_index));
@@ -437,7 +443,7 @@ static int nes_netdev_start_xmit(struct sk_buff *skb, struct net_device *netdev)
        struct nes_hw_nic_sq_wqe *nic_sqe;
        struct tcphdr *tcph;
        /* struct udphdr *udph; */
-#define NES_MAX_TSO_FRAGS 18
+#define NES_MAX_TSO_FRAGS MAX_SKB_FRAGS
        /* 64K segment plus overflow on each side */
        dma_addr_t tso_bus_address[NES_MAX_TSO_FRAGS];
        dma_addr_t bus_address;
@@ -605,6 +611,8 @@ tso_sq_no_longer_full:
                                        wqe_fragment_length[wqe_fragment_index] = 0;
                                        set_wqe_64bit_value(nic_sqe->wqe_words, NES_NIC_SQ_WQE_FRAG1_LOW_IDX,
                                                                        bus_address);
+                                       tso_wqe_length += skb_headlen(skb) -
+                                                       original_first_length;
                                }
                                while (wqe_fragment_index < 5) {
                                        wqe_fragment_length[wqe_fragment_index] =
@@ -789,14 +797,13 @@ static int nes_netdev_set_mac_address(struct net_device *netdev, void *p)
        int i;
        u32 macaddr_low;
        u16 macaddr_high;
-       DECLARE_MAC_BUF(mac);
 
        if (!is_valid_ether_addr(mac_addr->sa_data))
                return -EADDRNOTAVAIL;
 
        memcpy(netdev->dev_addr, mac_addr->sa_data, netdev->addr_len);
-       printk(PFX "%s: Address length = %d, Address = %s\n",
-              __func__, netdev->addr_len, print_mac(mac, mac_addr->sa_data));
+       printk(PFX "%s: Address length = %d, Address = %pM\n",
+              __func__, netdev->addr_len, mac_addr->sa_data);
        macaddr_high  = ((u16)netdev->dev_addr[0]) << 8;
        macaddr_high += (u16)netdev->dev_addr[1];
        macaddr_low   = ((u32)netdev->dev_addr[2]) << 24;
@@ -827,6 +834,7 @@ static void nes_netdev_set_multicast_list(struct net_device *netdev)
 {
        struct nes_vnic *nesvnic = netdev_priv(netdev);
        struct nes_device *nesdev = nesvnic->nesdev;
+       struct nes_adapter *nesadapter = nesvnic->nesdev->nesadapter;
        struct dev_mc_list *multicast_addr;
        u32 nic_active_bit;
        u32 nic_active;
@@ -836,7 +844,12 @@ static void nes_netdev_set_multicast_list(struct net_device *netdev)
        u8 mc_all_on = 0;
        u8 mc_index;
        int mc_nic_index = -1;
+       u8 pft_entries_preallocated = max(nesadapter->adapter_fcn_count *
+                                       nics_per_function, 4);
+       u8 max_pft_entries_avaiable = NES_PFT_SIZE - pft_entries_preallocated;
+       unsigned long flags;
 
+       spin_lock_irqsave(&nesadapter->resource_lock, flags);
        nic_active_bit = 1 << nesvnic->nic_index;
 
        if (netdev->flags & IFF_PROMISC) {
@@ -847,7 +860,7 @@ static void nes_netdev_set_multicast_list(struct net_device *netdev)
                nic_active |= nic_active_bit;
                nes_write_indexed(nesdev, NES_IDX_NIC_UNICAST_ALL, nic_active);
                mc_all_on = 1;
-       } else if ((netdev->flags & IFF_ALLMULTI) || (netdev->mc_count > NES_MULTICAST_PF_MAX) ||
+       } else if ((netdev->flags & IFF_ALLMULTI) ||
                           (nesvnic->nic_index > 3)) {
                nic_active = nes_read_indexed(nesdev, NES_IDX_NIC_MULTICAST_ALL);
                nic_active |= nic_active_bit;
@@ -866,21 +879,37 @@ static void nes_netdev_set_multicast_list(struct net_device *netdev)
        }
 
        nes_debug(NES_DBG_NIC_RX, "Number of MC entries = %d, Promiscous = %d, All Multicast = %d.\n",
-                         netdev->mc_count, (netdev->flags & IFF_PROMISC)?1:0,
-                         (netdev->flags & IFF_ALLMULTI)?1:0);
+                 netdev->mc_count, !!(netdev->flags & IFF_PROMISC),
+                 !!(netdev->flags & IFF_ALLMULTI));
        if (!mc_all_on) {
                multicast_addr = netdev->mc_list;
-               perfect_filter_register_address = NES_IDX_PERFECT_FILTER_LOW + 0x80;
-               perfect_filter_register_address += nesvnic->nic_index*0x40;
-               for (mc_index=0; mc_index < NES_MULTICAST_PF_MAX; mc_index++) {
-                       while (multicast_addr && nesvnic->mcrq_mcast_filter && ((mc_nic_index = nesvnic->mcrq_mcast_filter(nesvnic, multicast_addr->dmi_addr)) == 0))
+               perfect_filter_register_address = NES_IDX_PERFECT_FILTER_LOW +
+                                               pft_entries_preallocated * 0x8;
+               for (mc_index = 0; mc_index < max_pft_entries_avaiable;
+               mc_index++) {
+                       while (multicast_addr && nesvnic->mcrq_mcast_filter &&
+                       ((mc_nic_index = nesvnic->mcrq_mcast_filter(nesvnic,
+                                       multicast_addr->dmi_addr)) == 0)) {
                                multicast_addr = multicast_addr->next;
+                       }
                        if (mc_nic_index < 0)
                                mc_nic_index = nesvnic->nic_index;
+                       while (nesadapter->pft_mcast_map[mc_index] < 16 &&
+                               nesadapter->pft_mcast_map[mc_index] !=
+                                       nesvnic->nic_index &&
+                                       mc_index < max_pft_entries_avaiable) {
+                                               nes_debug(NES_DBG_NIC_RX,
+                                       "mc_index=%d skipping nic_index=%d,\
+                                       used for=%d \n", mc_index,
+                                       nesvnic->nic_index,
+                                       nesadapter->pft_mcast_map[mc_index]);
+                               mc_index++;
+                       }
+                       if (mc_index >= max_pft_entries_avaiable)
+                               break;
                        if (multicast_addr) {
-                               DECLARE_MAC_BUF(mac);
-                               nes_debug(NES_DBG_NIC_RX, "Assigning MC Address %s to register 0x%04X nic_idx=%d\n",
-                                         print_mac(mac, multicast_addr->dmi_addr),
+                               nes_debug(NES_DBG_NIC_RX, "Assigning MC Address %pM to register 0x%04X nic_idx=%d\n",
+                                         multicast_addr->dmi_addr,
                                          perfect_filter_register_address+(mc_index * 8),
                                          mc_nic_index);
                                macaddr_high  = ((u16)multicast_addr->dmi_addr[0]) << 8;
@@ -897,15 +926,33 @@ static void nes_netdev_set_multicast_list(struct net_device *netdev)
                                                (u32)macaddr_high | NES_MAC_ADDR_VALID |
                                                ((((u32)(1<<mc_nic_index)) << 16)));
                                multicast_addr = multicast_addr->next;
+                               nesadapter->pft_mcast_map[mc_index] =
+                                                       nesvnic->nic_index;
                        } else {
                                nes_debug(NES_DBG_NIC_RX, "Clearing MC Address at register 0x%04X\n",
                                                  perfect_filter_register_address+(mc_index * 8));
                                nes_write_indexed(nesdev,
                                                perfect_filter_register_address+4+(mc_index * 8),
                                                0);
+                               nesadapter->pft_mcast_map[mc_index] = 255;
                        }
                }
+               /* PFT is not large enough */
+               if (multicast_addr && multicast_addr->next) {
+                       nic_active = nes_read_indexed(nesdev,
+                                               NES_IDX_NIC_MULTICAST_ALL);
+                       nic_active |= nic_active_bit;
+                       nes_write_indexed(nesdev, NES_IDX_NIC_MULTICAST_ALL,
+                                                               nic_active);
+                       nic_active = nes_read_indexed(nesdev,
+                                               NES_IDX_NIC_UNICAST_ALL);
+                       nic_active &= ~nic_active_bit;
+                       nes_write_indexed(nesdev, NES_IDX_NIC_UNICAST_ALL,
+                                                               nic_active);
+               }
        }
+
+       spin_unlock_irqrestore(&nesadapter->resource_lock, flags);
 }
 
 
@@ -918,6 +965,10 @@ static int nes_netdev_change_mtu(struct net_device *netdev, int new_mtu)
        struct nes_device *nesdev = nesvnic->nesdev;
        int ret = 0;
        u8 jumbomode = 0;
+       u32 nic_active;
+       u32 nic_active_bit;
+       u32 uc_all_active;
+       u32 mc_all_active;
 
        if ((new_mtu < ETH_ZLEN) || (new_mtu > max_mtu))
                return -EINVAL;
@@ -931,8 +982,24 @@ static int nes_netdev_change_mtu(struct net_device *netdev, int new_mtu)
        nes_nic_init_timer_defaults(nesdev, jumbomode);
 
        if (netif_running(netdev)) {
+               nic_active_bit = 1 << nesvnic->nic_index;
+               mc_all_active = nes_read_indexed(nesdev,
+                               NES_IDX_NIC_MULTICAST_ALL) & nic_active_bit;
+               uc_all_active = nes_read_indexed(nesdev,
+                               NES_IDX_NIC_UNICAST_ALL)  & nic_active_bit;
+
                nes_netdev_stop(netdev);
                nes_netdev_open(netdev);
+
+               nic_active = nes_read_indexed(nesdev,
+                                       NES_IDX_NIC_MULTICAST_ALL);
+               nic_active |= mc_all_active;
+               nes_write_indexed(nesdev, NES_IDX_NIC_MULTICAST_ALL,
+                                                       nic_active);
+
+               nic_active = nes_read_indexed(nesdev, NES_IDX_NIC_UNICAST_ALL);
+               nic_active |= uc_all_active;
+               nes_write_indexed(nesdev, NES_IDX_NIC_UNICAST_ALL, nic_active);
        }
 
        return ret;
@@ -1208,10 +1275,12 @@ static void nes_netdev_get_drvinfo(struct net_device *netdev,
                struct ethtool_drvinfo *drvinfo)
 {
        struct nes_vnic *nesvnic = netdev_priv(netdev);
+       struct nes_adapter *nesadapter = nesvnic->nesdev->nesadapter;
 
        strcpy(drvinfo->driver, DRV_NAME);
        strcpy(drvinfo->bus_info, pci_name(nesvnic->nesdev->pcidev));
-       strcpy(drvinfo->fw_version, "TBD");
+       sprintf(drvinfo->fw_version, "%u.%u", nesadapter->firmware_version>>16,
+                               nesadapter->firmware_version & 0x000000ff);
        strcpy(drvinfo->version, DRV_VERSION);
        drvinfo->n_stats = nes_netdev_get_stats_count(netdev);
        drvinfo->testinfo_len = 0;
@@ -1587,7 +1656,9 @@ struct net_device *nes_netdev_init(struct nes_device *nesdev,
                        nesvnic, (unsigned long)netdev->features, nesvnic->nic.qp_id,
                        nesvnic->nic_index, nesvnic->logical_port,  nesdev->mac_index);
 
-       if (nesvnic->nesdev->nesadapter->port_count == 1) {
+       if (nesvnic->nesdev->nesadapter->port_count == 1 &&
+               nesvnic->nesdev->nesadapter->adapter_fcn_count == 1) {
+
                nesvnic->qp_nic_index[0] = nesvnic->nic_index;
                nesvnic->qp_nic_index[1] = nesvnic->nic_index + 1;
                if (nes_drv_opt & NES_DRV_OPT_DUAL_LOGICAL_PORT) {
@@ -1598,11 +1669,14 @@ struct net_device *nes_netdev_init(struct nes_device *nesdev,
                        nesvnic->qp_nic_index[3] = nesvnic->nic_index + 3;
                }
        } else {
-               if (nesvnic->nesdev->nesadapter->port_count == 2) {
-                       nesvnic->qp_nic_index[0] = nesvnic->nic_index;
-                       nesvnic->qp_nic_index[1] = nesvnic->nic_index + 2;
-                       nesvnic->qp_nic_index[2] = 0xf;
-                       nesvnic->qp_nic_index[3] = 0xf;
+               if (nesvnic->nesdev->nesadapter->port_count == 2 ||
+                       (nesvnic->nesdev->nesadapter->port_count == 1 &&
+                       nesvnic->nesdev->nesadapter->adapter_fcn_count == 2)) {
+                               nesvnic->qp_nic_index[0] = nesvnic->nic_index;
+                               nesvnic->qp_nic_index[1] = nesvnic->nic_index
+                                                                       + 2;
+                               nesvnic->qp_nic_index[2] = 0xf;
+                               nesvnic->qp_nic_index[3] = 0xf;
                } else {
                        nesvnic->qp_nic_index[0] = nesvnic->nic_index;
                        nesvnic->qp_nic_index[1] = 0xf;
This page took 0.037726 seconds and 5 git commands to generate.