Skip site navigation (1)Skip section navigation (2)
Date:      Tue, 5 Dec 2006 22:05:48 GMT
From:      Matt Jacob <mjacob@FreeBSD.org>
To:        Perforce Change Reviews <perforce@freebsd.org>
Subject:   PERFORCE change 111162 for review
Message-ID:  <200612052205.kB5M5mES092169@repoman.freebsd.org>

next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=111162

Change 111162 by mjacob@newisp on 2006/12/05 22:04:59

	Begin another process of cleanup where we try to follow the
	Fusion spec a bit more closely and be a bit more generic in
	our endian cleanliness.

Affected files ...

.. //depot/projects/newisp/dev/mpt/mpt.c#6 edit
.. //depot/projects/newisp/dev/mpt/mpt.h#8 edit
.. //depot/projects/newisp/dev/mpt/mpt_cam.c#19 edit
.. //depot/projects/newisp/dev/mpt/mpt_cam.h#2 edit
.. //depot/projects/newisp/dev/mpt/mpt_debug.c#2 edit
.. //depot/projects/newisp/dev/mpt/mpt_raid.c#6 edit

Differences ...

==== //depot/projects/newisp/dev/mpt/mpt.c#6 (text+ko) ====

@@ -128,7 +128,7 @@
 static int mpt_send_event_request(struct mpt_softc *mpt, int onoff);
 static int mpt_soft_reset(struct mpt_softc *mpt);
 static void mpt_hard_reset(struct mpt_softc *mpt);
-static int mpt_configure_ioc(struct mpt_softc *mpt);
+static int mpt_configure_ioc(struct mpt_softc *mpt, int, int);
 static int mpt_enable_ioc(struct mpt_softc *mpt, int);
 
 /************************* Personality Module Support *************************/
@@ -1484,25 +1484,27 @@
 	f_req.Function = MPI_FUNCTION_IOC_FACTS;
 	f_req.MsgContext = htole32(MPT_REPLY_HANDLER_HANDSHAKE);
 	error = mpt_send_handshake_cmd(mpt, sizeof f_req, &f_req);
-	if (error)
+	if (error) {
 		return(error);
+	}
 	error = mpt_recv_handshake_reply(mpt, sizeof (*freplp), freplp);
 	return (error);
 }
 
 static int
-mpt_get_portfacts(struct mpt_softc *mpt, MSG_PORT_FACTS_REPLY *freplp)
+mpt_get_portfacts(struct mpt_softc *mpt, U8 port, MSG_PORT_FACTS_REPLY *freplp)
 {
 	MSG_PORT_FACTS f_req;
 	int error;
 	
-	/* XXX: Only getting PORT FACTS for Port 0 */
 	memset(&f_req, 0, sizeof f_req);
 	f_req.Function = MPI_FUNCTION_PORT_FACTS;
+	f_req.PortNumber = port;
 	f_req.MsgContext = htole32(MPT_REPLY_HANDLER_HANDSHAKE);
 	error = mpt_send_handshake_cmd(mpt, sizeof f_req, &f_req);
-	if (error)
+	if (error) {
 		return(error);
+	}
 	error = mpt_recv_handshake_reply(mpt, sizeof (*freplp), freplp);
 	return (error);
 }
@@ -1523,8 +1525,8 @@
 	memset(&init, 0, sizeof init);
 	init.WhoInit = who;
 	init.Function = MPI_FUNCTION_IOC_INIT;
-	init.MaxDevices = mpt->mpt_max_devices;
-	init.MaxBuses = 1;
+	init.MaxDevices = 0;	/* at least 256 devices per bus */
+	init.MaxBuses = 16;	/* at least 16 busses */
 
 	init.MsgVersion = htole16(MPI_VERSION);
 	init.HeaderVersion = htole16(MPI_HEADER_VERSION);
@@ -1759,17 +1761,10 @@
 		return (rv);
 	}
 
-#if __FreeBSD_version >= 500000
-	mpt_lprt(mpt, MPT_PRT_DEBUG,  "IOC Page 2 Header: ver %x, len %zx, "
-		 "num %x, type %x\n", hdr.PageVersion,
-		 hdr.PageLength * sizeof(uint32_t),
-		 hdr.PageNumber, hdr.PageType);
-#else
-	mpt_lprt(mpt, MPT_PRT_DEBUG,  "IOC Page 2 Header: ver %x, len %z, "
-		 "num %x, type %x\n", hdr.PageVersion,
-		 hdr.PageLength * sizeof(uint32_t),
-		 hdr.PageNumber, hdr.PageType);
-#endif
+	mpt_lprt(mpt, MPT_PRT_DEBUG,
+	    "IOC Page 2 Header: Version %x len %x PageNumber %x PageType %x\n",
+	    hdr.PageVersion, hdr.PageLength << 2,
+	    hdr.PageNumber, hdr.PageType);
 
 	len = hdr.PageLength * sizeof(uint32_t);
 	mpt->ioc_page2 = malloc(len, M_DEVBUF, M_NOWAIT | M_ZERO);
@@ -1786,6 +1781,7 @@
 		mpt_raid_free_mem(mpt);
 		return (EIO);
 	}
+	mpt2host_config_page_ioc2(mpt->ioc_page2);
 
 	if (mpt->ioc_page2->CapabilitiesFlags != 0) {
 		uint32_t mask;
@@ -2107,11 +2103,8 @@
 mpt_core_attach(struct mpt_softc *mpt)
 {
         int val;
-	int error;
-
 
 	LIST_INIT(&mpt->ack_frames);
-
 	/* Put all request buffers on the free list */
 	TAILQ_INIT(&mpt->request_pending_list);
 	TAILQ_INIT(&mpt->request_free_list);
@@ -2121,24 +2114,17 @@
 		req->state = REQ_STATE_ALLOCATED;
 		mpt_free_request(mpt, req);
 	}
-
 	for (val = 0; val < MPT_MAX_LUNS; val++) {
 		STAILQ_INIT(&mpt->trt[val].atios);
 		STAILQ_INIT(&mpt->trt[val].inots);
 	}
 	STAILQ_INIT(&mpt->trt_wildcard.atios);
 	STAILQ_INIT(&mpt->trt_wildcard.inots);
-
 	mpt->scsi_tgt_handler_id = MPT_HANDLER_ID_NONE;
-
 	mpt_sysctl_attach(mpt);
-
 	mpt_lprt(mpt, MPT_PRT_DEBUG, "doorbell req = %s\n",
 	    mpt_ioc_diag(mpt_read(mpt, MPT_OFFSET_DOORBELL)));
-
-	error = mpt_configure_ioc(mpt);
-
-	return (error);
+	return (mpt_configure_ioc(mpt, 0, 0));
 }
 
 int
