Author: mav
Date: Tue Dec 22 12:54:13 2015
New Revision: 292597
URL: https://svnweb.freebsd.org/changeset/base/292597

Log:
  MFC r291868: Rework WWNs generation to make cards without NVRAM more useful.

Modified:
  stable/10/sys/dev/isp/isp_freebsd.c
Directory Properties:
  stable/10/   (props changed)

Modified: stable/10/sys/dev/isp/isp_freebsd.c
==============================================================================
--- stable/10/sys/dev/isp/isp_freebsd.c Tue Dec 22 12:53:01 2015        
(r292596)
+++ stable/10/sys/dev/isp/isp_freebsd.c Tue Dec 22 12:54:13 2015        
(r292597)
@@ -4550,91 +4550,52 @@ isp_uninit(ispsoftc_t *isp)
        ISP_DISABLE_INTS(isp);
 }
 
-/*
- * When we want to get the 'default' WWNs (when lacking NVRAM), we pick them
- * up from our platform default (defww{p|n}n) and morph them based upon
- * channel.
- * 
- * When we want to get the 'active' WWNs, we get NVRAM WWNs and then morph them
- * based upon channel.
- */
-
 uint64_t
 isp_default_wwn(ispsoftc_t * isp, int chan, int isactive, int iswwnn)
 {
        uint64_t seed;
        struct isp_fc *fc = ISP_FC_PC(isp, chan);
 
-       /*
-        * If we're asking for a active WWN, the default overrides get
-        * returned, otherwise the NVRAM value is picked.
-        * 
-        * If we're asking for a default WWN, we just pick the default override.
-        */
+       /* First try to use explicitly configured WWNs. */
+       seed = iswwnn ? fc->def_wwnn : fc->def_wwpn;
+       if (seed)
+               return (seed);
+
+       /* Otherwise try to use WWNs from NVRAM. */
        if (isactive) {
-               seed = iswwnn ? fc->def_wwnn : fc->def_wwpn;
-               if (seed) {
-                       return (seed);
-               }
-               seed = iswwnn ? FCPARAM(isp, chan)->isp_wwnn_nvram : 
FCPARAM(isp, chan)->isp_wwpn_nvram;
-               if (seed) {
+               seed = iswwnn ? FCPARAM(isp, chan)->isp_wwnn_nvram :
+                   FCPARAM(isp, chan)->isp_wwpn_nvram;
+               if (seed)
                        return (seed);
-               }
-               return (0x400000007F000009ull);
        }
 
-       seed = iswwnn ? fc->def_wwnn : fc->def_wwpn;
-
-       /*
-        * For channel zero just return what we have. For either ACTIVE or
-        * DEFAULT cases, we depend on default override of NVRAM values for
-        * channel zero.
-        */
-       if (chan == 0) {
-               return (seed);
+       /* If still no WWNs, try to steal them from the first channel. */
+       if (chan > 0) {
+               seed = iswwnn ? ISP_FC_PC(isp, 0)->def_wwnn :
+                   ISP_FC_PC(isp, 0)->def_wwpn;
+               if (seed == 0) {
+                       seed = iswwnn ? FCPARAM(isp, 0)->isp_wwnn_nvram :
+                           FCPARAM(isp, 0)->isp_wwpn_nvram;
+               }
        }
 
-       /*
-        * For other channels, we are doing one of three things:
-        * 
-        * 1. If what we have now is non-zero, return it. Otherwise we morph
-        * values from channel 0. 2. If we're here for a WWPN we synthesize
-        * it if Channel 0's wwpn has a type 2 NAA. 3. If we're here for a
-        * WWNN we synthesize it if Channel 0's wwnn has a type 2 NAA.
-        */
-
-       if (seed) {
-               return (seed);
+       /* If still nothing -- improvise. */
+       if (seed == 0) {
+               seed = 0x400000007F000000ull + device_get_unit(isp->isp_dev);
+               if (!iswwnn)
+                       seed ^= 0x0100000000000000ULL;
        }
-       seed = iswwnn ? ISP_FC_PC(isp, 0)->def_wwnn : ISP_FC_PC(isp, 
0)->def_wwpn;
-       if (seed == 0)
-               seed = iswwnn ? FCPARAM(isp, 0)->isp_wwnn_nvram : FCPARAM(isp, 
0)->isp_wwpn_nvram;
 
-       if (((seed >> 60) & 0xf) == 2) {
+       /* For additional channels we have to improvise even more. */
+       if (!iswwnn && chan > 0) {
                /*
-                * The type 2 NAA fields for QLogic cards appear be laid out
-                * thusly:
-                * 
-                * bits 63..60 NAA == 2 bits 59..57 unused/zero bit 56
-                * port (1) or node (0) WWN distinguishor bit 48
-                * physical port on dual-port chips (23XX/24XX)
-                * 
-                * This is somewhat nutty, particularly since bit 48 is
-                * irrelevant as they assign separate serial numbers to
-                * different physical ports anyway.
-                * 
                 * We'll stick our channel number plus one first into bits
                 * 57..59 and thence into bits 52..55 which allows for 8 bits
-                * of channel which is comfortably more than our maximum
-                * (126) now.
+                * of channel which is enough for our maximum of 255 channels.
                 */
-               seed &= ~0x0FF0000000000000ULL;
-               if (iswwnn == 0) {
-                       seed |= ((uint64_t) (chan + 1) & 0xf) << 56;
-                       seed |= ((uint64_t) ((chan + 1) >> 4) & 0xf) << 52;
-               }
-       } else {
-               seed = 0;
+               seed ^= 0x0100000000000000ULL;
+               seed ^= ((uint64_t) (chan + 1) & 0xf) << 56;
+               seed ^= ((uint64_t) ((chan + 1) >> 4) & 0xf) << 52;
        }
        return (seed);
 }
_______________________________________________
svn-src-stable-10@freebsd.org mailing list
https://lists.freebsd.org/mailman/listinfo/svn-src-stable-10
To unsubscribe, send any mail to "svn-src-stable-10-unsubscr...@freebsd.org"

Reply via email to