Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 9 Jul 2018 21:13:22 +0000 (UTC)
From:      David C Somayajulu <davidcs@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-11@freebsd.org
Subject:   svn commit: r336146 - stable/11/sys/dev/bxe
Message-ID:  <201807092113.w69LDMCw066301@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: davidcs
Date: Mon Jul  9 21:13:21 2018
New Revision: 336146
URL: https://svnweb.freebsd.org/changeset/base/336146

Log:
  MFC r333004
    Fix Issue with adding MultiCast Addresses. When multicast addresses are
    added/deleted, the delete the multicast addresses previously programmed
    in HW and reprogram the new set of multicast addresses.
  
  Submitted by:	Vaishali.Kulkarni@cavium.com

Modified:
  stable/11/sys/dev/bxe/bxe.c
Directory Properties:
  stable/11/   (props changed)

Modified: stable/11/sys/dev/bxe/bxe.c
==============================================================================
--- stable/11/sys/dev/bxe/bxe.c	Mon Jul  9 20:38:47 2018	(r336145)
+++ stable/11/sys/dev/bxe/bxe.c	Mon Jul  9 21:13:21 2018	(r336146)
@@ -27,7 +27,7 @@
 #include <sys/cdefs.h>
 __FBSDID("$FreeBSD$");
 
-#define BXE_DRIVER_VERSION "1.78.90"
+#define BXE_DRIVER_VERSION "1.78.91"
 
 #include "bxe.h"
 #include "ecore_sp.h"
@@ -11991,84 +11991,107 @@ bxe_initial_phy_init(struct bxe_softc *sc,
 }
 
 /* must be called under IF_ADDR_LOCK */
-
 static int
-bxe_set_mc_list(struct bxe_softc *sc)
+bxe_init_mcast_macs_list(struct bxe_softc                 *sc,
+                         struct ecore_mcast_ramrod_params *p)
 {
-    struct ecore_mcast_ramrod_params rparam = { NULL };
-    int rc = 0;
-    int mc_count = 0;
-    int mcnt, i;
-    struct ecore_mcast_list_elem *mc_mac, *mc_mac_start;
-    unsigned char *mta;
     if_t ifp = sc->ifp;
+    int mc_count = 0;
+    struct ifmultiaddr *ifma;
+    struct ecore_mcast_list_elem *mc_mac;
 
-    mc_count = if_multiaddr_count(ifp, -1);/* XXX they don't have a limit */
-    if (!mc_count)
-        return (0);
+    TAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
+        if (ifma->ifma_addr->sa_family != AF_LINK) {
+            continue;
+        }
 
-    mta = malloc(sizeof(unsigned char) * ETHER_ADDR_LEN *
-            mc_count, M_DEVBUF, M_NOWAIT);
+        mc_count++;
+    }
 
-    if(mta == NULL) {
-        BLOGE(sc, "Failed to allocate temp mcast list\n");
-        return (-1);
+    ECORE_LIST_INIT(&p->mcast_list);
+    p->mcast_list_len = 0;
+
+    if (!mc_count) {
+        return (0);
     }
-    bzero(mta, (sizeof(unsigned char) * ETHER_ADDR_LEN * mc_count));
-    
-    mc_mac = malloc(sizeof(*mc_mac) * mc_count, M_DEVBUF, (M_NOWAIT | M_ZERO));
-    mc_mac_start = mc_mac;
 
+    mc_mac = malloc(sizeof(*mc_mac) * mc_count, M_DEVBUF,
+                    (M_NOWAIT | M_ZERO));
     if (!mc_mac) {
-        free(mta, M_DEVBUF);
         BLOGE(sc, "Failed to allocate temp mcast list\n");
         return (-1);
     }
     bzero(mc_mac, (sizeof(*mc_mac) * mc_count));
 
-    /* mta and mcnt not expected to be  different */
-    if_multiaddr_array(ifp, mta, &mcnt, mc_count);
+    TAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
+        if (ifma->ifma_addr->sa_family != AF_LINK) {
+            continue;
+        }
 
+        mc_mac->mac = (uint8_t *)LLADDR((struct sockaddr_dl *)ifma->ifma_addr);
+        ECORE_LIST_PUSH_TAIL(&mc_mac->link, &p->mcast_list);
 
-    rparam.mcast_obj = &sc->mcast_obj;
-    ECORE_LIST_INIT(&rparam.mcast_list);
+        BLOGD(sc, DBG_LOAD,
+              "Setting MCAST %02X:%02X:%02X:%02X:%02X:%02X and mc_count %d\n",
+              mc_mac->mac[0], mc_mac->mac[1], mc_mac->mac[2],
+              mc_mac->mac[3], mc_mac->mac[4], mc_mac->mac[5], mc_count);
+       mc_mac++;
+    }
 
-    for(i=0; i< mcnt; i++) {
+    p->mcast_list_len = mc_count;
 
-        mc_mac->mac = (uint8_t *)(mta + (i * ETHER_ADDR_LEN));
-        ECORE_LIST_PUSH_TAIL(&mc_mac->link, &rparam.mcast_list);
+    return (0);
+}
 
-        BLOGD(sc, DBG_LOAD,
-              "Setting MCAST %02X:%02X:%02X:%02X:%02X:%02X\n",
-              mc_mac->mac[0], mc_mac->mac[1], mc_mac->mac[2],
-              mc_mac->mac[3], mc_mac->mac[4], mc_mac->mac[5]);
+static void
+bxe_free_mcast_macs_list(struct ecore_mcast_ramrod_params *p)
+{
+    struct ecore_mcast_list_elem *mc_mac =
+        ECORE_LIST_FIRST_ENTRY(&p->mcast_list,
+                               struct ecore_mcast_list_elem,
+                               link);
 
-        mc_mac++;
+    if (mc_mac) {
+        /* only a single free as all mc_macs are in the same heap array */
+        free(mc_mac, M_DEVBUF);
     }
-    rparam.mcast_list_len = mc_count;
+}
+static int
+bxe_set_mc_list(struct bxe_softc *sc)
+{
+    struct ecore_mcast_ramrod_params rparam = { NULL };
+    int rc = 0;
 
+    rparam.mcast_obj = &sc->mcast_obj;
+
     BXE_MCAST_LOCK(sc);
 
     /* first, clear all configured multicast MACs */
     rc = ecore_config_mcast(sc, &rparam, ECORE_MCAST_CMD_DEL);
     if (rc < 0) {
         BLOGE(sc, "Failed to clear multicast configuration: %d\n", rc);
+        /* Manual backport parts of FreeBSD upstream r284470. */
         BXE_MCAST_UNLOCK(sc);
-    	free(mc_mac_start, M_DEVBUF);
-        free(mta, M_DEVBUF);
         return (rc);
     }
 
+    /* configure a new MACs list */
+    rc = bxe_init_mcast_macs_list(sc, &rparam);
+    if (rc) {
+        BLOGE(sc, "Failed to create mcast MACs list (%d)\n", rc);
+        BXE_MCAST_UNLOCK(sc);
+        return (rc);
+    }
+
     /* Now add the new MACs */
     rc = ecore_config_mcast(sc, &rparam, ECORE_MCAST_CMD_ADD);
     if (rc < 0) {
         BLOGE(sc, "Failed to set new mcast config (%d)\n", rc);
     }
 
-    BXE_MCAST_UNLOCK(sc);
+    bxe_free_mcast_macs_list(&rparam);
 
-    free(mc_mac_start, M_DEVBUF);
-    free(mta, M_DEVBUF);
+    BXE_MCAST_UNLOCK(sc);
 
     return (rc);
 }



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201807092113.w69LDMCw066301>