@@ -2197,6 +2183,9 @@
 void
 mpt_core_detach(struct mpt_softc *mpt)
 {
+	/*
+	 * XXX: FREE MEMORY 
+	 */
 	mpt_disable_ints(mpt);
 }
 
@@ -2337,226 +2326,239 @@
  * once at instance startup.
  */
 static int
-mpt_configure_ioc(struct mpt_softc *mpt)
+mpt_configure_ioc(struct mpt_softc *mpt, int tn, int needreset)
 {
-        MSG_PORT_FACTS_REPLY pfp;
-        MSG_IOC_FACTS_REPLY facts;
-	int try;
-	int needreset;
-	uint32_t max_chain_depth;
+	PTR_MSG_PORT_FACTS_REPLY pfp;
+	int error,  port;
+	size_t len;
 
-	needreset = 0;
-	for (try = 0; try < MPT_MAX_TRYS; try++) {
+	if (tn == MPT_MAX_TRYS) {
+		return (-1);
+	}
 
-		/*
-		 * No need to reset if the IOC is already in the READY state.
-		 *
-		 * Force reset if initialization failed previously.
-		 * Note that a hard_reset of the second channel of a '929
-		 * will stop operation of the first channel.  Hopefully, if the
-		 * first channel is ok, the second will not require a hard
-		 * reset.
-		 */
-		if (needreset || MPT_STATE(mpt_rd_db(mpt)) !=
-		    MPT_DB_STATE_READY) {
-			if (mpt_reset(mpt, FALSE) != MPT_OK) {
-				continue;
-			}
+	/*
+	 * No need to reset if the IOC is already in the READY state.
+	 *
+	 * Force reset if initialization failed previously.
+	 * Note that a hard_reset of the second channel of a '929
+	 * will stop operation of the first channel.  Hopefully, if the
+	 * first channel is ok, the second will not require a hard
+	 * reset.
+	 */
+	if (needreset || MPT_STATE(mpt_rd_db(mpt)) != MPT_DB_STATE_READY) {
+		if (mpt_reset(mpt, FALSE) != MPT_OK) {
+			return (mpt_configure_ioc(mpt, tn++, 1));
 		}
 		needreset = 0;
+	}
 
-		if (mpt_get_iocfacts(mpt, &facts) != MPT_OK) {
-			mpt_prt(mpt, "mpt_get_iocfacts failed\n");
-			needreset = 1;
-			continue;
-		}
+	if (mpt_get_iocfacts(mpt, &mpt->ioc_facts) != MPT_OK) {
+		mpt_prt(mpt, "mpt_get_iocfacts failed\n");
+		return (mpt_configure_ioc(mpt, tn++, 1));
+	}
+	mpt2host_iocfacts_reply(&mpt->ioc_facts);
 
-		mpt->mpt_global_credits = le16toh(facts.GlobalCredits);
-		mpt->request_frame_size = le16toh(facts.RequestFrameSize);
-		mpt->ioc_facts_flags = facts.Flags;
-		mpt_prt(mpt, "MPI Version=%d.%d.%d.%d\n",
-			    le16toh(facts.MsgVersion) >> 8,
-			    le16toh(facts.MsgVersion) & 0xFF,
-			    le16toh(facts.HeaderVersion) >> 8,
-			    le16toh(facts.HeaderVersion) & 0xFF);
+	mpt_prt(mpt, "MPI Version=%d.%d.%d.%d\n",
+	    mpt->ioc_facts.MsgVersion >> 8,
+	    mpt->ioc_facts.MsgVersion & 0xFF,
+	    mpt->ioc_facts.HeaderVersion >> 8,
+	    mpt->ioc_facts.HeaderVersion & 0xFF);
 
-		/*
-		 * Now that we know request frame size, we can calculate
-		 * the actual (reasonable) segment limit for read/write I/O.
-		 *
-		 * This limit is constrained by:
-		 *
-		 *  + The size of each area we allocate per command (and how
-                 *    many chain segments we can fit into it).
-                 *  + The total number of areas we've set up.
-		 *  + The actual chain depth the card will allow.
-		 *
-		 * The first area's segment count is limited by the I/O request
-		 * at the head of it. We cannot allocate realistically more
-		 * than MPT_MAX_REQUESTS areas. Therefore, to account for both
-		 * conditions, we'll just start out with MPT_MAX_REQUESTS-2.
-		 *
-		 */
-		max_chain_depth = facts.MaxChainDepth;
+	/*
+	 * Now that we know request frame size, we can calculate
+	 * the actual (reasonable) segment limit for read/write I/O.
+	 *
+	 * This limit is constrained by:
+	 *
+	 *  + The size of each area we allocate per command (and how
+	 *    many chain segments we can fit into it).
+	 *  + The total number of areas we've set up.
+	 *  + The actual chain depth the card will allow.
+	 *
+	 * The first area's segment count is limited by the I/O request
+	 * at the head of it. We cannot allocate realistically more
+	 * than MPT_MAX_REQUESTS areas. Therefore, to account for both
+	 * conditions, we'll just start out with MPT_MAX_REQUESTS-2.
+	 *
+	 */
+	/* total number of request areas we (can) allocate */
+	mpt->max_seg_cnt = MPT_MAX_REQUESTS(mpt) - 2;
 
-		/* total number of request areas we (can) allocate */
-		mpt->max_seg_cnt = MPT_MAX_REQUESTS(mpt) - 2;
+	/* converted to the number of chain areas possible */
+	mpt->max_seg_cnt *= MPT_NRFM(mpt);
 
-		/* converted to the number of chain areas possible */
-		mpt->max_seg_cnt *= MPT_NRFM(mpt);
+	/* limited by the number of chain areas the card will support */
+	if (mpt->max_seg_cnt > mpt->ioc_facts.MaxChainDepth) {
+		mpt_lprt(mpt, MPT_PRT_DEBUG,
+		    "chain depth limited to %u (from %u)\n",
+		    mpt->ioc_facts.MaxChainDepth, mpt->max_seg_cnt);
+		mpt->max_seg_cnt = mpt->ioc_facts.MaxChainDepth;
+	}
 
-		/* limited by the number of chain areas the card will support */
-		if (mpt->max_seg_cnt > max_chain_depth) {
-			mpt_lprt(mpt, MPT_PRT_DEBUG,
-			    "chain depth limited to %u (from %u)\n",
-			    max_chain_depth, mpt->max_seg_cnt);
-			mpt->max_seg_cnt = max_chain_depth;
-		}
+	/* converted to the number of simple sges in chain segments. */
+	mpt->max_seg_cnt *= (MPT_NSGL(mpt) - 1);
 
-		/* converted to the number of simple sges in chain segments. */
-		mpt->max_seg_cnt *= (MPT_NSGL(mpt) - 1);
+	mpt_lprt(mpt, MPT_PRT_DEBUG, "Maximum Segment Count: %u\n",
+	    mpt->max_seg_cnt);
+	mpt_lprt(mpt, MPT_PRT_DEBUG, "MsgLength=%u IOCNumber = %d\n",
+	    mpt->ioc_facts.MsgLength, mpt->ioc_facts.IOCNumber);
+	mpt_lprt(mpt, MPT_PRT_DEBUG,
+	    "IOCFACTS: GlobalCredits=%d BlockSize=%u bytes "
+	    "Request Frame Size %u bytes Max Chain Depth %u\n",
+	    mpt->ioc_facts.GlobalCredits, mpt->ioc_facts.BlockSize,
+	    mpt->ioc_facts.RequestFrameSize << 2,
+	    mpt->ioc_facts.MaxChainDepth);
+	mpt_lprt(mpt, MPT_PRT_DEBUG, "IOCFACTS: Num Ports %d, FWImageSize %d, "
+	    "Flags=%#x\n", mpt->ioc_facts.NumberOfPorts,
+	    mpt->ioc_facts.FWImageSize, mpt->ioc_facts.Flags);
 
-		mpt_lprt(mpt, MPT_PRT_DEBUG,
-		    "Maximum Segment Count: %u\n", mpt->max_seg_cnt);
-		mpt_lprt(mpt, MPT_PRT_DEBUG,
-			 "MsgLength=%u IOCNumber = %d\n",
-			 facts.MsgLength, facts.IOCNumber);
-		mpt_lprt(mpt, MPT_PRT_DEBUG,
-			 "IOCFACTS: GlobalCredits=%d BlockSize=%u bytes "
-			 "Request Frame Size %u bytes Max Chain Depth %u\n",
-                         mpt->mpt_global_credits, facts.BlockSize,
-                         mpt->request_frame_size << 2, max_chain_depth);
-		mpt_lprt(mpt, MPT_PRT_DEBUG,
-			 "IOCFACTS: Num Ports %d, FWImageSize %d, "
-			 "Flags=%#x\n", facts.NumberOfPorts,
-			 le32toh(facts.FWImageSize), facts.Flags);
+	len = mpt->ioc_facts.NumberOfPorts * sizeof (MSG_PORT_FACTS_REPLY);
+	mpt->port_facts = malloc(len, M_DEVBUF, M_NOWAIT | M_ZERO);
+	if (mpt->port_facts == NULL) {
+		mpt_prt(mpt, "unable to allocate memory for port facts\n");
+		return (ENOMEM);
+	}
 
 
-		if ((facts.Flags & MPI_IOCFACTS_FLAGS_FW_DOWNLOAD_BOOT) != 0) {
-			struct mpt_map_info mi;
-			int error;
+	if ((mpt->ioc_facts.Flags & MPI_IOCFACTS_FLAGS_FW_DOWNLOAD_BOOT) &&
+	    (mpt->fw_uploaded == 0)) {
+		struct mpt_map_info mi;
 
-			/*
-			 * In some configurations, the IOC's firmware is
-			 * stored in a shared piece of system NVRAM that
-			 * is only accessable via the BIOS.  In this
-			 * case, the firmware keeps a copy of firmware in
-			 * RAM until the OS driver retrieves it.  Once
-			 * retrieved, we are responsible for re-downloading
-			 * the firmware after any hard-reset.
-			 */
-			mpt->fw_image_size = le32toh(facts.FWImageSize);
-			error = mpt_dma_tag_create(mpt, mpt->parent_dmat,
-			    /*alignment*/1, /*boundary*/0,
-			    /*lowaddr*/BUS_SPACE_MAXADDR_32BIT,
-			    /*highaddr*/BUS_SPACE_MAXADDR, /*filter*/NULL,
-			    /*filterarg*/NULL, mpt->fw_image_size,
-			    /*nsegments*/1, /*maxsegsz*/mpt->fw_image_size,
-			    /*flags*/0, &mpt->fw_dmat);
-			if (error != 0) {
-				mpt_prt(mpt, "cannot create fw dma tag\n");
-				return (ENOMEM);
-			}
-			error = bus_dmamem_alloc(mpt->fw_dmat,
-			    (void **)&mpt->fw_image, BUS_DMA_NOWAIT,
-			    &mpt->fw_dmap);
-			if (error != 0) {
-				mpt_prt(mpt, "cannot allocate fw mem.\n");
-				bus_dma_tag_destroy(mpt->fw_dmat);
-				return (ENOMEM);
-			}
-			mi.mpt = mpt;
-			mi.error = 0;
-			bus_dmamap_load(mpt->fw_dmat, mpt->fw_dmap,
-			    mpt->fw_image, mpt->fw_image_size, mpt_map_rquest,
-			    &mi, 0);
-			mpt->fw_phys = mi.phys;
-
-			error = mpt_upload_fw(mpt);
-			if (error != 0) {
-				mpt_prt(mpt, "fw upload failed.\n");
-				bus_dmamap_unload(mpt->fw_dmat, mpt->fw_dmap);
-				bus_dmamem_free(mpt->fw_dmat, mpt->fw_image,
-				    mpt->fw_dmap);
-				bus_dma_tag_destroy(mpt->fw_dmat);
-				mpt->fw_image = NULL;
-				return (EIO);
-			}
+		/*
+		 * In some configurations, the IOC's firmware is
+		 * stored in a shared piece of system NVRAM that
+		 * is only accessable via the BIOS.  In this
+		 * case, the firmware keeps a copy of firmware in
+		 * RAM until the OS driver retrieves it.  Once
+		 * retrieved, we are responsible for re-downloading
+		 * the firmware after any hard-reset.
+		 */
+		mpt->fw_image_size = mpt->ioc_facts.FWImageSize;
+		error = mpt_dma_tag_create(mpt, mpt->parent_dmat, 1, 0,
+		    BUS_SPACE_MAXADDR_32BIT, BUS_SPACE_MAXADDR, NULL, NULL,
+		    mpt->fw_image_size, 1, mpt->fw_image_size, 0,
+		    &mpt->fw_dmat);
+		if (error != 0) {
+			mpt_prt(mpt, "cannot create firmwarew dma tag\n");
+			return (ENOMEM);
+		}
+		error = bus_dmamem_alloc(mpt->fw_dmat,
+		    (void **)&mpt->fw_image, BUS_DMA_NOWAIT, &mpt->fw_dmap);
+		if (error != 0) {
+			mpt_prt(mpt, "cannot allocate firmware memory\n");
+			bus_dma_tag_destroy(mpt->fw_dmat);
+			return (ENOMEM);
 		}
+		mi.mpt = mpt;
+		mi.error = 0;
+		bus_dmamap_load(mpt->fw_dmat, mpt->fw_dmap,
+		    mpt->fw_image, mpt->fw_image_size, mpt_map_rquest, &mi, 0);
+		mpt->fw_phys = mi.phys;
 
-		if (mpt_get_portfacts(mpt, &pfp) != MPT_OK) {
-			mpt_prt(mpt, "mpt_get_portfacts failed\n");
-			needreset = 1;
-			continue;
+		error = mpt_upload_fw(mpt);
+		if (error != 0) {
+			mpt_prt(mpt, "firmware upload failed.\n");
+			bus_dmamap_unload(mpt->fw_dmat, mpt->fw_dmap);
+			bus_dmamem_free(mpt->fw_dmat, mpt->fw_image,
+			    mpt->fw_dmap);
+			bus_dma_tag_destroy(mpt->fw_dmat);
+			mpt->fw_image = NULL;
+			return (EIO);
 		}
+		mpt->fw_uploaded = 1;
+	}
 
-		mpt_lprt(mpt, MPT_PRT_DEBUG,
-			 "PORTFACTS: Type %x PFlags %x IID %d MaxDev %d\n",
-			 pfp.PortType, pfp.ProtocolFlags, pfp.PortSCSIID,
-			 pfp.MaxDevices);
-
-		mpt->mpt_port_type = pfp.PortType;
-		mpt->mpt_proto_flags = le16toh(pfp.ProtocolFlags);
-		if (pfp.PortType != MPI_PORTFACTS_PORTTYPE_SCSI &&
-		    pfp.PortType != MPI_PORTFACTS_PORTTYPE_SAS &&
-		    pfp.PortType != MPI_PORTFACTS_PORTTYPE_FC) {
-			mpt_prt(mpt, "Unsupported Port Type (%x)\n",
-			    pfp.PortType);
-			return (ENXIO);
+	for (port = 0; port < mpt->ioc_facts.NumberOfPorts; port++) {
+		pfp = &mpt->port_facts[port];
+		error = mpt_get_portfacts(mpt, 0, pfp);
+		if (error != MPT_OK) {
+			mpt_prt(mpt,
+			    "mpt_get_portfacts on port %d failed\n", port);
+			free(mpt->port_facts, M_DEVBUF);
+			mpt->port_facts = NULL;
+			return (mpt_configure_ioc(mpt, tn++, 1));
 		}
-		mpt->mpt_max_tgtcmds = le16toh(pfp.MaxPostedCmdBuffers);
+		mpt2host_portfacts_reply(pfp);
 
-		if (pfp.PortType == MPI_PORTFACTS_PORTTYPE_FC) {
-			mpt->is_fc = 1;
-			mpt->is_sas = 0;
-			mpt->is_spi = 0;
-		} else if (pfp.PortType == MPI_PORTFACTS_PORTTYPE_SAS) {
-			mpt->is_fc = 0;
-			mpt->is_sas = 1;
-			mpt->is_spi = 0;
+		if (port > 0) {
+			error = MPT_PRT_INFO;
 		} else {
-			mpt->is_fc = 0;
-			mpt->is_sas = 0;
-			mpt->is_spi = 1;
+			error = MPT_PRT_DEBUG;
 		}
-		mpt->mpt_ini_id = pfp.PortSCSIID;
-		mpt->mpt_max_devices = pfp.MaxDevices;
+		mpt_lprt(mpt, error,
+		    "PORTFACTS[%d]: Type %x PFlags %x IID %d MaxDev %d\n",
+		    port, pfp->PortType, pfp->ProtocolFlags, pfp->PortSCSIID,
+		    pfp->MaxDevices);
+
+	}
+
+	/*
+	 * XXX: Not yet supporting more than port 0
+	 */
+	pfp = &mpt->port_facts[0];
+	if (pfp->PortType == MPI_PORTFACTS_PORTTYPE_FC) {
+		mpt->is_fc = 1;
+		mpt->is_sas = 0;
+		mpt->is_spi = 0;
+	} else if (pfp->PortType == MPI_PORTFACTS_PORTTYPE_SAS) {
+		mpt->is_fc = 0;
+		mpt->is_sas = 1;
+		mpt->is_spi = 0;
+	} else if (pfp->PortType == MPI_PORTFACTS_PORTTYPE_SCSI) {
+		mpt->is_fc = 0;
+		mpt->is_sas = 0;
+		mpt->is_spi = 1;
+	} else if (pfp->PortType == MPI_PORTFACTS_PORTTYPE_ISCSI) {
+		mpt_prt(mpt, "iSCSI not supported yet\n");
+		return (ENXIO);
+	} else if (pfp->PortType == MPI_PORTFACTS_PORTTYPE_INACTIVE) {
+		mpt_prt(mpt, "Inactive Port\n");
+		return (ENXIO);
+	} else {
+		mpt_prt(mpt, "unknown Port Type %#x\n", pfp->PortType);
+		return (ENXIO);
+	}
 
-		/*
-		 * Set our role with what this port supports.
-		 *
-		 * Note this might be changed later in different modules
-		 * if this is different from what is wanted.
-		 */
-		mpt->role = MPT_ROLE_NONE;
-		if (mpt->mpt_proto_flags & MPI_PORTFACTS_PROTOCOL_INITIATOR) {
-			mpt->role |= MPT_ROLE_INITIATOR;
-		}
-		if (mpt->mpt_proto_flags & MPI_PORTFACTS_PROTOCOL_TARGET) {
-			mpt->role |= MPT_ROLE_TARGET;
-		}
-		if (mpt_enable_ioc(mpt, 0) != MPT_OK) {
-			mpt_prt(mpt, "unable to initialize IOC\n");
-			return (ENXIO);
-		}
+	if (pfp->ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) {
+		mpt_prt(mpt, "not supporting LAN protocol\n");
+		return (ENXIO);
+	}
 
-		/*
-		 * Read IOC configuration information.
-		 *
-		 * We need this to determine whether or not we have certain
-		 * settings for Integrated Mirroring (e.g.).
-		 */
-		mpt_read_config_info_ioc(mpt);
+	if (pfp->ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LOGBUSADDR) {
+		mpt_prt(mpt, "not supporting Logical Bus Address protocol\n");
+		return (ENXIO);
+	}
 
-		/* Everything worked */
-		break;
+	/*
+	 * Set our role with what this port supports.
+	 *
+	 * Note this might be changed later in different modules
+	 * if this is different from what is wanted.
+	 */
+	mpt->role = MPT_ROLE_NONE;
+	if (pfp->ProtocolFlags & MPI_PORTFACTS_PROTOCOL_INITIATOR) {
+		mpt->role |= MPT_ROLE_INITIATOR;
+	}
+	if (pfp->ProtocolFlags & MPI_PORTFACTS_PROTOCOL_TARGET) {
+		mpt->role |= MPT_ROLE_TARGET;
 	}
 
-	if (try >= MPT_MAX_TRYS) {
-		mpt_prt(mpt, "failed to initialize IOC");
-		return (EIO);
+	/*
+	 * Enable the IOC
+	 */
+	if (mpt_enable_ioc(mpt, 0) != MPT_OK) {
+		mpt_prt(mpt, "unable to initialize IOC\n");
+		return (ENXIO);
 	}
 
+	/*
+	 * Read IOC configuration information.
+	 *
+	 * We need this to determine whether or not we have certain
+	 * settings for Integrated Mirroring (e.g.).
+	 */
+	mpt_read_config_info_ioc(mpt);
+
 	return (0);
 }
 
@@ -2588,7 +2590,7 @@
 	    (pptr + MPT_REPLY_SIZE) < (mpt->reply_phys + PAGE_SIZE);
 	     pptr += MPT_REPLY_SIZE) {
 		mpt_free_reply(mpt, pptr);
-		if (++val == mpt->mpt_global_credits - 1)
+		if (++val == mpt->ioc_facts.GlobalCredits - 1)
 			break;
 	}
 
@@ -2610,3 +2612,92 @@
 	}
 	return (MPT_OK);
 }
+
+/*
+ * Endian Conversion Functions- only used on Big Endian machines
+ */
+#if	_BYTE_ORDER == _BIG_ENDIAN
+void
+mpt2host_sge_simple_union(SGE_SIMPLE_UNION *sge)
+{
+	MPT_2_HOST32(sge, FlagsLength);
+	MPT_2_HOST64(sge, u.Address64);
+};
+
+void
+mpt2host_iocfacts_reply(MSG_IOC_FACTS_REPLY *rp)
+{
+	MPT_2_HOST16(rp, MsgVersion);
+	MPT_2_HOST16(rp, HeaderVersion);
+	MPT_2_HOST32(rp, MsgContext);
+	MPT_2_HOST16(rp, IOCExceptions);
+	MPT_2_HOST16(rp, IOCStatus);
+	MPT_2_HOST32(rp, IOCLogInfo);
+	MPT_2_HOST16(rp, ReplyQueueDepth);
+	MPT_2_HOST16(rp, RequestFrameSize);
+	MPT_2_HOST16(rp, Reserved_0101_FWVersion);
+	MPT_2_HOST16(rp, ProductID);
+	MPT_2_HOST32(rp, CurrentHostMfaHighAddr);
+	MPT_2_HOST16(rp, GlobalCredits);
+	MPT_2_HOST32(rp, CurrentSenseBufferHighAddr);
+	MPT_2_HOST16(rp, CurReplyFrameSize);
+	MPT_2_HOST32(rp, FWImageSize);
+	MPT_2_HOST32(rp, IOCCapabilities);
+	MPT_2_HOST32(rp, FWVersion.Word);
+	MPT_2_HOST16(rp, HighPriorityQueueDepth);
+	MPT_2_HOST16(rp, Reserved2);
+	mpt2host_sge_simple_union(&rp->HostPageBufferSGE);
+	MPT_2_HOST32(rp, ReplyFifoHostSignalingAddr);
+}
+
+void
+mpt2host_portfacts_reply(MSG_PORT_FACTS_REPLY *pfp)
+{
+	MPT_2_HOST16(pfp, Reserved);
+	MPT_2_HOST16(pfp, Reserved1);
+	MPT_2_HOST32(pfp, MsgContext);
+	MPT_2_HOST16(pfp, Reserved2);
+	MPT_2_HOST16(pfp, IOCStatus);
+	MPT_2_HOST32(pfp, IOCLogInfo);
+	MPT_2_HOST16(pfp, MaxDevices);
+	MPT_2_HOST16(pfp, PortSCSIID);
+	MPT_2_HOST16(pfp, ProtocolFlags);
+	MPT_2_HOST16(pfp, MaxPostedCmdBuffers);
+	MPT_2_HOST16(pfp, MaxPersistentIDs);
+	MPT_2_HOST16(pfp, MaxLanBuckets);
+	MPT_2_HOST16(pfp, Reserved4);
+	MPT_2_HOST32(pfp, Reserved5);
+}
+void
+mpt2host_config_page_ioc2(CONFIG_PAGE_IOC_2 *ioc2)
+{
+	int i;
+	ioc2->CapabilitiesFlags = htole32(ioc2->CapabilitiesFlags);
+	for (i = 0; i < MPI_IOC_PAGE_2_RAID_VOLUME_MAX; i++) {
+		MPT_2_HOST16(ioc2->RaidVolume[i].Reserved3);
+	}
+}
+
+void
+mpt2host_config_page_raid_vol_0(CONFIG_PAGE_RAID_VOL_0 *volp)
+{
+	int i;
+	MPT_2_HOST16(volp, VolumeStatus.Reserved);
+	MPT_2_HOST16(volp, VolumeSettings.Settings);
+	MPT_2_HOST32(volp, MaxLBA);
+	MPT_2_HOST32(volp, Reserved1);
+	MPT_2_HOST32(volp, StripeSize);
+	MPT_2_HOST32(volp, Reserved2);
+	MPT_2_HOST32(volp, Reserved3);
+	for (i = 0; i < MPI_RAID_VOL_PAGE_0_PHYSDISK_MAX; i++) {
+		MPT_2_HOST16(volpd, PhysDisk[i].Reserved);
+	}
+}
+
+void
+mpt2host_mpi_raid_vol_indicator(MPI_RAID_VOL_INDICATOR *vi)
+{
+	MPT_2_HOST16(vi, TotalBlocks);
+	MPT_2_HOST16(vi, BlocksRemaining);
+}
+#endif

==== //depot/projects/newisp/dev/mpt/mpt.h#8 (text+ko) ====

@@ -155,6 +155,9 @@
 /* XXX For mpt_debug.c */
 #include <dev/mpt/mpilib/mpi_init.h>
 
+#define	MPT_S64_2_SCALAR(y)	((((int64_t)y.High) << 32) | (y.Low))
+#define	MPT_U64_2_SCALAR(y)	((((uint64_t)y.High) << 32) | (y.Low))
+
 /****************************** Misc Definitions ******************************/
 #define MPT_OK (0)
 #define MPT_FAIL (0x10000)
@@ -272,15 +275,29 @@
 #endif
 
 /********************************** Endianess *********************************/
-static __inline uint64_t
-u64toh(U64 s)
-{
-	uint64_t result;
+#define	MPT_2_HOST64(ptr, tag)	ptr->tag = le64toh(ptr->tag)
+#define	MPT_2_HOST32(ptr, tag)	ptr->tag = le32toh(ptr->tag)
+#define	MPT_2_HOST16(ptr, tag)	ptr->tag = le16toh(ptr->tag)
+
+#define	HOST_2_MPT64(ptr, tag)	ptr->tag = htole64(ptr->tag)
+#define	HOST_2_MPT32(ptr, tag)	ptr->tag = htole32(ptr->tag)
+#define	HOST_2_MPT16(ptr, tag)	ptr->tag = htole16(ptr->tag)
 
-	result = le32toh(s.Low);
-	result |= ((uint64_t)le32toh(s.High)) << 32;
-	return (result);
-}
+#if	_BYTE_ORDER == _LITTLE_ENDIAN
+#define	mpt2host_sge_simple_union(x)		do { ; } while (0)
+#define	mpt2host_iocfacts_reply(x)		do { ; } while (0)
+#define	mpt2host_portfacts_reply(x)		do { ; } while (0)
+#define	mpt2host_config_page_ioc2(x)		do { ; } while (0)
+#define	mpt2host_config_page_raid_vol_0(x)	do { ; } while (0)
+#define	mpt2host_mpi_raid_vol_indicator(x)	do { ; } while (0)
+#else
+void mpt2host_sge_simple_union(SGE_SIMPLE_UNION *);
+void mpt2host_iocfacts_reply(MSG_IOC_FACTS_REPLY *);
+void mpt2host_portfacts_reply(MSG_PORT_FACTS_REPLY *);
+void mpt2host_config_page_ioc2(CONFIG_PAGE_IOC_2 *);
+void mpt2host_config_page_raid_vol_0(CONFIG_PAGE_RAID_VOL_0 *);
+void mpt2host_mpi_raid_vol_indicator(MPI_RAID_VOL_INDICATOR *);
+#endif
 
 /**************************** MPI Transaction State ***************************/
 typedef enum {
@@ -495,8 +512,10 @@
 #endif
 	uint32_t		mpt_pers_mask;
 	uint32_t
+				: 8,
 		unit		: 8,
-				: 2,
+				: 1,
+		fw_uploaded	: 1,
 		msi_enable	: 1,
 		twildcard	: 1,
 		tenabled	: 1,
@@ -520,20 +539,14 @@
 	/*
 	 * IOC Facts
 	 */
-	uint16_t	mpt_global_credits;
-	uint16_t	request_frame_size;
-	uint16_t	mpt_max_devices;
-	uint8_t		mpt_max_buses;
-	uint8_t		ioc_facts_flags;
+	MSG_IOC_FACTS_REPLY	ioc_facts;
 
 	/*
 	 * Port Facts
-	 * XXX - Add multi-port support!.
 	 */
-	uint16_t	mpt_ini_id;
-	uint16_t	mpt_port_type;
-	uint16_t	mpt_proto_flags;
-	uint16_t	mpt_max_tgtcmds;
+	MSG_PORT_FACTS_REPLY *	port_facts;
+#define	mpt_ini_id	port_facts[0].PortSCSIID
+#define	mpt_max_tgtcmds	port_facts[0].MaxPostedCmdBuffers
 
 	/*
 	 * Device Configuration Information
@@ -930,7 +943,7 @@
 
 /************************** Scatter Gather Managment **************************/
 /* MPT_RQSL- size of request frame, in bytes */
-#define	MPT_RQSL(mpt)		(mpt->request_frame_size << 2)
+#define	MPT_RQSL(mpt)		(mpt->ioc_facts.RequestFrameSize << 2)
 
 /* MPT_NSGL- how many SG entries can fit in a request frame size */
 #define	MPT_NSGL(mpt)		(MPT_RQSL(mpt) / sizeof (SGE_IO_UNION))

==== //depot/projects/newisp/dev/mpt/mpt_cam.c#19 (text+ko) ====

@@ -211,8 +211,8 @@
 	int		 error;
 
 	TAILQ_INIT(&mpt->request_timeout_list);
-	maxq = (mpt->mpt_global_credits < MPT_MAX_REQUESTS(mpt))?
-	    mpt->mpt_global_credits : MPT_MAX_REQUESTS(mpt);
+	maxq = (mpt->ioc_facts.GlobalCredits < MPT_MAX_REQUESTS(mpt))?
+	    mpt->ioc_facts.GlobalCredits : MPT_MAX_REQUESTS(mpt);
 
 	handler.reply_handler = mpt_scsi_reply_handler;
 	error = mpt_register_handler(mpt, MPT_HANDLER_REPLY, handler,
@@ -3136,7 +3136,7 @@
 		cpi->version_num = 1;
 		cpi->target_sprt = 0;
 		cpi->hba_eng_cnt = 0;
-		cpi->max_target = mpt->mpt_max_devices - 1;
+		cpi->max_target = mpt->port_facts[0].MaxDevices - 1;
 		/*
 		 * FC cards report MAX_DEVICES of 512, but
 		 * the MSG_SCSI_IO_REQUEST target id field

==== //depot/projects/newisp/dev/mpt/mpt_cam.h#2 (text+ko) ====


==== //depot/projects/newisp/dev/mpt/mpt_debug.c#2 (text+ko) ====

@@ -819,7 +819,7 @@
 mpt_dump_request(struct mpt_softc *mpt, request_t *req)
 {
         uint32_t *pReq = req->req_vbuf;
-	int offset;
+	int o;
 #if __FreeBSD_version >= 500000
 	mpt_prt(mpt, "Send Request %d (%jx):",
 	    req->index, (uintmax_t) req->req_pbuf);
@@ -827,12 +827,12 @@
 	mpt_prt(mpt, "Send Request %d (%llx):",
 	    req->index, (unsigned long long) req->req_pbuf);
 #endif
-	for (offset = 0; offset < mpt->request_frame_size; offset++) {
-		if ((offset & 0x7) == 0) {
+	for (o = 0; o < mpt->ioc_facts.RequestFrameSize; o++) {
+		if ((o & 0x7) == 0) {
 			mpt_prtc(mpt, "\n");
 			mpt_prt(mpt, " ");
 		}
-		mpt_prtc(mpt, " %08x", pReq[offset]);
+		mpt_prtc(mpt, " %08x", pReq[o]);
 	}
 	mpt_prtc(mpt, "\n");
 }

==== //depot/projects/newisp/dev/mpt/mpt_raid.c#6 (text+ko) ====

@@ -1229,7 +1229,7 @@
 
 static void
 mpt_refresh_raid_vol(struct mpt_softc *mpt, struct mpt_raid_volume *mpt_vol,
-		     CONFIG_PAGE_IOC_2_RAID_VOL *ioc_vol)
+    CONFIG_PAGE_IOC_2_RAID_VOL *ioc_vol)
 {
 	CONFIG_PAGE_RAID_VOL_0 *vol_pg;
 	struct mpt_raid_action_result *ar;
@@ -1239,31 +1239,31 @@
 
 	vol_pg = mpt_vol->config_page;
 	mpt_vol->flags &= ~MPT_RVF_UP2DATE;
-	rv = mpt_read_cfg_header(mpt, MPI_CONFIG_PAGETYPE_RAID_VOLUME,
-				 /*PageNumber*/0, ioc_vol->VolumePageNumber,
-				 &vol_pg->Header, /*sleep_ok*/TRUE,
-				 /*timeout_ms*/5000);
+
+	rv = mpt_read_cfg_header(mpt, MPI_CONFIG_PAGETYPE_RAID_VOLUME, 0,
+	    ioc_vol->VolumePageNumber, &vol_pg->Header, TRUE, 5000);
 	if (rv != 0) {
-		mpt_vol_prt(mpt, mpt_vol, "mpt_refresh_raid_vol: "
-			    "Failed to read RAID Vol Hdr(%d)\n",
-			    ioc_vol->VolumePageNumber);
+		mpt_vol_prt(mpt, mpt_vol,
+		    "mpt_refresh_raid_vol: Failed to read RAID Vol Hdr(%d)\n",
+		    ioc_vol->VolumePageNumber);
 		return;
 	}
+
 	rv = mpt_read_cur_cfg_page(mpt, ioc_vol->VolumePageNumber,
-				   &vol_pg->Header, mpt->raid_page0_len,
-				   /*sleep_ok*/TRUE, /*timeout_ms*/5000);
+	    &vol_pg->Header, mpt->raid_page0_len, TRUE, 5000);
 	if (rv != 0) {
-		mpt_vol_prt(mpt, mpt_vol, "mpt_refresh_raid_vol: "
-			    "Failed to read RAID Vol Page(%d)\n",
-			    ioc_vol->VolumePageNumber);
+		mpt_vol_prt(mpt, mpt_vol,
+		    "mpt_refresh_raid_vol: Failed to read RAID Vol Page(%d)\n",
+		    ioc_vol->VolumePageNumber);
 		return;
 	}
+	mpt2host_config_page_raid_vol_0(vol_pg);
+
 	mpt_vol->flags |= MPT_RVF_ACTIVE;
 
 	/* Update disk entry array data. */
 	for (i = 0; i < vol_pg->NumPhysDisks; i++) {
 		struct mpt_raid_disk *mpt_disk;
-
 		mpt_disk = mpt->raid_disks + vol_pg->PhysDisk[i].PhysDiskNum;
 		mpt_disk->volume = mpt_vol;
 		mpt_disk->member_number = vol_pg->PhysDisk[i].PhysDiskMap;
@@ -1276,19 +1276,18 @@
 	   & MPI_RAIDVOL0_STATUS_FLAG_RESYNC_IN_PROGRESS) == 0)
 		return;
 
-	req = mpt_get_request(mpt, /*sleep_ok*/TRUE);
+	req = mpt_get_request(mpt, TRUE);
 	if (req == NULL) {
 		mpt_vol_prt(mpt, mpt_vol,
-			    "mpt_refresh_raid_vol: Get request failed!\n");
+		    "mpt_refresh_raid_vol: Get request failed!\n");
 		return;
 	}
-	rv = mpt_issue_raid_req(mpt, mpt_vol, /*disk*/NULL, req,
-				MPI_RAID_ACTION_INDICATOR_STRUCT,
-				/*ActionWord*/0, /*addr*/0, /*len*/0,
-				/*write*/FALSE, /*wait*/TRUE);
+	rv = mpt_issue_raid_req(mpt, mpt_vol, NULL, req,
+	    MPI_RAID_ACTION_INDICATOR_STRUCT, 0, 0, 0, FALSE, TRUE);
 	if (rv == ETIMEDOUT) {
-		mpt_vol_prt(mpt, mpt_vol, "mpt_refresh_raid_vol: "
-			    "Progress indicator fetch timedout!\n");
+		mpt_vol_prt(mpt, mpt_vol,
+		    "mpt_refresh_raid_vol: Progress Indicator fetch timeout\n");
+		mpt_free_request(mpt, req);
 		return;
 	}
 
@@ -1299,9 +1298,10 @@
 		memcpy(&mpt_vol->sync_progress,
 		       &ar->action_data.indicator_struct,
 		       sizeof(mpt_vol->sync_progress));
+		mpt2host_mpi_raid_vol_indicator(&mpt_vol->sync_progress);
 	} else {
-		mpt_vol_prt(mpt, mpt_vol, "mpt_refresh_raid_vol: "
-			    "Progress indicator fetch failed!\n");
+		mpt_vol_prt(mpt, mpt_vol,
+		    "mpt_refresh_raid_vol: Progress indicator fetch failed!\n");
 	}
 	mpt_free_request(mpt, req);
 }
