2 * linux/drivers/message/fusion/mptsas.c
3 * For use with LSI Logic PCI chip/adapter(s)
4 * running LSI Logic Fusion MPT (Message Passing Technology) firmware.
6 * Copyright (c) 1999-2007 LSI Logic Corporation
7 * (mailto:DL-MPTFusionLinux@lsi.com)
8 * Copyright (c) 2005-2007 Dell
10 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
12 This program is free software; you can redistribute it and/or modify
13 it under the terms of the GNU General Public License as published by
14 the Free Software Foundation; version 2 of the License.
16 This program is distributed in the hope that it will be useful,
17 but WITHOUT ANY WARRANTY; without even the implied warranty of
18 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 GNU General Public License for more details.
22 THE PROGRAM IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OR
23 CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED INCLUDING, WITHOUT
24 LIMITATION, ANY WARRANTIES OR CONDITIONS OF TITLE, NON-INFRINGEMENT,
25 MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. Each Recipient is
26 solely responsible for determining the appropriateness of using and
27 distributing the Program and assumes all risks associated with its
28 exercise of rights under this Agreement, including but not limited to
29 the risks and costs of program errors, damage to or loss of data,
30 programs or equipment, and unavailability or interruption of operations.
32 DISCLAIMER OF LIABILITY
33 NEITHER RECIPIENT NOR ANY CONTRIBUTORS SHALL HAVE ANY LIABILITY FOR ANY
34 DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
35 DAMAGES (INCLUDING WITHOUT LIMITATION LOST PROFITS), HOWEVER CAUSED AND
36 ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
37 TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
38 USE OR DISTRIBUTION OF THE PROGRAM OR THE EXERCISE OF ANY RIGHTS GRANTED
39 HEREUNDER, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGES
41 You should have received a copy of the GNU General Public License
42 along with this program; if not, write to the Free Software
43 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
45 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
47 #include <linux/module.h>
48 #include <linux/kernel.h>
49 #include <linux/init.h>
50 #include <linux/errno.h>
51 #include <linux/jiffies.h>
52 #include <linux/workqueue.h>
53 #include <linux/delay.h> /* for mdelay */
55 #include <scsi/scsi.h>
56 #include <scsi/scsi_cmnd.h>
57 #include <scsi/scsi_device.h>
58 #include <scsi/scsi_host.h>
59 #include <scsi/scsi_transport_sas.h>
60 #include <scsi/scsi_dbg.h>
66 #define my_NAME "Fusion MPT SAS Host driver"
67 #define my_VERSION MPT_LINUX_VERSION_COMMON
68 #define MYNAM "mptsas"
71 * Reserved channel for integrated raid
73 #define MPTSAS_RAID_CHANNEL 1
75 MODULE_AUTHOR(MODULEAUTHOR);
76 MODULE_DESCRIPTION(my_NAME);
77 MODULE_LICENSE("GPL");
78 MODULE_VERSION(my_VERSION);
80 static int mpt_pt_clear;
81 module_param(mpt_pt_clear, int, 0);
82 MODULE_PARM_DESC(mpt_pt_clear,
83 " Clear persistency table: enable=1 "
84 "(default=MPTSCSIH_PT_CLEAR=0)");
86 /* scsi-mid layer global parmeter is max_report_luns, which is 511 */
87 #define MPTSAS_MAX_LUN (16895)
88 static int max_lun = MPTSAS_MAX_LUN;
89 module_param(max_lun, int, 0);
90 MODULE_PARM_DESC(max_lun, " max lun, default=16895 ");
92 static int mptsasDoneCtx = -1;
93 static int mptsasTaskCtx = -1;
94 static int mptsasInternalCtx = -1; /* Used only for internal commands */
95 static int mptsasMgmtCtx = -1;
97 static void mptsas_hotplug_work(struct work_struct *work);
99 struct mptsas_target_reset_event {
100 struct list_head list;
101 EVENT_DATA_SAS_DEVICE_STATUS_CHANGE sas_event_data;
102 u8 target_reset_issued;
105 enum mptsas_hotplug_action {
110 MPTSAS_ADD_INACTIVE_VOLUME,
114 struct mptsas_hotplug_event {
115 struct work_struct work;
117 enum mptsas_hotplug_action event_type;
125 u8 phys_disk_num_valid; /* hrc (hidden raid component) */
126 u8 phys_disk_num; /* hrc - unique index*/
127 u8 hidden_raid_component; /* hrc - don't expose*/
130 struct mptsas_discovery_event {
131 struct work_struct work;
136 * SAS topology structures
138 * The MPT Fusion firmware interface spreads information about the
139 * SAS topology over many manufacture pages, thus we need some data
140 * structure to collect it and process it for the SAS transport class.
143 struct mptsas_devinfo {
144 u16 handle; /* unique id to address this device */
145 u16 handle_parent; /* unique id to address parent device */
146 u16 handle_enclosure; /* enclosure identifier of the enclosure */
147 u16 slot; /* physical slot in enclosure */
148 u8 phy_id; /* phy number of parent device */
149 u8 port_id; /* sas physical port this device
151 u8 id; /* logical target id of this device */
152 u32 phys_disk_num; /* phys disk id, for csmi-ioctls */
153 u8 channel; /* logical bus number of this device */
154 u64 sas_address; /* WWN of this device,
155 SATA is assigned by HBA,expander */
156 u32 device_info; /* bitfield detailed info about this device */
160 * Specific details on ports, wide/narrow
162 struct mptsas_portinfo_details{
163 u16 num_phys; /* number of phys belong to this port */
164 u64 phy_bitmask; /* TODO, extend support for 255 phys */
165 struct sas_rphy *rphy; /* transport layer rphy object */
166 struct sas_port *port; /* transport layer port object */
167 struct scsi_target *starget;
168 struct mptsas_portinfo *port_info;
171 struct mptsas_phyinfo {
172 u16 handle; /* unique id to address this */
173 u8 phy_id; /* phy index */
174 u8 port_id; /* firmware port identifier */
175 u8 negotiated_link_rate; /* nego'd link rate for this phy */
176 u8 hw_link_rate; /* hardware max/min phys link rate */
177 u8 programmed_link_rate; /* programmed max/min phy link rate */
178 u8 sas_port_add_phy; /* flag to request sas_port_add_phy*/
179 struct mptsas_devinfo identify; /* point to phy device info */
180 struct mptsas_devinfo attached; /* point to attached device info */
181 struct sas_phy *phy; /* transport layer phy object */
182 struct mptsas_portinfo *portinfo;
183 struct mptsas_portinfo_details * port_details;
186 struct mptsas_portinfo {
187 struct list_head list;
188 u16 num_phys; /* number of phys */
189 struct mptsas_phyinfo *phy_info;
192 struct mptsas_enclosure {
193 u64 enclosure_logical_id; /* The WWN for the enclosure */
194 u16 enclosure_handle; /* unique id to address this */
195 u16 flags; /* details enclosure management */
196 u16 num_slot; /* num slots */
197 u16 start_slot; /* first slot */
198 u8 start_id; /* starting logical target id */
199 u8 start_channel; /* starting logical channel id */
200 u8 sep_id; /* SEP device logical target id */
201 u8 sep_channel; /* SEP channel logical channel id */
205 static void mptsas_print_phy_data(MPI_SAS_IO_UNIT0_PHY_DATA *phy_data)
207 printk("---- IO UNIT PAGE 0 ------------\n");
208 printk("Handle=0x%X\n",
209 le16_to_cpu(phy_data->AttachedDeviceHandle));
210 printk("Controller Handle=0x%X\n",
211 le16_to_cpu(phy_data->ControllerDevHandle));
212 printk("Port=0x%X\n", phy_data->Port);
213 printk("Port Flags=0x%X\n", phy_data->PortFlags);
214 printk("PHY Flags=0x%X\n", phy_data->PhyFlags);
215 printk("Negotiated Link Rate=0x%X\n", phy_data->NegotiatedLinkRate);
216 printk("Controller PHY Device Info=0x%X\n",
217 le32_to_cpu(phy_data->ControllerPhyDeviceInfo));
218 printk("DiscoveryStatus=0x%X\n",
219 le32_to_cpu(phy_data->DiscoveryStatus));
223 static void mptsas_print_phy_pg0(SasPhyPage0_t *pg0)
227 memcpy(&sas_address, &pg0->SASAddress, sizeof(__le64));
229 printk("---- SAS PHY PAGE 0 ------------\n");
230 printk("Attached Device Handle=0x%X\n",
231 le16_to_cpu(pg0->AttachedDevHandle));
232 printk("SAS Address=0x%llX\n",
233 (unsigned long long)le64_to_cpu(sas_address));
234 printk("Attached PHY Identifier=0x%X\n", pg0->AttachedPhyIdentifier);
235 printk("Attached Device Info=0x%X\n",
236 le32_to_cpu(pg0->AttachedDeviceInfo));
237 printk("Programmed Link Rate=0x%X\n", pg0->ProgrammedLinkRate);
238 printk("Change Count=0x%X\n", pg0->ChangeCount);
239 printk("PHY Info=0x%X\n", le32_to_cpu(pg0->PhyInfo));
243 static void mptsas_print_phy_pg1(SasPhyPage1_t *pg1)
245 printk("---- SAS PHY PAGE 1 ------------\n");
246 printk("Invalid Dword Count=0x%x\n", pg1->InvalidDwordCount);
247 printk("Running Disparity Error Count=0x%x\n",
248 pg1->RunningDisparityErrorCount);
249 printk("Loss Dword Synch Count=0x%x\n", pg1->LossDwordSynchCount);
250 printk("PHY Reset Problem Count=0x%x\n", pg1->PhyResetProblemCount);
254 static void mptsas_print_device_pg0(SasDevicePage0_t *pg0)
258 memcpy(&sas_address, &pg0->SASAddress, sizeof(__le64));
260 printk("---- SAS DEVICE PAGE 0 ---------\n");
261 printk("Handle=0x%X\n" ,le16_to_cpu(pg0->DevHandle));
262 printk("Parent Handle=0x%X\n" ,le16_to_cpu(pg0->ParentDevHandle));
263 printk("Enclosure Handle=0x%X\n", le16_to_cpu(pg0->EnclosureHandle));
264 printk("Slot=0x%X\n", le16_to_cpu(pg0->Slot));
265 printk("SAS Address=0x%llX\n", (unsigned long long)
266 le64_to_cpu(sas_address));
267 printk("Target ID=0x%X\n", pg0->TargetID);
268 printk("Bus=0x%X\n", pg0->Bus);
269 /* The PhyNum field specifies the PHY number of the parent
270 * device this device is linked to
272 printk("Parent Phy Num=0x%X\n", pg0->PhyNum);
273 printk("Access Status=0x%X\n", le16_to_cpu(pg0->AccessStatus));
274 printk("Device Info=0x%X\n", le32_to_cpu(pg0->DeviceInfo));
275 printk("Flags=0x%X\n", le16_to_cpu(pg0->Flags));
276 printk("Physical Port=0x%X\n", pg0->PhysicalPort);
280 static void mptsas_print_expander_pg1(SasExpanderPage1_t *pg1)
282 printk("---- SAS EXPANDER PAGE 1 ------------\n");
284 printk("Physical Port=0x%X\n", pg1->PhysicalPort);
285 printk("PHY Identifier=0x%X\n", pg1->PhyIdentifier);
286 printk("Negotiated Link Rate=0x%X\n", pg1->NegotiatedLinkRate);
287 printk("Programmed Link Rate=0x%X\n", pg1->ProgrammedLinkRate);
288 printk("Hardware Link Rate=0x%X\n", pg1->HwLinkRate);
289 printk("Owner Device Handle=0x%X\n",
290 le16_to_cpu(pg1->OwnerDevHandle));
291 printk("Attached Device Handle=0x%X\n",
292 le16_to_cpu(pg1->AttachedDevHandle));
295 #define mptsas_print_phy_data(phy_data) do { } while (0)
296 #define mptsas_print_phy_pg0(pg0) do { } while (0)
297 #define mptsas_print_phy_pg1(pg1) do { } while (0)
298 #define mptsas_print_device_pg0(pg0) do { } while (0)
299 #define mptsas_print_expander_pg1(pg1) do { } while (0)
302 static inline MPT_ADAPTER *phy_to_ioc(struct sas_phy *phy)
304 struct Scsi_Host *shost = dev_to_shost(phy->dev.parent);
305 return ((MPT_SCSI_HOST *)shost->hostdata)->ioc;
308 static inline MPT_ADAPTER *rphy_to_ioc(struct sas_rphy *rphy)
310 struct Scsi_Host *shost = dev_to_shost(rphy->dev.parent->parent);
311 return ((MPT_SCSI_HOST *)shost->hostdata)->ioc;
315 * mptsas_find_portinfo_by_handle
317 * This function should be called with the sas_topology_mutex already held
319 static struct mptsas_portinfo *
320 mptsas_find_portinfo_by_handle(MPT_ADAPTER *ioc, u16 handle)
322 struct mptsas_portinfo *port_info, *rc=NULL;
325 list_for_each_entry(port_info, &ioc->sas_topology, list)
326 for (i = 0; i < port_info->num_phys; i++)
327 if (port_info->phy_info[i].identify.handle == handle) {
336 * Returns true if there is a scsi end device
339 mptsas_is_end_device(struct mptsas_devinfo * attached)
341 if ((attached->sas_address) &&
342 (attached->device_info &
343 MPI_SAS_DEVICE_INFO_END_DEVICE) &&
344 ((attached->device_info &
345 MPI_SAS_DEVICE_INFO_SSP_TARGET) |
346 (attached->device_info &
347 MPI_SAS_DEVICE_INFO_STP_TARGET) |
348 (attached->device_info &
349 MPI_SAS_DEVICE_INFO_SATA_DEVICE)))
357 mptsas_port_delete(struct mptsas_portinfo_details * port_details)
359 struct mptsas_portinfo *port_info;
360 struct mptsas_phyinfo *phy_info;
366 port_info = port_details->port_info;
367 phy_info = port_info->phy_info;
369 dsaswideprintk((KERN_DEBUG "%s: [%p]: num_phys=%02d "
370 "bitmask=0x%016llX\n", __FUNCTION__, port_details,
371 port_details->num_phys, (unsigned long long)
372 port_details->phy_bitmask));
374 for (i = 0; i < port_info->num_phys; i++, phy_info++) {
375 if(phy_info->port_details != port_details)
377 memset(&phy_info->attached, 0, sizeof(struct mptsas_devinfo));
378 phy_info->port_details = NULL;
383 static inline struct sas_rphy *
384 mptsas_get_rphy(struct mptsas_phyinfo *phy_info)
386 if (phy_info->port_details)
387 return phy_info->port_details->rphy;
393 mptsas_set_rphy(struct mptsas_phyinfo *phy_info, struct sas_rphy *rphy)
395 if (phy_info->port_details) {
396 phy_info->port_details->rphy = rphy;
397 dsaswideprintk((KERN_DEBUG "sas_rphy_add: rphy=%p\n", rphy));
400 #ifdef MPT_DEBUG_SAS_WIDE
402 dev_printk(KERN_DEBUG, &rphy->dev, "add:");
403 printk("rphy=%p release=%p\n",
404 rphy, rphy->dev.release);
409 static inline struct sas_port *
410 mptsas_get_port(struct mptsas_phyinfo *phy_info)
412 if (phy_info->port_details)
413 return phy_info->port_details->port;
419 mptsas_set_port(struct mptsas_phyinfo *phy_info, struct sas_port *port)
421 if (phy_info->port_details)
422 phy_info->port_details->port = port;
424 #ifdef MPT_DEBUG_SAS_WIDE
426 dev_printk(KERN_DEBUG, &port->dev, "add: ");
427 printk("port=%p release=%p\n",
428 port, port->dev.release);
433 static inline struct scsi_target *
434 mptsas_get_starget(struct mptsas_phyinfo *phy_info)
436 if (phy_info->port_details)
437 return phy_info->port_details->starget;
443 mptsas_set_starget(struct mptsas_phyinfo *phy_info, struct scsi_target *
446 if (phy_info->port_details)
447 phy_info->port_details->starget = starget;
452 * mptsas_setup_wide_ports
454 * Updates for new and existing narrow/wide port configuration
455 * in the sas_topology
458 mptsas_setup_wide_ports(MPT_ADAPTER *ioc, struct mptsas_portinfo *port_info)
460 struct mptsas_portinfo_details * port_details;
461 struct mptsas_phyinfo *phy_info, *phy_info_cmp;
465 mutex_lock(&ioc->sas_topology_mutex);
467 phy_info = port_info->phy_info;
468 for (i = 0 ; i < port_info->num_phys ; i++, phy_info++) {
469 if (phy_info->attached.handle)
471 port_details = phy_info->port_details;
474 if (port_details->num_phys < 2)
477 * Removing a phy from a port, letting the last
478 * phy be removed by firmware events.
480 dsaswideprintk((KERN_DEBUG
481 "%s: [%p]: deleting phy = %d\n",
482 __FUNCTION__, port_details, i));
483 port_details->num_phys--;
484 port_details->phy_bitmask &= ~ (1 << phy_info->phy_id);
485 memset(&phy_info->attached, 0, sizeof(struct mptsas_devinfo));
486 sas_port_delete_phy(port_details->port, phy_info->phy);
487 phy_info->port_details = NULL;
491 * Populate and refresh the tree
493 phy_info = port_info->phy_info;
494 for (i = 0 ; i < port_info->num_phys ; i++, phy_info++) {
495 sas_address = phy_info->attached.sas_address;
496 dsaswideprintk((KERN_DEBUG "phy_id=%d sas_address=0x%018llX\n",
497 i, (unsigned long long)sas_address));
500 port_details = phy_info->port_details;
505 port_details = kzalloc(sizeof(*port_details),
509 port_details->num_phys = 1;
510 port_details->port_info = port_info;
511 if (phy_info->phy_id < 64 )
512 port_details->phy_bitmask |=
513 (1 << phy_info->phy_id);
514 phy_info->sas_port_add_phy=1;
515 dsaswideprintk((KERN_DEBUG "\t\tForming port\n\t\t"
516 "phy_id=%d sas_address=0x%018llX\n",
517 i, (unsigned long long)sas_address));
518 phy_info->port_details = port_details;
521 if (i == port_info->num_phys - 1)
523 phy_info_cmp = &port_info->phy_info[i + 1];
524 for (j = i + 1 ; j < port_info->num_phys ; j++,
526 if (!phy_info_cmp->attached.sas_address)
528 if (sas_address != phy_info_cmp->attached.sas_address)
530 if (phy_info_cmp->port_details == port_details )
532 dsaswideprintk((KERN_DEBUG
533 "\t\tphy_id=%d sas_address=0x%018llX\n",
534 j, (unsigned long long)
535 phy_info_cmp->attached.sas_address));
536 if (phy_info_cmp->port_details) {
538 mptsas_get_rphy(phy_info_cmp);
540 mptsas_get_port(phy_info_cmp);
541 port_details->starget =
542 mptsas_get_starget(phy_info_cmp);
543 port_details->num_phys =
544 phy_info_cmp->port_details->num_phys;
545 if (!phy_info_cmp->port_details->num_phys)
546 kfree(phy_info_cmp->port_details);
548 phy_info_cmp->sas_port_add_phy=1;
550 * Adding a phy to a port
552 phy_info_cmp->port_details = port_details;
553 if (phy_info_cmp->phy_id < 64 )
554 port_details->phy_bitmask |=
555 (1 << phy_info_cmp->phy_id);
556 port_details->num_phys++;
562 #ifdef MPT_DEBUG_SAS_WIDE
563 for (i = 0; i < port_info->num_phys; i++) {
564 port_details = port_info->phy_info[i].port_details;
567 dsaswideprintk((KERN_DEBUG
568 "%s: [%p]: phy_id=%02d num_phys=%02d "
569 "bitmask=0x%016llX\n", __FUNCTION__,
570 port_details, i, port_details->num_phys,
571 (unsigned long long)port_details->phy_bitmask));
572 dsaswideprintk((KERN_DEBUG"\t\tport = %p rphy=%p\n",
573 port_details->port, port_details->rphy));
575 dsaswideprintk((KERN_DEBUG"\n"));
577 mutex_unlock(&ioc->sas_topology_mutex);
581 * csmisas_find_vtarget
589 mptsas_find_vtarget(MPT_ADAPTER *ioc, u8 channel, u8 id)
591 struct scsi_device *sdev;
593 VirtTarget *vtarget = NULL;
595 shost_for_each_device(sdev, ioc->sh) {
596 if ((vdev = sdev->hostdata) == NULL)
598 if (vdev->vtarget->id == id &&
599 vdev->vtarget->channel == channel)
600 vtarget = vdev->vtarget;
606 * mptsas_target_reset
608 * Issues TARGET_RESET to end device using handshaking method
614 * Returns (1) success
619 mptsas_target_reset(MPT_ADAPTER *ioc, u8 channel, u8 id)
622 SCSITaskMgmt_t *pScsiTm;
624 if ((mf = mpt_get_msg_frame(ioc->TaskCtx, ioc)) == NULL) {
625 dfailprintk((MYIOC_s_WARN_FMT "%s, no msg frames @%d!!\n",
626 ioc->name,__FUNCTION__, __LINE__));
630 /* Format the Request
632 pScsiTm = (SCSITaskMgmt_t *) mf;
633 memset (pScsiTm, 0, sizeof(SCSITaskMgmt_t));
634 pScsiTm->TargetID = id;
635 pScsiTm->Bus = channel;
636 pScsiTm->Function = MPI_FUNCTION_SCSI_TASK_MGMT;
637 pScsiTm->TaskType = MPI_SCSITASKMGMT_TASKTYPE_TARGET_RESET;
638 pScsiTm->MsgFlags = MPI_SCSITASKMGMT_MSGFLAGS_LIPRESET_RESET_OPTION;
640 DBG_DUMP_TM_REQUEST_FRAME(mf);
642 if (mpt_send_handshake_request(ioc->TaskCtx, ioc,
643 sizeof(SCSITaskMgmt_t), (u32 *)mf, NO_SLEEP)) {
644 mpt_free_msg_frame(ioc, mf);
645 dfailprintk((MYIOC_s_WARN_FMT "%s, tm handshake failed @%d!!\n",
646 ioc->name,__FUNCTION__, __LINE__));
654 * mptsas_target_reset_queue
656 * Receive request for TARGET_RESET after recieving an firmware
657 * event NOT_RESPONDING_EVENT, then put command in link list
658 * and queue if task_queue already in use.
665 mptsas_target_reset_queue(MPT_ADAPTER *ioc,
666 EVENT_DATA_SAS_DEVICE_STATUS_CHANGE *sas_event_data)
668 MPT_SCSI_HOST *hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
669 VirtTarget *vtarget = NULL;
670 struct mptsas_target_reset_event *target_reset_list;
673 id = sas_event_data->TargetID;
674 channel = sas_event_data->Bus;
676 if (!(vtarget = mptsas_find_vtarget(ioc, channel, id)))
679 vtarget->deleted = 1; /* block IO */
681 target_reset_list = kzalloc(sizeof(*target_reset_list),
683 if (!target_reset_list) {
684 dfailprintk((MYIOC_s_WARN_FMT "%s, failed to allocate mem @%d..!!\n",
685 ioc->name,__FUNCTION__, __LINE__));
689 memcpy(&target_reset_list->sas_event_data, sas_event_data,
690 sizeof(*sas_event_data));
691 list_add_tail(&target_reset_list->list, &hd->target_reset_list);
693 if (hd->resetPending)
696 if (mptsas_target_reset(ioc, channel, id)) {
697 target_reset_list->target_reset_issued = 1;
698 hd->resetPending = 1;
703 * mptsas_dev_reset_complete
705 * Completion for TARGET_RESET after NOT_RESPONDING_EVENT,
706 * enable work queue to finish off removing device from upper layers.
707 * then send next TARGET_RESET in the queue.
713 mptsas_dev_reset_complete(MPT_ADAPTER *ioc)
715 MPT_SCSI_HOST *hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
716 struct list_head *head = &hd->target_reset_list;
717 struct mptsas_target_reset_event *target_reset_list;
718 struct mptsas_hotplug_event *ev;
719 EVENT_DATA_SAS_DEVICE_STATUS_CHANGE *sas_event_data;
723 if (list_empty(head))
726 target_reset_list = list_entry(head->next, struct mptsas_target_reset_event, list);
728 sas_event_data = &target_reset_list->sas_event_data;
729 id = sas_event_data->TargetID;
730 channel = sas_event_data->Bus;
731 hd->resetPending = 0;
736 if (!target_reset_list->target_reset_issued) {
737 if (mptsas_target_reset(ioc, channel, id)) {
738 target_reset_list->target_reset_issued = 1;
739 hd->resetPending = 1;
745 * enable work queue to remove device from upper layers
747 list_del(&target_reset_list->list);
749 ev = kzalloc(sizeof(*ev), GFP_ATOMIC);
751 dfailprintk((MYIOC_s_WARN_FMT "%s, failed to allocate mem @%d..!!\n",
752 ioc->name,__FUNCTION__, __LINE__));
756 INIT_WORK(&ev->work, mptsas_hotplug_work);
758 ev->handle = le16_to_cpu(sas_event_data->DevHandle);
760 le16_to_cpu(sas_event_data->ParentDevHandle);
761 ev->channel = channel;
763 ev->phy_id = sas_event_data->PhyNum;
764 memcpy(&sas_address, &sas_event_data->SASAddress,
766 ev->sas_address = le64_to_cpu(sas_address);
767 ev->device_info = le32_to_cpu(sas_event_data->DeviceInfo);
768 ev->event_type = MPTSAS_DEL_DEVICE;
769 schedule_work(&ev->work);
770 kfree(target_reset_list);
773 * issue target reset to next device in the queue
776 head = &hd->target_reset_list;
777 if (list_empty(head))
780 target_reset_list = list_entry(head->next, struct mptsas_target_reset_event,
783 sas_event_data = &target_reset_list->sas_event_data;
784 id = sas_event_data->TargetID;
785 channel = sas_event_data->Bus;
787 if (mptsas_target_reset(ioc, channel, id)) {
788 target_reset_list->target_reset_issued = 1;
789 hd->resetPending = 1;
794 * mptsas_taskmgmt_complete
802 mptsas_taskmgmt_complete(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf, MPT_FRAME_HDR *mr)
804 mptsas_dev_reset_complete(ioc);
805 return mptscsih_taskmgmt_complete(ioc, mf, mr);
816 mptsas_ioc_reset(MPT_ADAPTER *ioc, int reset_phase)
819 struct mptsas_target_reset_event *target_reset_list, *n;
822 rc = mptscsih_ioc_reset(ioc, reset_phase);
824 if (ioc->bus_type != SAS)
827 if (reset_phase != MPT_IOC_POST_RESET)
830 if (!ioc->sh || !ioc->sh->hostdata)
832 hd = (MPT_SCSI_HOST *)ioc->sh->hostdata;
836 if (list_empty(&hd->target_reset_list))
839 /* flush the target_reset_list */
840 list_for_each_entry_safe(target_reset_list, n,
841 &hd->target_reset_list, list) {
842 list_del(&target_reset_list->list);
843 kfree(target_reset_list);
851 mptsas_sas_enclosure_pg0(MPT_ADAPTER *ioc, struct mptsas_enclosure *enclosure,
852 u32 form, u32 form_specific)
854 ConfigExtendedPageHeader_t hdr;
856 SasEnclosurePage0_t *buffer;
857 dma_addr_t dma_handle;
859 __le64 le_identifier;
861 memset(&hdr, 0, sizeof(hdr));
862 hdr.PageVersion = MPI_SASENCLOSURE0_PAGEVERSION;
864 hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
865 hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_ENCLOSURE;
867 cfg.cfghdr.ehdr = &hdr;
869 cfg.pageAddr = form + form_specific;
870 cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
871 cfg.dir = 0; /* read */
874 error = mpt_config(ioc, &cfg);
877 if (!hdr.ExtPageLength) {
882 buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
889 cfg.physAddr = dma_handle;
890 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
892 error = mpt_config(ioc, &cfg);
894 goto out_free_consistent;
896 /* save config data */
897 memcpy(&le_identifier, &buffer->EnclosureLogicalID, sizeof(__le64));
898 enclosure->enclosure_logical_id = le64_to_cpu(le_identifier);
899 enclosure->enclosure_handle = le16_to_cpu(buffer->EnclosureHandle);
900 enclosure->flags = le16_to_cpu(buffer->Flags);
901 enclosure->num_slot = le16_to_cpu(buffer->NumSlots);
902 enclosure->start_slot = le16_to_cpu(buffer->StartSlot);
903 enclosure->start_id = buffer->StartTargetID;
904 enclosure->start_channel = buffer->StartBus;
905 enclosure->sep_id = buffer->SEPTargetID;
906 enclosure->sep_channel = buffer->SEPBus;
909 pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
916 mptsas_slave_configure(struct scsi_device *sdev)
919 if (sdev->channel == MPTSAS_RAID_CHANNEL)
922 sas_read_port_mode_page(sdev);
925 return mptscsih_slave_configure(sdev);
929 mptsas_target_alloc(struct scsi_target *starget)
931 struct Scsi_Host *host = dev_to_shost(&starget->dev);
932 MPT_SCSI_HOST *hd = (MPT_SCSI_HOST *)host->hostdata;
935 struct sas_rphy *rphy;
936 struct mptsas_portinfo *p;
939 vtarget = kzalloc(sizeof(VirtTarget), GFP_KERNEL);
943 vtarget->starget = starget;
944 vtarget->ioc_id = hd->ioc->id;
945 vtarget->tflags = MPT_TARGET_FLAGS_Q_YES;
950 * RAID volumes placed beyond the last expected port.
952 if (starget->channel == MPTSAS_RAID_CHANNEL) {
953 for (i=0; i < hd->ioc->raid_data.pIocPg2->NumActiveVolumes; i++)
954 if (id == hd->ioc->raid_data.pIocPg2->RaidVolume[i].VolumeID)
955 channel = hd->ioc->raid_data.pIocPg2->RaidVolume[i].VolumeBus;
959 rphy = dev_to_rphy(starget->dev.parent);
960 mutex_lock(&hd->ioc->sas_topology_mutex);
961 list_for_each_entry(p, &hd->ioc->sas_topology, list) {
962 for (i = 0; i < p->num_phys; i++) {
963 if (p->phy_info[i].attached.sas_address !=
964 rphy->identify.sas_address)
966 id = p->phy_info[i].attached.id;
967 channel = p->phy_info[i].attached.channel;
968 mptsas_set_starget(&p->phy_info[i], starget);
971 * Exposing hidden raid components
973 if (mptscsih_is_phys_disk(hd->ioc, channel, id)) {
974 id = mptscsih_raid_id_to_num(hd->ioc,
977 MPT_TARGET_FLAGS_RAID_COMPONENT;
978 p->phy_info[i].attached.phys_disk_num = id;
980 mutex_unlock(&hd->ioc->sas_topology_mutex);
984 mutex_unlock(&hd->ioc->sas_topology_mutex);
991 vtarget->channel = channel;
992 starget->hostdata = vtarget;
997 mptsas_target_destroy(struct scsi_target *starget)
999 struct Scsi_Host *host = dev_to_shost(&starget->dev);
1000 MPT_SCSI_HOST *hd = (MPT_SCSI_HOST *)host->hostdata;
1001 struct sas_rphy *rphy;
1002 struct mptsas_portinfo *p;
1005 if (!starget->hostdata)
1008 if (starget->channel == MPTSAS_RAID_CHANNEL)
1011 rphy = dev_to_rphy(starget->dev.parent);
1012 list_for_each_entry(p, &hd->ioc->sas_topology, list) {
1013 for (i = 0; i < p->num_phys; i++) {
1014 if (p->phy_info[i].attached.sas_address !=
1015 rphy->identify.sas_address)
1017 mptsas_set_starget(&p->phy_info[i], NULL);
1023 kfree(starget->hostdata);
1024 starget->hostdata = NULL;
1029 mptsas_slave_alloc(struct scsi_device *sdev)
1031 struct Scsi_Host *host = sdev->host;
1032 MPT_SCSI_HOST *hd = (MPT_SCSI_HOST *)host->hostdata;
1033 struct sas_rphy *rphy;
1034 struct mptsas_portinfo *p;
1036 struct scsi_target *starget;
1039 vdev = kzalloc(sizeof(VirtDevice), GFP_KERNEL);
1041 printk(MYIOC_s_ERR_FMT "slave_alloc kzalloc(%zd) FAILED!\n",
1042 hd->ioc->name, sizeof(VirtDevice));
1045 starget = scsi_target(sdev);
1046 vdev->vtarget = starget->hostdata;
1048 if (sdev->channel == MPTSAS_RAID_CHANNEL)
1051 rphy = dev_to_rphy(sdev->sdev_target->dev.parent);
1052 mutex_lock(&hd->ioc->sas_topology_mutex);
1053 list_for_each_entry(p, &hd->ioc->sas_topology, list) {
1054 for (i = 0; i < p->num_phys; i++) {
1055 if (p->phy_info[i].attached.sas_address !=
1056 rphy->identify.sas_address)
1058 vdev->lun = sdev->lun;
1060 * Exposing hidden raid components
1062 if (mptscsih_is_phys_disk(hd->ioc,
1063 p->phy_info[i].attached.channel,
1064 p->phy_info[i].attached.id))
1065 sdev->no_uld_attach = 1;
1066 mutex_unlock(&hd->ioc->sas_topology_mutex);
1070 mutex_unlock(&hd->ioc->sas_topology_mutex);
1076 vdev->vtarget->num_luns++;
1077 sdev->hostdata = vdev;
1082 mptsas_qcmd(struct scsi_cmnd *SCpnt, void (*done)(struct scsi_cmnd *))
1084 VirtDevice *vdev = SCpnt->device->hostdata;
1086 if (!vdev || !vdev->vtarget || vdev->vtarget->deleted) {
1087 SCpnt->result = DID_NO_CONNECT << 16;
1092 // scsi_print_command(SCpnt);
1094 return mptscsih_qcmd(SCpnt,done);
1098 static struct scsi_host_template mptsas_driver_template = {
1099 .module = THIS_MODULE,
1100 .proc_name = "mptsas",
1101 .proc_info = mptscsih_proc_info,
1102 .name = "MPT SPI Host",
1103 .info = mptscsih_info,
1104 .queuecommand = mptsas_qcmd,
1105 .target_alloc = mptsas_target_alloc,
1106 .slave_alloc = mptsas_slave_alloc,
1107 .slave_configure = mptsas_slave_configure,
1108 .target_destroy = mptsas_target_destroy,
1109 .slave_destroy = mptscsih_slave_destroy,
1110 .change_queue_depth = mptscsih_change_queue_depth,
1111 .eh_abort_handler = mptscsih_abort,
1112 .eh_device_reset_handler = mptscsih_dev_reset,
1113 .eh_bus_reset_handler = mptscsih_bus_reset,
1114 .eh_host_reset_handler = mptscsih_host_reset,
1115 .bios_param = mptscsih_bios_param,
1116 .can_queue = MPT_FC_CAN_QUEUE,
1118 .sg_tablesize = MPT_SCSI_SG_DEPTH,
1119 .max_sectors = 8192,
1121 .use_clustering = ENABLE_CLUSTERING,
1122 .shost_attrs = mptscsih_host_attrs,
1125 static int mptsas_get_linkerrors(struct sas_phy *phy)
1127 MPT_ADAPTER *ioc = phy_to_ioc(phy);
1128 ConfigExtendedPageHeader_t hdr;
1130 SasPhyPage1_t *buffer;
1131 dma_addr_t dma_handle;
1134 /* FIXME: only have link errors on local phys */
1135 if (!scsi_is_sas_phy_local(phy))
1138 hdr.PageVersion = MPI_SASPHY1_PAGEVERSION;
1139 hdr.ExtPageLength = 0;
1140 hdr.PageNumber = 1 /* page number 1*/;
1143 hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1144 hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_PHY;
1146 cfg.cfghdr.ehdr = &hdr;
1148 cfg.pageAddr = phy->identify.phy_identifier;
1149 cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1150 cfg.dir = 0; /* read */
1153 error = mpt_config(ioc, &cfg);
1156 if (!hdr.ExtPageLength)
1159 buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1164 cfg.physAddr = dma_handle;
1165 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1167 error = mpt_config(ioc, &cfg);
1169 goto out_free_consistent;
1171 mptsas_print_phy_pg1(buffer);
1173 phy->invalid_dword_count = le32_to_cpu(buffer->InvalidDwordCount);
1174 phy->running_disparity_error_count =
1175 le32_to_cpu(buffer->RunningDisparityErrorCount);
1176 phy->loss_of_dword_sync_count =
1177 le32_to_cpu(buffer->LossDwordSynchCount);
1178 phy->phy_reset_problem_count =
1179 le32_to_cpu(buffer->PhyResetProblemCount);
1181 out_free_consistent:
1182 pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1183 buffer, dma_handle);
1187 static int mptsas_mgmt_done(MPT_ADAPTER *ioc, MPT_FRAME_HDR *req,
1188 MPT_FRAME_HDR *reply)
1190 ioc->sas_mgmt.status |= MPT_SAS_MGMT_STATUS_COMMAND_GOOD;
1191 if (reply != NULL) {
1192 ioc->sas_mgmt.status |= MPT_SAS_MGMT_STATUS_RF_VALID;
1193 memcpy(ioc->sas_mgmt.reply, reply,
1194 min(ioc->reply_sz, 4 * reply->u.reply.MsgLength));
1196 complete(&ioc->sas_mgmt.done);
1200 static int mptsas_phy_reset(struct sas_phy *phy, int hard_reset)
1202 MPT_ADAPTER *ioc = phy_to_ioc(phy);
1203 SasIoUnitControlRequest_t *req;
1204 SasIoUnitControlReply_t *reply;
1207 unsigned long timeleft;
1208 int error = -ERESTARTSYS;
1210 /* FIXME: fusion doesn't allow non-local phy reset */
1211 if (!scsi_is_sas_phy_local(phy))
1214 /* not implemented for expanders */
1215 if (phy->identify.target_port_protocols & SAS_PROTOCOL_SMP)
1218 if (mutex_lock_interruptible(&ioc->sas_mgmt.mutex))
1221 mf = mpt_get_msg_frame(mptsasMgmtCtx, ioc);
1227 hdr = (MPIHeader_t *) mf;
1228 req = (SasIoUnitControlRequest_t *)mf;
1229 memset(req, 0, sizeof(SasIoUnitControlRequest_t));
1230 req->Function = MPI_FUNCTION_SAS_IO_UNIT_CONTROL;
1231 req->MsgContext = hdr->MsgContext;
1232 req->Operation = hard_reset ?
1233 MPI_SAS_OP_PHY_HARD_RESET : MPI_SAS_OP_PHY_LINK_RESET;
1234 req->PhyNum = phy->identify.phy_identifier;
1236 mpt_put_msg_frame(mptsasMgmtCtx, ioc, mf);
1238 timeleft = wait_for_completion_timeout(&ioc->sas_mgmt.done,
1241 /* On timeout reset the board */
1242 mpt_free_msg_frame(ioc, mf);
1243 mpt_HardResetHandler(ioc, CAN_SLEEP);
1248 /* a reply frame is expected */
1249 if ((ioc->sas_mgmt.status &
1250 MPT_IOCTL_STATUS_RF_VALID) == 0) {
1255 /* process the completed Reply Message Frame */
1256 reply = (SasIoUnitControlReply_t *)ioc->sas_mgmt.reply;
1257 if (reply->IOCStatus != MPI_IOCSTATUS_SUCCESS) {
1258 printk("%s: IOCStatus=0x%X IOCLogInfo=0x%X\n",
1269 mutex_unlock(&ioc->sas_mgmt.mutex);
1275 mptsas_get_enclosure_identifier(struct sas_rphy *rphy, u64 *identifier)
1277 MPT_ADAPTER *ioc = rphy_to_ioc(rphy);
1279 struct mptsas_portinfo *p;
1280 struct mptsas_enclosure enclosure_info;
1281 u64 enclosure_handle;
1283 mutex_lock(&ioc->sas_topology_mutex);
1284 list_for_each_entry(p, &ioc->sas_topology, list) {
1285 for (i = 0; i < p->num_phys; i++) {
1286 if (p->phy_info[i].attached.sas_address ==
1287 rphy->identify.sas_address) {
1288 enclosure_handle = p->phy_info[i].
1289 attached.handle_enclosure;
1294 mutex_unlock(&ioc->sas_topology_mutex);
1298 mutex_unlock(&ioc->sas_topology_mutex);
1299 memset(&enclosure_info, 0, sizeof(struct mptsas_enclosure));
1300 error = mptsas_sas_enclosure_pg0(ioc, &enclosure_info,
1301 (MPI_SAS_ENCLOS_PGAD_FORM_HANDLE <<
1302 MPI_SAS_ENCLOS_PGAD_FORM_SHIFT), enclosure_handle);
1304 *identifier = enclosure_info.enclosure_logical_id;
1309 mptsas_get_bay_identifier(struct sas_rphy *rphy)
1311 MPT_ADAPTER *ioc = rphy_to_ioc(rphy);
1312 struct mptsas_portinfo *p;
1315 mutex_lock(&ioc->sas_topology_mutex);
1316 list_for_each_entry(p, &ioc->sas_topology, list) {
1317 for (i = 0; i < p->num_phys; i++) {
1318 if (p->phy_info[i].attached.sas_address ==
1319 rphy->identify.sas_address) {
1320 rc = p->phy_info[i].attached.slot;
1327 mutex_unlock(&ioc->sas_topology_mutex);
1331 static struct sas_function_template mptsas_transport_functions = {
1332 .get_linkerrors = mptsas_get_linkerrors,
1333 .get_enclosure_identifier = mptsas_get_enclosure_identifier,
1334 .get_bay_identifier = mptsas_get_bay_identifier,
1335 .phy_reset = mptsas_phy_reset,
1338 static struct scsi_transport_template *mptsas_transport_template;
1341 mptsas_sas_io_unit_pg0(MPT_ADAPTER *ioc, struct mptsas_portinfo *port_info)
1343 ConfigExtendedPageHeader_t hdr;
1345 SasIOUnitPage0_t *buffer;
1346 dma_addr_t dma_handle;
1349 hdr.PageVersion = MPI_SASIOUNITPAGE0_PAGEVERSION;
1350 hdr.ExtPageLength = 0;
1354 hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1355 hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
1357 cfg.cfghdr.ehdr = &hdr;
1360 cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1361 cfg.dir = 0; /* read */
1364 error = mpt_config(ioc, &cfg);
1367 if (!hdr.ExtPageLength) {
1372 buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1379 cfg.physAddr = dma_handle;
1380 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1382 error = mpt_config(ioc, &cfg);
1384 goto out_free_consistent;
1386 port_info->num_phys = buffer->NumPhys;
1387 port_info->phy_info = kcalloc(port_info->num_phys,
1388 sizeof(*port_info->phy_info),GFP_KERNEL);
1389 if (!port_info->phy_info) {
1391 goto out_free_consistent;
1394 ioc->nvdata_version_persistent =
1395 le16_to_cpu(buffer->NvdataVersionPersistent);
1396 ioc->nvdata_version_default =
1397 le16_to_cpu(buffer->NvdataVersionDefault);
1399 for (i = 0; i < port_info->num_phys; i++) {
1400 mptsas_print_phy_data(&buffer->PhyData[i]);
1401 port_info->phy_info[i].phy_id = i;
1402 port_info->phy_info[i].port_id =
1403 buffer->PhyData[i].Port;
1404 port_info->phy_info[i].negotiated_link_rate =
1405 buffer->PhyData[i].NegotiatedLinkRate;
1406 port_info->phy_info[i].portinfo = port_info;
1407 port_info->phy_info[i].handle =
1408 le16_to_cpu(buffer->PhyData[i].ControllerDevHandle);
1411 out_free_consistent:
1412 pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1413 buffer, dma_handle);
1419 mptsas_sas_io_unit_pg1(MPT_ADAPTER *ioc)
1421 ConfigExtendedPageHeader_t hdr;
1423 SasIOUnitPage1_t *buffer;
1424 dma_addr_t dma_handle;
1426 u16 device_missing_delay;
1428 memset(&hdr, 0, sizeof(ConfigExtendedPageHeader_t));
1429 memset(&cfg, 0, sizeof(CONFIGPARMS));
1431 cfg.cfghdr.ehdr = &hdr;
1432 cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1434 cfg.cfghdr.ehdr->PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1435 cfg.cfghdr.ehdr->ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
1436 cfg.cfghdr.ehdr->PageVersion = MPI_SASIOUNITPAGE1_PAGEVERSION;
1437 cfg.cfghdr.ehdr->PageNumber = 1;
1439 error = mpt_config(ioc, &cfg);
1442 if (!hdr.ExtPageLength) {
1447 buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1454 cfg.physAddr = dma_handle;
1455 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1457 error = mpt_config(ioc, &cfg);
1459 goto out_free_consistent;
1461 ioc->io_missing_delay =
1462 le16_to_cpu(buffer->IODeviceMissingDelay);
1463 device_missing_delay = le16_to_cpu(buffer->ReportDeviceMissingDelay);
1464 ioc->device_missing_delay = (device_missing_delay & MPI_SAS_IOUNIT1_REPORT_MISSING_UNIT_16) ?
1465 (device_missing_delay & MPI_SAS_IOUNIT1_REPORT_MISSING_TIMEOUT_MASK) * 16 :
1466 device_missing_delay & MPI_SAS_IOUNIT1_REPORT_MISSING_TIMEOUT_MASK;
1468 out_free_consistent:
1469 pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1470 buffer, dma_handle);
1476 mptsas_sas_phy_pg0(MPT_ADAPTER *ioc, struct mptsas_phyinfo *phy_info,
1477 u32 form, u32 form_specific)
1479 ConfigExtendedPageHeader_t hdr;
1481 SasPhyPage0_t *buffer;
1482 dma_addr_t dma_handle;
1485 hdr.PageVersion = MPI_SASPHY0_PAGEVERSION;
1486 hdr.ExtPageLength = 0;
1490 hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1491 hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_PHY;
1493 cfg.cfghdr.ehdr = &hdr;
1494 cfg.dir = 0; /* read */
1497 /* Get Phy Pg 0 for each Phy. */
1499 cfg.pageAddr = form + form_specific;
1500 cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1502 error = mpt_config(ioc, &cfg);
1506 if (!hdr.ExtPageLength) {
1511 buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1518 cfg.physAddr = dma_handle;
1519 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1521 error = mpt_config(ioc, &cfg);
1523 goto out_free_consistent;
1525 mptsas_print_phy_pg0(buffer);
1527 phy_info->hw_link_rate = buffer->HwLinkRate;
1528 phy_info->programmed_link_rate = buffer->ProgrammedLinkRate;
1529 phy_info->identify.handle = le16_to_cpu(buffer->OwnerDevHandle);
1530 phy_info->attached.handle = le16_to_cpu(buffer->AttachedDevHandle);
1532 out_free_consistent:
1533 pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1534 buffer, dma_handle);
1540 mptsas_sas_device_pg0(MPT_ADAPTER *ioc, struct mptsas_devinfo *device_info,
1541 u32 form, u32 form_specific)
1543 ConfigExtendedPageHeader_t hdr;
1545 SasDevicePage0_t *buffer;
1546 dma_addr_t dma_handle;
1550 if (ioc->sas_discovery_runtime &&
1551 mptsas_is_end_device(device_info))
1554 hdr.PageVersion = MPI_SASDEVICE0_PAGEVERSION;
1555 hdr.ExtPageLength = 0;
1559 hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1560 hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_DEVICE;
1562 cfg.cfghdr.ehdr = &hdr;
1563 cfg.pageAddr = form + form_specific;
1565 cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1566 cfg.dir = 0; /* read */
1569 memset(device_info, 0, sizeof(struct mptsas_devinfo));
1570 error = mpt_config(ioc, &cfg);
1573 if (!hdr.ExtPageLength) {
1578 buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1585 cfg.physAddr = dma_handle;
1586 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1588 error = mpt_config(ioc, &cfg);
1590 goto out_free_consistent;
1592 mptsas_print_device_pg0(buffer);
1594 device_info->handle = le16_to_cpu(buffer->DevHandle);
1595 device_info->handle_parent = le16_to_cpu(buffer->ParentDevHandle);
1596 device_info->handle_enclosure =
1597 le16_to_cpu(buffer->EnclosureHandle);
1598 device_info->slot = le16_to_cpu(buffer->Slot);
1599 device_info->phy_id = buffer->PhyNum;
1600 device_info->port_id = buffer->PhysicalPort;
1601 device_info->id = buffer->TargetID;
1602 device_info->phys_disk_num = ~0;
1603 device_info->channel = buffer->Bus;
1604 memcpy(&sas_address, &buffer->SASAddress, sizeof(__le64));
1605 device_info->sas_address = le64_to_cpu(sas_address);
1606 device_info->device_info =
1607 le32_to_cpu(buffer->DeviceInfo);
1609 out_free_consistent:
1610 pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1611 buffer, dma_handle);
1617 mptsas_sas_expander_pg0(MPT_ADAPTER *ioc, struct mptsas_portinfo *port_info,
1618 u32 form, u32 form_specific)
1620 ConfigExtendedPageHeader_t hdr;
1622 SasExpanderPage0_t *buffer;
1623 dma_addr_t dma_handle;
1626 hdr.PageVersion = MPI_SASEXPANDER0_PAGEVERSION;
1627 hdr.ExtPageLength = 0;
1631 hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1632 hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_EXPANDER;
1634 cfg.cfghdr.ehdr = &hdr;
1636 cfg.pageAddr = form + form_specific;
1637 cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1638 cfg.dir = 0; /* read */
1641 memset(port_info, 0, sizeof(struct mptsas_portinfo));
1642 error = mpt_config(ioc, &cfg);
1646 if (!hdr.ExtPageLength) {
1651 buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1658 cfg.physAddr = dma_handle;
1659 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1661 error = mpt_config(ioc, &cfg);
1663 goto out_free_consistent;
1665 /* save config data */
1666 port_info->num_phys = buffer->NumPhys;
1667 port_info->phy_info = kcalloc(port_info->num_phys,
1668 sizeof(*port_info->phy_info),GFP_KERNEL);
1669 if (!port_info->phy_info) {
1671 goto out_free_consistent;
1674 for (i = 0; i < port_info->num_phys; i++) {
1675 port_info->phy_info[i].portinfo = port_info;
1676 port_info->phy_info[i].handle =
1677 le16_to_cpu(buffer->DevHandle);
1680 out_free_consistent:
1681 pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1682 buffer, dma_handle);
1688 mptsas_sas_expander_pg1(MPT_ADAPTER *ioc, struct mptsas_phyinfo *phy_info,
1689 u32 form, u32 form_specific)
1691 ConfigExtendedPageHeader_t hdr;
1693 SasExpanderPage1_t *buffer;
1694 dma_addr_t dma_handle;
1697 if (ioc->sas_discovery_runtime &&
1698 mptsas_is_end_device(&phy_info->attached))
1701 hdr.PageVersion = MPI_SASEXPANDER0_PAGEVERSION;
1702 hdr.ExtPageLength = 0;
1706 hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
1707 hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_EXPANDER;
1709 cfg.cfghdr.ehdr = &hdr;
1711 cfg.pageAddr = form + form_specific;
1712 cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
1713 cfg.dir = 0; /* read */
1716 error = mpt_config(ioc, &cfg);
1720 if (!hdr.ExtPageLength) {
1725 buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1732 cfg.physAddr = dma_handle;
1733 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
1735 error = mpt_config(ioc, &cfg);
1737 goto out_free_consistent;
1740 mptsas_print_expander_pg1(buffer);
1742 /* save config data */
1743 phy_info->phy_id = buffer->PhyIdentifier;
1744 phy_info->port_id = buffer->PhysicalPort;
1745 phy_info->negotiated_link_rate = buffer->NegotiatedLinkRate;
1746 phy_info->programmed_link_rate = buffer->ProgrammedLinkRate;
1747 phy_info->hw_link_rate = buffer->HwLinkRate;
1748 phy_info->identify.handle = le16_to_cpu(buffer->OwnerDevHandle);
1749 phy_info->attached.handle = le16_to_cpu(buffer->AttachedDevHandle);
1751 out_free_consistent:
1752 pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
1753 buffer, dma_handle);
1759 mptsas_parse_device_info(struct sas_identify *identify,
1760 struct mptsas_devinfo *device_info)
1764 identify->sas_address = device_info->sas_address;
1765 identify->phy_identifier = device_info->phy_id;
1768 * Fill in Phy Initiator Port Protocol.
1769 * Bits 6:3, more than one bit can be set, fall through cases.
1771 protocols = device_info->device_info & 0x78;
1772 identify->initiator_port_protocols = 0;
1773 if (protocols & MPI_SAS_DEVICE_INFO_SSP_INITIATOR)
1774 identify->initiator_port_protocols |= SAS_PROTOCOL_SSP;
1775 if (protocols & MPI_SAS_DEVICE_INFO_STP_INITIATOR)
1776 identify->initiator_port_protocols |= SAS_PROTOCOL_STP;
1777 if (protocols & MPI_SAS_DEVICE_INFO_SMP_INITIATOR)
1778 identify->initiator_port_protocols |= SAS_PROTOCOL_SMP;
1779 if (protocols & MPI_SAS_DEVICE_INFO_SATA_HOST)
1780 identify->initiator_port_protocols |= SAS_PROTOCOL_SATA;
1783 * Fill in Phy Target Port Protocol.
1784 * Bits 10:7, more than one bit can be set, fall through cases.
1786 protocols = device_info->device_info & 0x780;
1787 identify->target_port_protocols = 0;
1788 if (protocols & MPI_SAS_DEVICE_INFO_SSP_TARGET)
1789 identify->target_port_protocols |= SAS_PROTOCOL_SSP;
1790 if (protocols & MPI_SAS_DEVICE_INFO_STP_TARGET)
1791 identify->target_port_protocols |= SAS_PROTOCOL_STP;
1792 if (protocols & MPI_SAS_DEVICE_INFO_SMP_TARGET)
1793 identify->target_port_protocols |= SAS_PROTOCOL_SMP;
1794 if (protocols & MPI_SAS_DEVICE_INFO_SATA_DEVICE)
1795 identify->target_port_protocols |= SAS_PROTOCOL_SATA;
1798 * Fill in Attached device type.
1800 switch (device_info->device_info &
1801 MPI_SAS_DEVICE_INFO_MASK_DEVICE_TYPE) {
1802 case MPI_SAS_DEVICE_INFO_NO_DEVICE:
1803 identify->device_type = SAS_PHY_UNUSED;
1805 case MPI_SAS_DEVICE_INFO_END_DEVICE:
1806 identify->device_type = SAS_END_DEVICE;
1808 case MPI_SAS_DEVICE_INFO_EDGE_EXPANDER:
1809 identify->device_type = SAS_EDGE_EXPANDER_DEVICE;
1811 case MPI_SAS_DEVICE_INFO_FANOUT_EXPANDER:
1812 identify->device_type = SAS_FANOUT_EXPANDER_DEVICE;
1817 static int mptsas_probe_one_phy(struct device *dev,
1818 struct mptsas_phyinfo *phy_info, int index, int local)
1821 struct sas_phy *phy;
1822 struct sas_port *port;
1830 if (!phy_info->phy) {
1831 phy = sas_phy_alloc(dev, index);
1837 phy = phy_info->phy;
1839 mptsas_parse_device_info(&phy->identify, &phy_info->identify);
1842 * Set Negotiated link rate.
1844 switch (phy_info->negotiated_link_rate) {
1845 case MPI_SAS_IOUNIT0_RATE_PHY_DISABLED:
1846 phy->negotiated_linkrate = SAS_PHY_DISABLED;
1848 case MPI_SAS_IOUNIT0_RATE_FAILED_SPEED_NEGOTIATION:
1849 phy->negotiated_linkrate = SAS_LINK_RATE_FAILED;
1851 case MPI_SAS_IOUNIT0_RATE_1_5:
1852 phy->negotiated_linkrate = SAS_LINK_RATE_1_5_GBPS;
1854 case MPI_SAS_IOUNIT0_RATE_3_0:
1855 phy->negotiated_linkrate = SAS_LINK_RATE_3_0_GBPS;
1857 case MPI_SAS_IOUNIT0_RATE_SATA_OOB_COMPLETE:
1858 case MPI_SAS_IOUNIT0_RATE_UNKNOWN:
1860 phy->negotiated_linkrate = SAS_LINK_RATE_UNKNOWN;
1865 * Set Max hardware link rate.
1867 switch (phy_info->hw_link_rate & MPI_SAS_PHY0_PRATE_MAX_RATE_MASK) {
1868 case MPI_SAS_PHY0_HWRATE_MAX_RATE_1_5:
1869 phy->maximum_linkrate_hw = SAS_LINK_RATE_1_5_GBPS;
1871 case MPI_SAS_PHY0_PRATE_MAX_RATE_3_0:
1872 phy->maximum_linkrate_hw = SAS_LINK_RATE_3_0_GBPS;
1879 * Set Max programmed link rate.
1881 switch (phy_info->programmed_link_rate &
1882 MPI_SAS_PHY0_PRATE_MAX_RATE_MASK) {
1883 case MPI_SAS_PHY0_PRATE_MAX_RATE_1_5:
1884 phy->maximum_linkrate = SAS_LINK_RATE_1_5_GBPS;
1886 case MPI_SAS_PHY0_PRATE_MAX_RATE_3_0:
1887 phy->maximum_linkrate = SAS_LINK_RATE_3_0_GBPS;
1894 * Set Min hardware link rate.
1896 switch (phy_info->hw_link_rate & MPI_SAS_PHY0_HWRATE_MIN_RATE_MASK) {
1897 case MPI_SAS_PHY0_HWRATE_MIN_RATE_1_5:
1898 phy->minimum_linkrate_hw = SAS_LINK_RATE_1_5_GBPS;
1900 case MPI_SAS_PHY0_PRATE_MIN_RATE_3_0:
1901 phy->minimum_linkrate_hw = SAS_LINK_RATE_3_0_GBPS;
1908 * Set Min programmed link rate.
1910 switch (phy_info->programmed_link_rate &
1911 MPI_SAS_PHY0_PRATE_MIN_RATE_MASK) {
1912 case MPI_SAS_PHY0_PRATE_MIN_RATE_1_5:
1913 phy->minimum_linkrate = SAS_LINK_RATE_1_5_GBPS;
1915 case MPI_SAS_PHY0_PRATE_MIN_RATE_3_0:
1916 phy->minimum_linkrate = SAS_LINK_RATE_3_0_GBPS;
1922 if (!phy_info->phy) {
1924 error = sas_phy_add(phy);
1929 phy_info->phy = phy;
1932 if (!phy_info->attached.handle ||
1933 !phy_info->port_details)
1936 port = mptsas_get_port(phy_info);
1937 ioc = phy_to_ioc(phy_info->phy);
1939 if (phy_info->sas_port_add_phy) {
1942 port = sas_port_alloc_num(dev);
1947 error = sas_port_add(port);
1949 dfailprintk((MYIOC_s_ERR_FMT
1950 "%s: exit at line=%d\n", ioc->name,
1951 __FUNCTION__, __LINE__));
1954 mptsas_set_port(phy_info, port);
1955 dsaswideprintk((KERN_DEBUG
1956 "sas_port_alloc: port=%p dev=%p port_id=%d\n",
1957 port, dev, port->port_identifier));
1959 dsaswideprintk((KERN_DEBUG "sas_port_add_phy: phy_id=%d\n",
1961 sas_port_add_phy(port, phy_info->phy);
1962 phy_info->sas_port_add_phy = 0;
1965 if (!mptsas_get_rphy(phy_info) && port && !port->rphy) {
1967 struct sas_rphy *rphy;
1968 struct device *parent;
1969 struct sas_identify identify;
1971 parent = dev->parent->parent;
1973 * Let the hotplug_work thread handle processing
1974 * the adding/removing of devices that occur
1975 * after start of day.
1977 if (ioc->sas_discovery_runtime &&
1978 mptsas_is_end_device(&phy_info->attached))
1981 mptsas_parse_device_info(&identify, &phy_info->attached);
1982 if (scsi_is_host_device(parent)) {
1983 struct mptsas_portinfo *port_info;
1986 mutex_lock(&ioc->sas_topology_mutex);
1987 port_info = mptsas_find_portinfo_by_handle(ioc,
1989 mutex_unlock(&ioc->sas_topology_mutex);
1991 for (i = 0; i < port_info->num_phys; i++)
1992 if (port_info->phy_info[i].identify.sas_address ==
1993 identify.sas_address) {
1994 sas_port_mark_backlink(port);
1998 } else if (scsi_is_sas_rphy(parent)) {
1999 struct sas_rphy *parent_rphy = dev_to_rphy(parent);
2000 if (identify.sas_address ==
2001 parent_rphy->identify.sas_address) {
2002 sas_port_mark_backlink(port);
2007 switch (identify.device_type) {
2008 case SAS_END_DEVICE:
2009 rphy = sas_end_device_alloc(port);
2011 case SAS_EDGE_EXPANDER_DEVICE:
2012 case SAS_FANOUT_EXPANDER_DEVICE:
2013 rphy = sas_expander_alloc(port, identify.device_type);
2020 dfailprintk((MYIOC_s_ERR_FMT
2021 "%s: exit at line=%d\n", ioc->name,
2022 __FUNCTION__, __LINE__));
2026 rphy->identify = identify;
2027 error = sas_rphy_add(rphy);
2029 dfailprintk((MYIOC_s_ERR_FMT
2030 "%s: exit at line=%d\n", ioc->name,
2031 __FUNCTION__, __LINE__));
2032 sas_rphy_free(rphy);
2035 mptsas_set_rphy(phy_info, rphy);
2043 mptsas_probe_hba_phys(MPT_ADAPTER *ioc)
2045 struct mptsas_portinfo *port_info, *hba;
2046 int error = -ENOMEM, i;
2048 hba = kzalloc(sizeof(*port_info), GFP_KERNEL);
2052 error = mptsas_sas_io_unit_pg0(ioc, hba);
2054 goto out_free_port_info;
2056 mptsas_sas_io_unit_pg1(ioc);
2057 mutex_lock(&ioc->sas_topology_mutex);
2058 ioc->handle = hba->phy_info[0].handle;
2059 port_info = mptsas_find_portinfo_by_handle(ioc, ioc->handle);
2062 list_add_tail(&port_info->list, &ioc->sas_topology);
2064 for (i = 0; i < hba->num_phys; i++) {
2065 port_info->phy_info[i].negotiated_link_rate =
2066 hba->phy_info[i].negotiated_link_rate;
2067 port_info->phy_info[i].handle =
2068 hba->phy_info[i].handle;
2069 port_info->phy_info[i].port_id =
2070 hba->phy_info[i].port_id;
2072 kfree(hba->phy_info);
2076 mutex_unlock(&ioc->sas_topology_mutex);
2077 for (i = 0; i < port_info->num_phys; i++) {
2078 mptsas_sas_phy_pg0(ioc, &port_info->phy_info[i],
2079 (MPI_SAS_PHY_PGAD_FORM_PHY_NUMBER <<
2080 MPI_SAS_PHY_PGAD_FORM_SHIFT), i);
2082 mptsas_sas_device_pg0(ioc, &port_info->phy_info[i].identify,
2083 (MPI_SAS_DEVICE_PGAD_FORM_HANDLE <<
2084 MPI_SAS_DEVICE_PGAD_FORM_SHIFT),
2085 port_info->phy_info[i].handle);
2086 port_info->phy_info[i].identify.phy_id =
2087 port_info->phy_info[i].phy_id = i;
2088 if (port_info->phy_info[i].attached.handle)
2089 mptsas_sas_device_pg0(ioc,
2090 &port_info->phy_info[i].attached,
2091 (MPI_SAS_DEVICE_PGAD_FORM_HANDLE <<
2092 MPI_SAS_DEVICE_PGAD_FORM_SHIFT),
2093 port_info->phy_info[i].attached.handle);
2096 mptsas_setup_wide_ports(ioc, port_info);
2098 for (i = 0; i < port_info->num_phys; i++, ioc->sas_index++)
2099 mptsas_probe_one_phy(&ioc->sh->shost_gendev,
2100 &port_info->phy_info[i], ioc->sas_index, 1);
2111 mptsas_probe_expander_phys(MPT_ADAPTER *ioc, u32 *handle)
2113 struct mptsas_portinfo *port_info, *p, *ex;
2114 struct device *parent;
2115 struct sas_rphy *rphy;
2116 int error = -ENOMEM, i, j;
2118 ex = kzalloc(sizeof(*port_info), GFP_KERNEL);
2122 error = mptsas_sas_expander_pg0(ioc, ex,
2123 (MPI_SAS_EXPAND_PGAD_FORM_GET_NEXT_HANDLE <<
2124 MPI_SAS_EXPAND_PGAD_FORM_SHIFT), *handle);
2126 goto out_free_port_info;
2128 *handle = ex->phy_info[0].handle;
2130 mutex_lock(&ioc->sas_topology_mutex);
2131 port_info = mptsas_find_portinfo_by_handle(ioc, *handle);
2134 list_add_tail(&port_info->list, &ioc->sas_topology);
2136 for (i = 0; i < ex->num_phys; i++) {
2137 port_info->phy_info[i].handle =
2138 ex->phy_info[i].handle;
2139 port_info->phy_info[i].port_id =
2140 ex->phy_info[i].port_id;
2142 kfree(ex->phy_info);
2146 mutex_unlock(&ioc->sas_topology_mutex);
2148 for (i = 0; i < port_info->num_phys; i++) {
2149 mptsas_sas_expander_pg1(ioc, &port_info->phy_info[i],
2150 (MPI_SAS_EXPAND_PGAD_FORM_HANDLE_PHY_NUM <<
2151 MPI_SAS_EXPAND_PGAD_FORM_SHIFT), (i << 16) + *handle);
2153 if (port_info->phy_info[i].identify.handle) {
2154 mptsas_sas_device_pg0(ioc,
2155 &port_info->phy_info[i].identify,
2156 (MPI_SAS_DEVICE_PGAD_FORM_HANDLE <<
2157 MPI_SAS_DEVICE_PGAD_FORM_SHIFT),
2158 port_info->phy_info[i].identify.handle);
2159 port_info->phy_info[i].identify.phy_id =
2160 port_info->phy_info[i].phy_id;
2163 if (port_info->phy_info[i].attached.handle) {
2164 mptsas_sas_device_pg0(ioc,
2165 &port_info->phy_info[i].attached,
2166 (MPI_SAS_DEVICE_PGAD_FORM_HANDLE <<
2167 MPI_SAS_DEVICE_PGAD_FORM_SHIFT),
2168 port_info->phy_info[i].attached.handle);
2169 port_info->phy_info[i].attached.phy_id =
2170 port_info->phy_info[i].phy_id;
2174 parent = &ioc->sh->shost_gendev;
2175 for (i = 0; i < port_info->num_phys; i++) {
2176 mutex_lock(&ioc->sas_topology_mutex);
2177 list_for_each_entry(p, &ioc->sas_topology, list) {
2178 for (j = 0; j < p->num_phys; j++) {
2179 if (port_info->phy_info[i].identify.handle !=
2180 p->phy_info[j].attached.handle)
2182 rphy = mptsas_get_rphy(&p->phy_info[j]);
2183 parent = &rphy->dev;
2186 mutex_unlock(&ioc->sas_topology_mutex);
2189 mptsas_setup_wide_ports(ioc, port_info);
2191 for (i = 0; i < port_info->num_phys; i++, ioc->sas_index++)
2192 mptsas_probe_one_phy(parent, &port_info->phy_info[i],
2199 kfree(ex->phy_info);
2207 * mptsas_delete_expander_phys
2210 * This will traverse topology, and remove expanders
2211 * that are no longer present
2214 mptsas_delete_expander_phys(MPT_ADAPTER *ioc)
2216 struct mptsas_portinfo buffer;
2217 struct mptsas_portinfo *port_info, *n, *parent;
2218 struct mptsas_phyinfo *phy_info;
2219 struct sas_port * port;
2221 u64 expander_sas_address;
2223 mutex_lock(&ioc->sas_topology_mutex);
2224 list_for_each_entry_safe(port_info, n, &ioc->sas_topology, list) {
2226 if (port_info->phy_info &&
2227 (!(port_info->phy_info[0].identify.device_info &
2228 MPI_SAS_DEVICE_INFO_SMP_TARGET)))
2231 if (mptsas_sas_expander_pg0(ioc, &buffer,
2232 (MPI_SAS_EXPAND_PGAD_FORM_HANDLE <<
2233 MPI_SAS_EXPAND_PGAD_FORM_SHIFT),
2234 port_info->phy_info[0].handle)) {
2237 * Obtain the port_info instance to the parent port
2239 parent = mptsas_find_portinfo_by_handle(ioc,
2240 port_info->phy_info[0].identify.handle_parent);
2245 expander_sas_address =
2246 port_info->phy_info[0].identify.sas_address;
2249 * Delete rphys in the parent that point
2250 * to this expander. The transport layer will
2251 * cleanup all the children.
2253 phy_info = parent->phy_info;
2254 for (i = 0; i < parent->num_phys; i++, phy_info++) {
2255 port = mptsas_get_port(phy_info);
2258 if (phy_info->attached.sas_address !=
2259 expander_sas_address)
2261 #ifdef MPT_DEBUG_SAS_WIDE
2262 dev_printk(KERN_DEBUG, &port->dev,
2263 "delete port (%d)\n", port->port_identifier);
2265 sas_port_delete(port);
2266 mptsas_port_delete(phy_info->port_details);
2270 phy_info = port_info->phy_info;
2271 for (i = 0; i < port_info->num_phys; i++, phy_info++)
2272 mptsas_port_delete(phy_info->port_details);
2274 list_del(&port_info->list);
2275 kfree(port_info->phy_info);
2279 * Free this memory allocated from inside
2280 * mptsas_sas_expander_pg0
2282 kfree(buffer.phy_info);
2284 mutex_unlock(&ioc->sas_topology_mutex);
2288 * Start of day discovery
2291 mptsas_scan_sas_topology(MPT_ADAPTER *ioc)
2293 u32 handle = 0xFFFF;
2296 mutex_lock(&ioc->sas_discovery_mutex);
2297 mptsas_probe_hba_phys(ioc);
2298 while (!mptsas_probe_expander_phys(ioc, &handle))
2301 Reporting RAID volumes.
2303 if (!ioc->ir_firmware)
2305 if (!ioc->raid_data.pIocPg2)
2307 if (!ioc->raid_data.pIocPg2->NumActiveVolumes)
2309 for (i = 0; i < ioc->raid_data.pIocPg2->NumActiveVolumes; i++) {
2310 scsi_add_device(ioc->sh, MPTSAS_RAID_CHANNEL,
2311 ioc->raid_data.pIocPg2->RaidVolume[i].VolumeID, 0);
2314 mutex_unlock(&ioc->sas_discovery_mutex);
2318 * Work queue thread to handle Runtime discovery
2319 * Mere purpose is the hot add/delete of expanders
2323 __mptsas_discovery_work(MPT_ADAPTER *ioc)
2325 u32 handle = 0xFFFF;
2327 ioc->sas_discovery_runtime=1;
2328 mptsas_delete_expander_phys(ioc);
2329 mptsas_probe_hba_phys(ioc);
2330 while (!mptsas_probe_expander_phys(ioc, &handle))
2332 ioc->sas_discovery_runtime=0;
2336 * Work queue thread to handle Runtime discovery
2337 * Mere purpose is the hot add/delete of expanders
2341 mptsas_discovery_work(struct work_struct *work)
2343 struct mptsas_discovery_event *ev =
2344 container_of(work, struct mptsas_discovery_event, work);
2345 MPT_ADAPTER *ioc = ev->ioc;
2347 mutex_lock(&ioc->sas_discovery_mutex);
2348 __mptsas_discovery_work(ioc);
2349 mutex_unlock(&ioc->sas_discovery_mutex);
2353 static struct mptsas_phyinfo *
2354 mptsas_find_phyinfo_by_sas_address(MPT_ADAPTER *ioc, u64 sas_address)
2356 struct mptsas_portinfo *port_info;
2357 struct mptsas_phyinfo *phy_info = NULL;
2360 mutex_lock(&ioc->sas_topology_mutex);
2361 list_for_each_entry(port_info, &ioc->sas_topology, list) {
2362 for (i = 0; i < port_info->num_phys; i++) {
2363 if (!mptsas_is_end_device(
2364 &port_info->phy_info[i].attached))
2366 if (port_info->phy_info[i].attached.sas_address
2369 phy_info = &port_info->phy_info[i];
2373 mutex_unlock(&ioc->sas_topology_mutex);
2377 static struct mptsas_phyinfo *
2378 mptsas_find_phyinfo_by_target(MPT_ADAPTER *ioc, u8 channel, u8 id)
2380 struct mptsas_portinfo *port_info;
2381 struct mptsas_phyinfo *phy_info = NULL;
2384 mutex_lock(&ioc->sas_topology_mutex);
2385 list_for_each_entry(port_info, &ioc->sas_topology, list) {
2386 for (i = 0; i < port_info->num_phys; i++) {
2387 if (!mptsas_is_end_device(
2388 &port_info->phy_info[i].attached))
2390 if (port_info->phy_info[i].attached.id != id)
2392 if (port_info->phy_info[i].attached.channel != channel)
2394 phy_info = &port_info->phy_info[i];
2398 mutex_unlock(&ioc->sas_topology_mutex);
2402 static struct mptsas_phyinfo *
2403 mptsas_find_phyinfo_by_phys_disk_num(MPT_ADAPTER *ioc, u8 channel, u8 id)
2405 struct mptsas_portinfo *port_info;
2406 struct mptsas_phyinfo *phy_info = NULL;
2409 mutex_lock(&ioc->sas_topology_mutex);
2410 list_for_each_entry(port_info, &ioc->sas_topology, list) {
2411 for (i = 0; i < port_info->num_phys; i++) {
2412 if (!mptsas_is_end_device(
2413 &port_info->phy_info[i].attached))
2415 if (port_info->phy_info[i].attached.phys_disk_num == ~0)
2417 if (port_info->phy_info[i].attached.phys_disk_num != id)
2419 if (port_info->phy_info[i].attached.channel != channel)
2421 phy_info = &port_info->phy_info[i];
2425 mutex_unlock(&ioc->sas_topology_mutex);
2430 * Work queue thread to clear the persitency table
2433 mptsas_persist_clear_table(struct work_struct *work)
2435 MPT_ADAPTER *ioc = container_of(work, MPT_ADAPTER, sas_persist_task);
2437 mptbase_sas_persist_operation(ioc, MPI_SAS_OP_CLEAR_NOT_PRESENT);
2441 mptsas_reprobe_lun(struct scsi_device *sdev, void *data)
2445 sdev->no_uld_attach = data ? 1 : 0;
2446 rc = scsi_device_reprobe(sdev);
2450 mptsas_reprobe_target(struct scsi_target *starget, int uld_attach)
2452 starget_for_each_device(starget, uld_attach ? (void *)1 : NULL,
2453 mptsas_reprobe_lun);
2457 mptsas_adding_inactive_raid_components(MPT_ADAPTER *ioc, u8 channel, u8 id)
2460 ConfigPageHeader_t hdr;
2461 dma_addr_t dma_handle;
2462 pRaidVolumePage0_t buffer = NULL;
2463 RaidPhysDiskPage0_t phys_disk;
2465 struct mptsas_hotplug_event *ev;
2467 memset(&cfg, 0 , sizeof(CONFIGPARMS));
2468 memset(&hdr, 0 , sizeof(ConfigPageHeader_t));
2469 hdr.PageType = MPI_CONFIG_PAGETYPE_RAID_VOLUME;
2470 cfg.pageAddr = (channel << 8) + id;
2471 cfg.cfghdr.hdr = &hdr;
2472 cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
2474 if (mpt_config(ioc, &cfg) != 0)
2477 if (!hdr.PageLength)
2480 buffer = pci_alloc_consistent(ioc->pcidev, hdr.PageLength * 4,
2486 cfg.physAddr = dma_handle;
2487 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
2489 if (mpt_config(ioc, &cfg) != 0)
2492 if (!(buffer->VolumeStatus.Flags &
2493 MPI_RAIDVOL0_STATUS_FLAG_VOLUME_INACTIVE))
2496 if (!buffer->NumPhysDisks)
2499 for (i = 0; i < buffer->NumPhysDisks; i++) {
2501 if (mpt_raid_phys_disk_pg0(ioc,
2502 buffer->PhysDisk[i].PhysDiskNum, &phys_disk) != 0)
2505 ev = kzalloc(sizeof(*ev), GFP_ATOMIC);
2507 printk(KERN_WARNING "mptsas: lost hotplug event\n");
2511 INIT_WORK(&ev->work, mptsas_hotplug_work);
2513 ev->id = phys_disk.PhysDiskID;
2514 ev->channel = phys_disk.PhysDiskBus;
2515 ev->phys_disk_num_valid = 1;
2516 ev->phys_disk_num = phys_disk.PhysDiskNum;
2517 ev->event_type = MPTSAS_ADD_DEVICE;
2518 schedule_work(&ev->work);
2523 pci_free_consistent(ioc->pcidev, hdr.PageLength * 4, buffer,
2527 * Work queue thread to handle SAS hotplug events
2530 mptsas_hotplug_work(struct work_struct *work)
2532 struct mptsas_hotplug_event *ev =
2533 container_of(work, struct mptsas_hotplug_event, work);
2535 MPT_ADAPTER *ioc = ev->ioc;
2536 struct mptsas_phyinfo *phy_info;
2537 struct sas_rphy *rphy;
2538 struct sas_port *port;
2539 struct scsi_device *sdev;
2540 struct scsi_target * starget;
2541 struct sas_identify identify;
2543 struct mptsas_devinfo sas_device;
2544 VirtTarget *vtarget;
2545 VirtDevice *vdevice;
2547 mutex_lock(&ioc->sas_discovery_mutex);
2548 switch (ev->event_type) {
2549 case MPTSAS_DEL_DEVICE:
2552 if (ev->phys_disk_num_valid) {
2553 if (ev->hidden_raid_component){
2554 if (mptsas_sas_device_pg0(ioc, &sas_device,
2555 (MPI_SAS_DEVICE_PGAD_FORM_BUS_TARGET_ID <<
2556 MPI_SAS_DEVICE_PGAD_FORM_SHIFT),
2557 (ev->channel << 8) + ev->id)) {
2558 dfailprintk((MYIOC_s_ERR_FMT
2559 "%s: exit at line=%d\n", ioc->name,
2560 __FUNCTION__, __LINE__));
2563 phy_info = mptsas_find_phyinfo_by_sas_address(
2564 ioc, sas_device.sas_address);
2566 phy_info = mptsas_find_phyinfo_by_phys_disk_num(
2567 ioc, ev->channel, ev->phys_disk_num);
2571 phy_info = mptsas_find_phyinfo_by_target(ioc,
2572 ev->channel, ev->id);
2575 * Sanity checks, for non-existing phys and remote rphys.
2578 dfailprintk((MYIOC_s_ERR_FMT
2579 "%s: exit at line=%d\n", ioc->name,
2580 __FUNCTION__, __LINE__));
2583 if (!phy_info->port_details) {
2584 dfailprintk((MYIOC_s_ERR_FMT
2585 "%s: exit at line=%d\n", ioc->name,
2586 __FUNCTION__, __LINE__));
2589 rphy = mptsas_get_rphy(phy_info);
2591 dfailprintk((MYIOC_s_ERR_FMT
2592 "%s: exit at line=%d\n", ioc->name,
2593 __FUNCTION__, __LINE__));
2597 port = mptsas_get_port(phy_info);
2599 dfailprintk((MYIOC_s_ERR_FMT
2600 "%s: exit at line=%d\n", ioc->name,
2601 __FUNCTION__, __LINE__));
2605 starget = mptsas_get_starget(phy_info);
2607 vtarget = starget->hostdata;
2610 dfailprintk((MYIOC_s_ERR_FMT
2611 "%s: exit at line=%d\n", ioc->name,
2612 __FUNCTION__, __LINE__));
2617 * Handling RAID components
2619 if (ev->phys_disk_num_valid &&
2620 ev->hidden_raid_component) {
2621 printk(MYIOC_s_INFO_FMT
2622 "RAID Hidding: channel=%d, id=%d, "
2623 "physdsk %d \n", ioc->name, ev->channel,
2624 ev->id, ev->phys_disk_num);
2625 vtarget->id = ev->phys_disk_num;
2627 MPT_TARGET_FLAGS_RAID_COMPONENT;
2628 mptsas_reprobe_target(starget, 1);
2629 phy_info->attached.phys_disk_num =
2635 if (phy_info->attached.device_info &
2636 MPI_SAS_DEVICE_INFO_SSP_TARGET)
2638 if (phy_info->attached.device_info &
2639 MPI_SAS_DEVICE_INFO_STP_TARGET)
2641 if (phy_info->attached.device_info &
2642 MPI_SAS_DEVICE_INFO_SATA_DEVICE)
2645 printk(MYIOC_s_INFO_FMT
2646 "removing %s device, channel %d, id %d, phy %d\n",
2647 ioc->name, ds, ev->channel, ev->id, phy_info->phy_id);
2648 #ifdef MPT_DEBUG_SAS_WIDE
2649 dev_printk(KERN_DEBUG, &port->dev,
2650 "delete port (%d)\n", port->port_identifier);
2652 sas_port_delete(port);
2653 mptsas_port_delete(phy_info->port_details);
2655 case MPTSAS_ADD_DEVICE:
2657 if (ev->phys_disk_num_valid)
2658 mpt_findImVolumes(ioc);
2661 * Refresh sas device pg0 data
2663 if (mptsas_sas_device_pg0(ioc, &sas_device,
2664 (MPI_SAS_DEVICE_PGAD_FORM_BUS_TARGET_ID <<
2665 MPI_SAS_DEVICE_PGAD_FORM_SHIFT),
2666 (ev->channel << 8) + ev->id)) {
2667 dfailprintk((MYIOC_s_ERR_FMT
2668 "%s: exit at line=%d\n", ioc->name,
2669 __FUNCTION__, __LINE__));
2673 __mptsas_discovery_work(ioc);
2675 phy_info = mptsas_find_phyinfo_by_sas_address(ioc,
2676 sas_device.sas_address);
2678 if (!phy_info || !phy_info->port_details) {
2679 dfailprintk((MYIOC_s_ERR_FMT
2680 "%s: exit at line=%d\n", ioc->name,
2681 __FUNCTION__, __LINE__));
2685 starget = mptsas_get_starget(phy_info);
2686 if (starget && (!ev->hidden_raid_component)){
2688 vtarget = starget->hostdata;
2691 dfailprintk((MYIOC_s_ERR_FMT
2692 "%s: exit at line=%d\n", ioc->name,
2693 __FUNCTION__, __LINE__));
2697 * Handling RAID components
2699 if (vtarget->tflags & MPT_TARGET_FLAGS_RAID_COMPONENT) {
2700 printk(MYIOC_s_INFO_FMT
2701 "RAID Exposing: channel=%d, id=%d, "
2702 "physdsk %d \n", ioc->name, ev->channel,
2703 ev->id, ev->phys_disk_num);
2705 ~MPT_TARGET_FLAGS_RAID_COMPONENT;
2706 vtarget->id = ev->id;
2707 mptsas_reprobe_target(starget, 0);
2708 phy_info->attached.phys_disk_num = ~0;
2713 if (mptsas_get_rphy(phy_info)) {
2714 dfailprintk((MYIOC_s_ERR_FMT
2715 "%s: exit at line=%d\n", ioc->name,
2716 __FUNCTION__, __LINE__));
2717 if (ev->channel) printk("%d\n", __LINE__);
2721 port = mptsas_get_port(phy_info);
2723 dfailprintk((MYIOC_s_ERR_FMT
2724 "%s: exit at line=%d\n", ioc->name,
2725 __FUNCTION__, __LINE__));
2728 memcpy(&phy_info->attached, &sas_device,
2729 sizeof(struct mptsas_devinfo));
2731 if (phy_info->attached.device_info &
2732 MPI_SAS_DEVICE_INFO_SSP_TARGET)
2734 if (phy_info->attached.device_info &
2735 MPI_SAS_DEVICE_INFO_STP_TARGET)
2737 if (phy_info->attached.device_info &
2738 MPI_SAS_DEVICE_INFO_SATA_DEVICE)
2741 printk(MYIOC_s_INFO_FMT
2742 "attaching %s device, channel %d, id %d, phy %d\n",
2743 ioc->name, ds, ev->channel, ev->id, ev->phy_id);
2745 mptsas_parse_device_info(&identify, &phy_info->attached);
2746 rphy = sas_end_device_alloc(port);
2748 dfailprintk((MYIOC_s_ERR_FMT
2749 "%s: exit at line=%d\n", ioc->name,
2750 __FUNCTION__, __LINE__));
2751 break; /* non-fatal: an rphy can be added later */
2754 rphy->identify = identify;
2755 if (sas_rphy_add(rphy)) {
2756 dfailprintk((MYIOC_s_ERR_FMT
2757 "%s: exit at line=%d\n", ioc->name,
2758 __FUNCTION__, __LINE__));
2759 sas_rphy_free(rphy);
2762 mptsas_set_rphy(phy_info, rphy);
2764 case MPTSAS_ADD_RAID:
2765 sdev = scsi_device_lookup(ioc->sh, MPTSAS_RAID_CHANNEL,
2768 scsi_device_put(sdev);
2771 printk(MYIOC_s_INFO_FMT
2772 "attaching raid volume, channel %d, id %d\n",
2773 ioc->name, MPTSAS_RAID_CHANNEL, ev->id);
2774 scsi_add_device(ioc->sh, MPTSAS_RAID_CHANNEL, ev->id, 0);
2775 mpt_findImVolumes(ioc);
2777 case MPTSAS_DEL_RAID:
2778 sdev = scsi_device_lookup(ioc->sh, MPTSAS_RAID_CHANNEL,
2782 printk(MYIOC_s_INFO_FMT
2783 "removing raid volume, channel %d, id %d\n",
2784 ioc->name, MPTSAS_RAID_CHANNEL, ev->id);
2785 vdevice = sdev->hostdata;
2786 scsi_remove_device(sdev);
2787 scsi_device_put(sdev);
2788 mpt_findImVolumes(ioc);
2790 case MPTSAS_ADD_INACTIVE_VOLUME:
2791 mptsas_adding_inactive_raid_components(ioc,
2792 ev->channel, ev->id);
2794 case MPTSAS_IGNORE_EVENT:
2799 mutex_unlock(&ioc->sas_discovery_mutex);
2804 mptsas_send_sas_event(MPT_ADAPTER *ioc,
2805 EVENT_DATA_SAS_DEVICE_STATUS_CHANGE *sas_event_data)
2807 struct mptsas_hotplug_event *ev;
2808 u32 device_info = le32_to_cpu(sas_event_data->DeviceInfo);
2812 (MPI_SAS_DEVICE_INFO_SSP_TARGET |
2813 MPI_SAS_DEVICE_INFO_STP_TARGET |
2814 MPI_SAS_DEVICE_INFO_SATA_DEVICE )) == 0)
2817 switch (sas_event_data->ReasonCode) {
2818 case MPI_EVENT_SAS_DEV_STAT_RC_NOT_RESPONDING:
2820 mptsas_target_reset_queue(ioc, sas_event_data);
2823 case MPI_EVENT_SAS_DEV_STAT_RC_ADDED:
2824 ev = kzalloc(sizeof(*ev), GFP_ATOMIC);
2826 printk(KERN_WARNING "mptsas: lost hotplug event\n");
2830 INIT_WORK(&ev->work, mptsas_hotplug_work);
2832 ev->handle = le16_to_cpu(sas_event_data->DevHandle);
2834 le16_to_cpu(sas_event_data->ParentDevHandle);
2835 ev->channel = sas_event_data->Bus;
2836 ev->id = sas_event_data->TargetID;
2837 ev->phy_id = sas_event_data->PhyNum;
2838 memcpy(&sas_address, &sas_event_data->SASAddress,
2840 ev->sas_address = le64_to_cpu(sas_address);
2841 ev->device_info = device_info;
2843 if (sas_event_data->ReasonCode &
2844 MPI_EVENT_SAS_DEV_STAT_RC_ADDED)
2845 ev->event_type = MPTSAS_ADD_DEVICE;
2847 ev->event_type = MPTSAS_DEL_DEVICE;
2848 schedule_work(&ev->work);
2850 case MPI_EVENT_SAS_DEV_STAT_RC_NO_PERSIST_ADDED:
2852 * Persistent table is full.
2854 INIT_WORK(&ioc->sas_persist_task,
2855 mptsas_persist_clear_table);
2856 schedule_work(&ioc->sas_persist_task);
2859 * TODO, handle other events
2861 case MPI_EVENT_SAS_DEV_STAT_RC_SMART_DATA:
2862 case MPI_EVENT_SAS_DEV_STAT_RC_UNSUPPORTED:
2863 case MPI_EVENT_SAS_DEV_STAT_RC_INTERNAL_DEVICE_RESET:
2864 case MPI_EVENT_SAS_DEV_STAT_RC_TASK_ABORT_INTERNAL:
2865 case MPI_EVENT_SAS_DEV_STAT_RC_ABORT_TASK_SET_INTERNAL:
2866 case MPI_EVENT_SAS_DEV_STAT_RC_CLEAR_TASK_SET_INTERNAL:
2867 case MPI_EVENT_SAS_DEV_STAT_RC_QUERY_TASK_INTERNAL:
2873 mptsas_send_raid_event(MPT_ADAPTER *ioc,
2874 EVENT_DATA_RAID *raid_event_data)
2876 struct mptsas_hotplug_event *ev;
2877 int status = le32_to_cpu(raid_event_data->SettingsStatus);
2878 int state = (status >> 8) & 0xff;
2880 if (ioc->bus_type != SAS)
2883 ev = kzalloc(sizeof(*ev), GFP_ATOMIC);
2885 printk(KERN_WARNING "mptsas: lost hotplug event\n");
2889 INIT_WORK(&ev->work, mptsas_hotplug_work);
2891 ev->id = raid_event_data->VolumeID;
2892 ev->channel = raid_event_data->VolumeBus;
2893 ev->event_type = MPTSAS_IGNORE_EVENT;
2895 switch (raid_event_data->ReasonCode) {
2896 case MPI_EVENT_RAID_RC_PHYSDISK_DELETED:
2897 ev->phys_disk_num_valid = 1;
2898 ev->phys_disk_num = raid_event_data->PhysDiskNum;
2899 ev->event_type = MPTSAS_ADD_DEVICE;
2901 case MPI_EVENT_RAID_RC_PHYSDISK_CREATED:
2902 ev->phys_disk_num_valid = 1;
2903 ev->phys_disk_num = raid_event_data->PhysDiskNum;
2904 ev->hidden_raid_component = 1;
2905 ev->event_type = MPTSAS_DEL_DEVICE;
2907 case MPI_EVENT_RAID_RC_PHYSDISK_STATUS_CHANGED:
2909 case MPI_PD_STATE_ONLINE:
2910 case MPI_PD_STATE_NOT_COMPATIBLE:
2911 ev->phys_disk_num_valid = 1;
2912 ev->phys_disk_num = raid_event_data->PhysDiskNum;
2913 ev->hidden_raid_component = 1;
2914 ev->event_type = MPTSAS_ADD_DEVICE;
2916 case MPI_PD_STATE_MISSING:
2917 case MPI_PD_STATE_OFFLINE_AT_HOST_REQUEST:
2918 case MPI_PD_STATE_FAILED_AT_HOST_REQUEST:
2919 case MPI_PD_STATE_OFFLINE_FOR_ANOTHER_REASON:
2920 ev->phys_disk_num_valid = 1;
2921 ev->phys_disk_num = raid_event_data->PhysDiskNum;
2922 ev->event_type = MPTSAS_DEL_DEVICE;
2928 case MPI_EVENT_RAID_RC_VOLUME_DELETED:
2929 ev->event_type = MPTSAS_DEL_RAID;
2931 case MPI_EVENT_RAID_RC_VOLUME_CREATED:
2932 ev->event_type = MPTSAS_ADD_RAID;
2934 case MPI_EVENT_RAID_RC_VOLUME_STATUS_CHANGED:
2936 case MPI_RAIDVOL0_STATUS_STATE_FAILED:
2937 case MPI_RAIDVOL0_STATUS_STATE_MISSING:
2938 ev->event_type = MPTSAS_DEL_RAID;
2940 case MPI_RAIDVOL0_STATUS_STATE_OPTIMAL:
2941 case MPI_RAIDVOL0_STATUS_STATE_DEGRADED:
2942 ev->event_type = MPTSAS_ADD_RAID;
2951 schedule_work(&ev->work);
2955 mptsas_send_discovery_event(MPT_ADAPTER *ioc,
2956 EVENT_DATA_SAS_DISCOVERY *discovery_data)
2958 struct mptsas_discovery_event *ev;
2963 * This flag will be non-zero when firmware
2964 * kicks off discovery, and return to zero
2965 * once its completed.
2967 if (discovery_data->DiscoveryStatus)
2970 ev = kzalloc(sizeof(*ev), GFP_ATOMIC);
2973 INIT_WORK(&ev->work, mptsas_discovery_work);
2975 schedule_work(&ev->work);
2979 * mptsas_send_ir2_event - handle exposing hidden disk when
2980 * an inactive raid volume is added
2982 * @ioc: Pointer to MPT_ADAPTER structure
2987 mptsas_send_ir2_event(MPT_ADAPTER *ioc, PTR_MPI_EVENT_DATA_IR2 ir2_data)
2989 struct mptsas_hotplug_event *ev;
2991 if (ir2_data->ReasonCode !=
2992 MPI_EVENT_IR2_RC_FOREIGN_CFG_DETECTED)
2995 ev = kzalloc(sizeof(*ev), GFP_ATOMIC);
2999 INIT_WORK(&ev->work, mptsas_hotplug_work);
3001 ev->id = ir2_data->TargetID;
3002 ev->channel = ir2_data->Bus;
3003 ev->event_type = MPTSAS_ADD_INACTIVE_VOLUME;
3005 schedule_work(&ev->work);
3009 mptsas_event_process(MPT_ADAPTER *ioc, EventNotificationReply_t *reply)
3012 u8 event = le32_to_cpu(reply->Event) & 0xFF;
3018 * sas_discovery_ignore_events
3020 * This flag is to prevent anymore processing of
3021 * sas events once mptsas_remove function is called.
3023 if (ioc->sas_discovery_ignore_events) {
3024 rc = mptscsih_event_process(ioc, reply);
3029 case MPI_EVENT_SAS_DEVICE_STATUS_CHANGE:
3030 mptsas_send_sas_event(ioc,
3031 (EVENT_DATA_SAS_DEVICE_STATUS_CHANGE *)reply->Data);
3033 case MPI_EVENT_INTEGRATED_RAID:
3034 mptsas_send_raid_event(ioc,
3035 (EVENT_DATA_RAID *)reply->Data);
3037 case MPI_EVENT_PERSISTENT_TABLE_FULL:
3038 INIT_WORK(&ioc->sas_persist_task,
3039 mptsas_persist_clear_table);
3040 schedule_work(&ioc->sas_persist_task);
3042 case MPI_EVENT_SAS_DISCOVERY:
3043 mptsas_send_discovery_event(ioc,
3044 (EVENT_DATA_SAS_DISCOVERY *)reply->Data);
3047 mptsas_send_ir2_event(ioc,
3048 (PTR_MPI_EVENT_DATA_IR2)reply->Data);
3051 rc = mptscsih_event_process(ioc, reply);
3060 mptsas_probe(struct pci_dev *pdev, const struct pci_device_id *id)
3062 struct Scsi_Host *sh;
3065 unsigned long flags;
3073 r = mpt_attach(pdev,id);
3077 ioc = pci_get_drvdata(pdev);
3078 ioc->DoneCtx = mptsasDoneCtx;
3079 ioc->TaskCtx = mptsasTaskCtx;
3080 ioc->InternalCtx = mptsasInternalCtx;
3082 /* Added sanity check on readiness of the MPT adapter.
3084 if (ioc->last_state != MPI_IOC_STATE_OPERATIONAL) {
3085 printk(MYIOC_s_WARN_FMT
3086 "Skipping because it's not operational!\n",
3089 goto out_mptsas_probe;
3093 printk(MYIOC_s_WARN_FMT "Skipping because it's disabled!\n",
3096 goto out_mptsas_probe;
3099 /* Sanity check - ensure at least 1 port is INITIATOR capable
3102 for (ii = 0; ii < ioc->facts.NumberOfPorts; ii++) {
3103 if (ioc->pfacts[ii].ProtocolFlags &
3104 MPI_PORTFACTS_PROTOCOL_INITIATOR)
3109 printk(MYIOC_s_WARN_FMT
3110 "Skipping ioc=%p because SCSI Initiator mode "
3111 "is NOT enabled!\n", ioc->name, ioc);
3115 sh = scsi_host_alloc(&mptsas_driver_template, sizeof(MPT_SCSI_HOST));
3117 printk(MYIOC_s_WARN_FMT
3118 "Unable to register controller with SCSI subsystem\n",
3121 goto out_mptsas_probe;
3124 spin_lock_irqsave(&ioc->FreeQlock, flags);
3126 /* Attach the SCSI Host to the IOC structure
3134 /* set 16 byte cdb's */
3135 sh->max_cmd_len = 16;
3137 sh->max_id = ioc->pfacts[0].PortSCSIID;
3138 sh->max_lun = max_lun;
3140 sh->transportt = mptsas_transport_template;
3142 sh->this_id = ioc->pfacts[0].PortSCSIID;
3146 sh->unique_id = ioc->id;
3148 INIT_LIST_HEAD(&ioc->sas_topology);
3149 mutex_init(&ioc->sas_topology_mutex);
3150 mutex_init(&ioc->sas_discovery_mutex);
3151 mutex_init(&ioc->sas_mgmt.mutex);
3152 init_completion(&ioc->sas_mgmt.done);
3154 /* Verify that we won't exceed the maximum
3155 * number of chain buffers
3156 * We can optimize: ZZ = req_sz/sizeof(SGE)
3158 * numSGE = 1 + (ZZ-1)*(maxChain -1) + ZZ
3159 * + (req_sz - 64)/sizeof(SGE)
3160 * A slightly different algorithm is required for
3163 scale = ioc->req_sz/(sizeof(dma_addr_t) + sizeof(u32));
3164 if (sizeof(dma_addr_t) == sizeof(u64)) {
3165 numSGE = (scale - 1) *
3166 (ioc->facts.MaxChainDepth-1) + scale +
3167 (ioc->req_sz - 60) / (sizeof(dma_addr_t) +
3170 numSGE = 1 + (scale - 1) *
3171 (ioc->facts.MaxChainDepth-1) + scale +
3172 (ioc->req_sz - 64) / (sizeof(dma_addr_t) +
3176 if (numSGE < sh->sg_tablesize) {
3177 /* Reset this value */
3178 dprintk((MYIOC_s_INFO_FMT
3179 "Resetting sg_tablesize to %d from %d\n",
3180 ioc->name, numSGE, sh->sg_tablesize));
3181 sh->sg_tablesize = numSGE;
3184 hd = (MPT_SCSI_HOST *) sh->hostdata;
3187 /* SCSI needs scsi_cmnd lookup table!
3188 * (with size equal to req_depth*PtrSz!)
3190 hd->ScsiLookup = kcalloc(ioc->req_depth, sizeof(void *), GFP_ATOMIC);
3191 if (!hd->ScsiLookup) {
3193 goto out_mptsas_probe;
3196 dprintk((MYIOC_s_INFO_FMT "ScsiLookup @ %p\n",
3197 ioc->name, hd->ScsiLookup));
3199 /* Clear the TM flags
3202 hd->tmState = TM_STATE_NONE;
3203 hd->resetPending = 0;
3204 hd->abortSCpnt = NULL;
3206 /* Clear the pointer used to store
3207 * single-threaded commands, i.e., those
3208 * issued during a bus scan, dv and
3209 * configuration pages.
3213 /* Initialize this SCSI Hosts' timers
3214 * To use, set the timer expires field
3217 init_timer(&hd->timer);
3218 hd->timer.data = (unsigned long) hd;
3219 hd->timer.function = mptscsih_timer_expired;
3221 ioc->sas_data.ptClear = mpt_pt_clear;
3223 init_waitqueue_head(&hd->scandv_waitq);
3224 hd->scandv_wait_done = 0;
3225 hd->last_queue_full = 0;
3226 INIT_LIST_HEAD(&hd->target_reset_list);
3227 spin_unlock_irqrestore(&ioc->FreeQlock, flags);
3229 if (ioc->sas_data.ptClear==1) {
3230 mptbase_sas_persist_operation(
3231 ioc, MPI_SAS_OP_CLEAR_ALL_PERSISTENT);
3234 error = scsi_add_host(sh, &ioc->pcidev->dev);
3236 dprintk((KERN_ERR MYNAM
3237 "scsi_add_host failed\n"));
3238 goto out_mptsas_probe;
3241 mptsas_scan_sas_topology(ioc);
3247 mptscsih_remove(pdev);
3251 static void __devexit mptsas_remove(struct pci_dev *pdev)
3253 MPT_ADAPTER *ioc = pci_get_drvdata(pdev);
3254 struct mptsas_portinfo *p, *n;
3257 ioc->sas_discovery_ignore_events = 1;
3258 sas_remove_host(ioc->sh);
3260 mutex_lock(&ioc->sas_topology_mutex);
3261 list_for_each_entry_safe(p, n, &ioc->sas_topology, list) {
3263 for (i = 0 ; i < p->num_phys ; i++)
3264 mptsas_port_delete(p->phy_info[i].port_details);
3268 mutex_unlock(&ioc->sas_topology_mutex);
3270 mptscsih_remove(pdev);
3273 static struct pci_device_id mptsas_pci_table[] = {
3274 { PCI_VENDOR_ID_LSI_LOGIC, MPI_MANUFACTPAGE_DEVID_SAS1064,
3275 PCI_ANY_ID, PCI_ANY_ID },
3276 { PCI_VENDOR_ID_LSI_LOGIC, MPI_MANUFACTPAGE_DEVID_SAS1068,
3277 PCI_ANY_ID, PCI_ANY_ID },
3278 { PCI_VENDOR_ID_LSI_LOGIC, MPI_MANUFACTPAGE_DEVID_SAS1064E,
3279 PCI_ANY_ID, PCI_ANY_ID },
3280 { PCI_VENDOR_ID_LSI_LOGIC, MPI_MANUFACTPAGE_DEVID_SAS1068E,
3281 PCI_ANY_ID, PCI_ANY_ID },
3282 { PCI_VENDOR_ID_LSI_LOGIC, MPI_MANUFACTPAGE_DEVID_SAS1078,
3283 PCI_ANY_ID, PCI_ANY_ID },
3284 {0} /* Terminating entry */
3286 MODULE_DEVICE_TABLE(pci, mptsas_pci_table);
3289 static struct pci_driver mptsas_driver = {
3291 .id_table = mptsas_pci_table,
3292 .probe = mptsas_probe,
3293 .remove = __devexit_p(mptsas_remove),
3294 .shutdown = mptscsih_shutdown,
3296 .suspend = mptscsih_suspend,
3297 .resume = mptscsih_resume,
3306 show_mptmod_ver(my_NAME, my_VERSION);
3308 mptsas_transport_template =
3309 sas_attach_transport(&mptsas_transport_functions);
3310 if (!mptsas_transport_template)
3313 mptsasDoneCtx = mpt_register(mptscsih_io_done, MPTSAS_DRIVER);
3314 mptsasTaskCtx = mpt_register(mptsas_taskmgmt_complete, MPTSAS_DRIVER);
3316 mpt_register(mptscsih_scandv_complete, MPTSAS_DRIVER);
3317 mptsasMgmtCtx = mpt_register(mptsas_mgmt_done, MPTSAS_DRIVER);
3319 if (mpt_event_register(mptsasDoneCtx, mptsas_event_process) == 0) {
3320 devtverboseprintk((KERN_INFO MYNAM
3321 ": Registered for IOC event notifications\n"));
3324 if (mpt_reset_register(mptsasDoneCtx, mptsas_ioc_reset) == 0) {
3325 dprintk((KERN_INFO MYNAM
3326 ": Registered for IOC reset notifications\n"));
3329 error = pci_register_driver(&mptsas_driver);
3331 sas_release_transport(mptsas_transport_template);
3339 pci_unregister_driver(&mptsas_driver);
3340 sas_release_transport(mptsas_transport_template);
3342 mpt_reset_deregister(mptsasDoneCtx);
3343 mpt_event_deregister(mptsasDoneCtx);
3345 mpt_deregister(mptsasMgmtCtx);
3346 mpt_deregister(mptsasInternalCtx);
3347 mpt_deregister(mptsasTaskCtx);
3348 mpt_deregister(mptsasDoneCtx);
3351 module_init(mptsas_init);
3352 module_exit(mptsas_exit);