@@ -1414,8 +1414,9 @@
 
 		mpt_vol = &mpt->raid_volumes[i];
 
-		if ((mpt_vol->flags & MPT_RVF_ACTIVE) == 0)
+		if ((mpt_vol->flags & MPT_RVF_ACTIVE) == 0) {
 			continue;
+		}
 
 		vol_pg = mpt_vol->config_page;
 		if ((mpt_vol->flags & (MPT_RVF_REFERENCED|MPT_RVF_ANNOUNCED))
@@ -1426,7 +1427,6 @@
 		}
 
 		if ((mpt_vol->flags & MPT_RVF_ANNOUNCED) == 0) {
-
 			mpt_announce_vol(mpt, mpt_vol);
 			mpt_vol->flags |= MPT_RVF_ANNOUNCED;
 		}
@@ -1440,11 +1440,12 @@
 
 		mpt_vol->flags |= MPT_RVF_UP2DATE;
 		mpt_vol_prt(mpt, mpt_vol, "%s - %s\n",
-			    mpt_vol_type(mpt_vol), mpt_vol_state(mpt_vol));
+		    mpt_vol_type(mpt_vol), mpt_vol_state(mpt_vol));
 		mpt_verify_mwce(mpt, mpt_vol);
 
-		if (vol_pg->VolumeStatus.Flags == 0)
+		if (vol_pg->VolumeStatus.Flags == 0) {
 			continue;
+		}
 
 		mpt_vol_prt(mpt, mpt_vol, "Status (");
 		for (m = 1; m <= 0x80; m <<= 1) {
@@ -1473,8 +1474,8 @@
 
 		mpt_verify_resync_rate(mpt, mpt_vol);
 
-		left = u64toh(mpt_vol->sync_progress.BlocksRemaining);
-		total = u64toh(mpt_vol->sync_progress.TotalBlocks);
+		left = MPT_U64_2_SCALAR(mpt_vol->sync_progress.BlocksRemaining);
+		total = MPT_U64_2_SCALAR(mpt_vol->sync_progress.TotalBlocks);
 		if (vol_pg->ResyncRate != 0) {
 
 			prio = ((u_int)vol_pg->ResyncRate * 100000) / 0xFF;



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