root/drivers/message/fusion/mptbase.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. pci_disable_io_access
  2. pci_enable_io_access
  3. mpt_set_debug_level
  4. mpt_get_cb_idx
  5. mpt_is_discovery_complete
  6. mpt_remove_dead_ioc_func
  7. mpt_fault_reset_work
  8. mpt_turbo_reply
  9. mpt_reply
  10. mpt_interrupt
  11. mptbase_reply
  12. mpt_register
  13. mpt_deregister
  14. mpt_event_register
  15. mpt_event_deregister
  16. mpt_reset_register
  17. mpt_reset_deregister
  18. mpt_device_driver_register
  19. mpt_device_driver_deregister
  20. mpt_get_msg_frame
  21. mpt_put_msg_frame
  22. mpt_put_msg_frame_hi_pri
  23. mpt_free_msg_frame
  24. mpt_add_sge
  25. mpt_add_sge_64bit
  26. mpt_add_sge_64bit_1078
  27. mpt_add_chain
  28. mpt_add_chain_64bit
  29. mpt_send_handshake_request
  30. mpt_host_page_access_control
  31. mpt_host_page_alloc
  32. mpt_verify_adapter
  33. mpt_get_product_name
  34. mpt_mapresources
  35. mpt_attach
  36. mpt_detach
  37. mpt_suspend
  38. mpt_resume
  39. mpt_signal_reset
  40. mpt_do_ioc_recovery
  41. mpt_detect_bound_ports
  42. mpt_adapter_disable
  43. mpt_adapter_dispose
  44. MptDisplayIocCapabilities
  45. MakeIocReady
  46. mpt_GetIocState
  47. GetIocFacts
  48. GetPortFacts
  49. SendIocInit
  50. SendPortEnable
  51. mpt_alloc_fw_memory
  52. mpt_free_fw_memory
  53. mpt_do_upload
  54. mpt_downloadboot
  55. KickStart
  56. mpt_diag_reset
  57. SendIocReset
  58. initChainBuffers
  59. PrimeIocFifos
  60. mpt_handshake_req_reply_wait
  61. WaitForDoorbellAck
  62. WaitForDoorbellInt
  63. WaitForDoorbellReply
  64. GetLanConfigPages
  65. mptbase_sas_persist_operation
  66. mptbase_raid_process_event_data
  67. GetIoUnitPage2
  68. mpt_GetScsiPortSettings
  69. mpt_readScsiDevicePageHeaders
  70. mpt_inactive_raid_list_free
  71. mpt_inactive_raid_volumes
  72. mpt_raid_phys_disk_pg0
  73. mpt_raid_phys_disk_get_num_paths
  74. mpt_raid_phys_disk_pg1
  75. mpt_findImVolumes
  76. mpt_read_ioc_pg_3
  77. mpt_read_ioc_pg_4
  78. mpt_read_ioc_pg_1
  79. mpt_get_manufacturing_pg_0
  80. SendEventNotification
  81. SendEventAck
  82. mpt_config
  83. mpt_ioc_reset
  84. procmpt_create
  85. procmpt_destroy
  86. mpt_summary_proc_show
  87. mpt_version_proc_show
  88. mpt_iocinfo_proc_show
  89. mpt_get_fw_exp_ver
  90. mpt_print_ioc_summary
  91. seq_mpt_print_ioc_summary
  92. mpt_set_taskmgmt_in_progress_flag
  93. mpt_clear_taskmgmt_in_progress_flag
  94. mpt_halt_firmware
  95. mpt_SoftResetHandler
  96. mpt_Soft_Hard_ResetHandler
  97. mpt_HardResetHandler
  98. mpt_display_event_info
  99. ProcessEventNotification
  100. mpt_fc_log_info
  101. mpt_spi_log_info
  102. mpt_sas_log_info
  103. mpt_iocstatus_info_config
  104. mpt_iocstatus_info
  105. fusion_init
  106. fusion_exit

   1 /*
   2  *  linux/drivers/message/fusion/mptbase.c
   3  *      This is the Fusion MPT base driver which supports multiple
   4  *      (SCSI + LAN) specialized protocol drivers.
   5  *      For use with LSI PCI chip/adapter(s)
   6  *      running LSI Fusion MPT (Message Passing Technology) firmware.
   7  *
   8  *  Copyright (c) 1999-2008 LSI Corporation
   9  *  (mailto:DL-MPTFusionLinux@lsi.com)
  10  *
  11  */
  12 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
  13 /*
  14     This program is free software; you can redistribute it and/or modify
  15     it under the terms of the GNU General Public License as published by
  16     the Free Software Foundation; version 2 of the License.
  17 
  18     This program is distributed in the hope that it will be useful,
  19     but WITHOUT ANY WARRANTY; without even the implied warranty of
  20     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  21     GNU General Public License for more details.
  22 
  23     NO WARRANTY
  24     THE PROGRAM IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OR
  25     CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED INCLUDING, WITHOUT
  26     LIMITATION, ANY WARRANTIES OR CONDITIONS OF TITLE, NON-INFRINGEMENT,
  27     MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. Each Recipient is
  28     solely responsible for determining the appropriateness of using and
  29     distributing the Program and assumes all risks associated with its
  30     exercise of rights under this Agreement, including but not limited to
  31     the risks and costs of program errors, damage to or loss of data,
  32     programs or equipment, and unavailability or interruption of operations.
  33 
  34     DISCLAIMER OF LIABILITY
  35     NEITHER RECIPIENT NOR ANY CONTRIBUTORS SHALL HAVE ANY LIABILITY FOR ANY
  36     DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  37     DAMAGES (INCLUDING WITHOUT LIMITATION LOST PROFITS), HOWEVER CAUSED AND
  38     ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
  39     TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
  40     USE OR DISTRIBUTION OF THE PROGRAM OR THE EXERCISE OF ANY RIGHTS GRANTED
  41     HEREUNDER, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGES
  42 
  43     You should have received a copy of the GNU General Public License
  44     along with this program; if not, write to the Free Software
  45     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  46 */
  47 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
  48 
  49 #include <linux/kernel.h>
  50 #include <linux/module.h>
  51 #include <linux/errno.h>
  52 #include <linux/init.h>
  53 #include <linux/seq_file.h>
  54 #include <linux/slab.h>
  55 #include <linux/types.h>
  56 #include <linux/pci.h>
  57 #include <linux/kdev_t.h>
  58 #include <linux/blkdev.h>
  59 #include <linux/delay.h>
  60 #include <linux/interrupt.h>            /* needed for in_interrupt() proto */
  61 #include <linux/dma-mapping.h>
  62 #include <linux/kthread.h>
  63 #include <scsi/scsi_host.h>
  64 
  65 #include "mptbase.h"
  66 #include "lsi/mpi_log_fc.h"
  67 
  68 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
  69 #define my_NAME         "Fusion MPT base driver"
  70 #define my_VERSION      MPT_LINUX_VERSION_COMMON
  71 #define MYNAM           "mptbase"
  72 
  73 MODULE_AUTHOR(MODULEAUTHOR);
  74 MODULE_DESCRIPTION(my_NAME);
  75 MODULE_LICENSE("GPL");
  76 MODULE_VERSION(my_VERSION);
  77 
  78 /*
  79  *  cmd line parameters
  80  */
  81 
  82 static int mpt_msi_enable_spi;
  83 module_param(mpt_msi_enable_spi, int, 0);
  84 MODULE_PARM_DESC(mpt_msi_enable_spi,
  85                  " Enable MSI Support for SPI controllers (default=0)");
  86 
  87 static int mpt_msi_enable_fc;
  88 module_param(mpt_msi_enable_fc, int, 0);
  89 MODULE_PARM_DESC(mpt_msi_enable_fc,
  90                  " Enable MSI Support for FC controllers (default=0)");
  91 
  92 static int mpt_msi_enable_sas;
  93 module_param(mpt_msi_enable_sas, int, 0);
  94 MODULE_PARM_DESC(mpt_msi_enable_sas,
  95                  " Enable MSI Support for SAS controllers (default=0)");
  96 
  97 static int mpt_channel_mapping;
  98 module_param(mpt_channel_mapping, int, 0);
  99 MODULE_PARM_DESC(mpt_channel_mapping, " Mapping id's to channels (default=0)");
 100 
 101 static int mpt_debug_level;
 102 static int mpt_set_debug_level(const char *val, const struct kernel_param *kp);
 103 module_param_call(mpt_debug_level, mpt_set_debug_level, param_get_int,
 104                   &mpt_debug_level, 0600);
 105 MODULE_PARM_DESC(mpt_debug_level,
 106                  " debug level - refer to mptdebug.h - (default=0)");
 107 
 108 int mpt_fwfault_debug;
 109 EXPORT_SYMBOL(mpt_fwfault_debug);
 110 module_param(mpt_fwfault_debug, int, 0600);
 111 MODULE_PARM_DESC(mpt_fwfault_debug,
 112                  "Enable detection of Firmware fault and halt Firmware on fault - (default=0)");
 113 
 114 static char     MptCallbacksName[MPT_MAX_PROTOCOL_DRIVERS]
 115                                 [MPT_MAX_CALLBACKNAME_LEN+1];
 116 
 117 #ifdef MFCNT
 118 static int mfcounter = 0;
 119 #define PRINT_MF_COUNT 20000
 120 #endif
 121 
 122 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 123 /*
 124  *  Public data...
 125  */
 126 
 127 #define WHOINIT_UNKNOWN         0xAA
 128 
 129 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 130 /*
 131  *  Private data...
 132  */
 133                                         /* Adapter link list */
 134 LIST_HEAD(ioc_list);
 135                                         /* Callback lookup table */
 136 static MPT_CALLBACK              MptCallbacks[MPT_MAX_PROTOCOL_DRIVERS];
 137                                         /* Protocol driver class lookup table */
 138 static int                       MptDriverClass[MPT_MAX_PROTOCOL_DRIVERS];
 139                                         /* Event handler lookup table */
 140 static MPT_EVHANDLER             MptEvHandlers[MPT_MAX_PROTOCOL_DRIVERS];
 141                                         /* Reset handler lookup table */
 142 static MPT_RESETHANDLER          MptResetHandlers[MPT_MAX_PROTOCOL_DRIVERS];
 143 static struct mpt_pci_driver    *MptDeviceDriverHandlers[MPT_MAX_PROTOCOL_DRIVERS];
 144 
 145 #ifdef CONFIG_PROC_FS
 146 static struct proc_dir_entry    *mpt_proc_root_dir;
 147 #endif
 148 
 149 /*
 150  *  Driver Callback Index's
 151  */
 152 static u8 mpt_base_index = MPT_MAX_PROTOCOL_DRIVERS;
 153 static u8 last_drv_idx;
 154 
 155 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 156 /*
 157  *  Forward protos...
 158  */
 159 static irqreturn_t mpt_interrupt(int irq, void *bus_id);
 160 static int      mptbase_reply(MPT_ADAPTER *ioc, MPT_FRAME_HDR *req,
 161                 MPT_FRAME_HDR *reply);
 162 static int      mpt_handshake_req_reply_wait(MPT_ADAPTER *ioc, int reqBytes,
 163                         u32 *req, int replyBytes, u16 *u16reply, int maxwait,
 164                         int sleepFlag);
 165 static int      mpt_do_ioc_recovery(MPT_ADAPTER *ioc, u32 reason, int sleepFlag);
 166 static void     mpt_detect_bound_ports(MPT_ADAPTER *ioc, struct pci_dev *pdev);
 167 static void     mpt_adapter_disable(MPT_ADAPTER *ioc);
 168 static void     mpt_adapter_dispose(MPT_ADAPTER *ioc);
 169 
 170 static void     MptDisplayIocCapabilities(MPT_ADAPTER *ioc);
 171 static int      MakeIocReady(MPT_ADAPTER *ioc, int force, int sleepFlag);
 172 static int      GetIocFacts(MPT_ADAPTER *ioc, int sleepFlag, int reason);
 173 static int      GetPortFacts(MPT_ADAPTER *ioc, int portnum, int sleepFlag);
 174 static int      SendIocInit(MPT_ADAPTER *ioc, int sleepFlag);
 175 static int      SendPortEnable(MPT_ADAPTER *ioc, int portnum, int sleepFlag);
 176 static int      mpt_do_upload(MPT_ADAPTER *ioc, int sleepFlag);
 177 static int      mpt_downloadboot(MPT_ADAPTER *ioc, MpiFwHeader_t *pFwHeader, int sleepFlag);
 178 static int      mpt_diag_reset(MPT_ADAPTER *ioc, int ignore, int sleepFlag);
 179 static int      KickStart(MPT_ADAPTER *ioc, int ignore, int sleepFlag);
 180 static int      SendIocReset(MPT_ADAPTER *ioc, u8 reset_type, int sleepFlag);
 181 static int      PrimeIocFifos(MPT_ADAPTER *ioc);
 182 static int      WaitForDoorbellAck(MPT_ADAPTER *ioc, int howlong, int sleepFlag);
 183 static int      WaitForDoorbellInt(MPT_ADAPTER *ioc, int howlong, int sleepFlag);
 184 static int      WaitForDoorbellReply(MPT_ADAPTER *ioc, int howlong, int sleepFlag);
 185 static int      GetLanConfigPages(MPT_ADAPTER *ioc);
 186 static int      GetIoUnitPage2(MPT_ADAPTER *ioc);
 187 int             mptbase_sas_persist_operation(MPT_ADAPTER *ioc, u8 persist_opcode);
 188 static int      mpt_GetScsiPortSettings(MPT_ADAPTER *ioc, int portnum);
 189 static int      mpt_readScsiDevicePageHeaders(MPT_ADAPTER *ioc, int portnum);
 190 static void     mpt_read_ioc_pg_1(MPT_ADAPTER *ioc);
 191 static void     mpt_read_ioc_pg_4(MPT_ADAPTER *ioc);
 192 static void     mpt_get_manufacturing_pg_0(MPT_ADAPTER *ioc);
 193 static int      SendEventNotification(MPT_ADAPTER *ioc, u8 EvSwitch,
 194         int sleepFlag);
 195 static int      SendEventAck(MPT_ADAPTER *ioc, EventNotificationReply_t *evnp);
 196 static int      mpt_host_page_access_control(MPT_ADAPTER *ioc, u8 access_control_value, int sleepFlag);
 197 static int      mpt_host_page_alloc(MPT_ADAPTER *ioc, pIOCInit_t ioc_init);
 198 
 199 #ifdef CONFIG_PROC_FS
 200 static int mpt_summary_proc_show(struct seq_file *m, void *v);
 201 static int mpt_version_proc_show(struct seq_file *m, void *v);
 202 static int mpt_iocinfo_proc_show(struct seq_file *m, void *v);
 203 #endif
 204 static void     mpt_get_fw_exp_ver(char *buf, MPT_ADAPTER *ioc);
 205 
 206 static int      ProcessEventNotification(MPT_ADAPTER *ioc,
 207                 EventNotificationReply_t *evReply, int *evHandlers);
 208 static void     mpt_iocstatus_info(MPT_ADAPTER *ioc, u32 ioc_status, MPT_FRAME_HDR *mf);
 209 static void     mpt_fc_log_info(MPT_ADAPTER *ioc, u32 log_info);
 210 static void     mpt_spi_log_info(MPT_ADAPTER *ioc, u32 log_info);
 211 static void     mpt_sas_log_info(MPT_ADAPTER *ioc, u32 log_info , u8 cb_idx);
 212 static int      mpt_read_ioc_pg_3(MPT_ADAPTER *ioc);
 213 static void     mpt_inactive_raid_list_free(MPT_ADAPTER *ioc);
 214 
 215 /* module entry point */
 216 static int  __init    fusion_init  (void);
 217 static void __exit    fusion_exit  (void);
 218 
 219 #define CHIPREG_READ32(addr)            readl_relaxed(addr)
 220 #define CHIPREG_READ32_dmasync(addr)    readl(addr)
 221 #define CHIPREG_WRITE32(addr,val)       writel(val, addr)
 222 #define CHIPREG_PIO_WRITE32(addr,val)   outl(val, (unsigned long)addr)
 223 #define CHIPREG_PIO_READ32(addr)        inl((unsigned long)addr)
 224 
 225 static void
 226 pci_disable_io_access(struct pci_dev *pdev)
 227 {
 228         u16 command_reg;
 229 
 230         pci_read_config_word(pdev, PCI_COMMAND, &command_reg);
 231         command_reg &= ~1;
 232         pci_write_config_word(pdev, PCI_COMMAND, command_reg);
 233 }
 234 
 235 static void
 236 pci_enable_io_access(struct pci_dev *pdev)
 237 {
 238         u16 command_reg;
 239 
 240         pci_read_config_word(pdev, PCI_COMMAND, &command_reg);
 241         command_reg |= 1;
 242         pci_write_config_word(pdev, PCI_COMMAND, command_reg);
 243 }
 244 
 245 static int mpt_set_debug_level(const char *val, const struct kernel_param *kp)
 246 {
 247         int ret = param_set_int(val, kp);
 248         MPT_ADAPTER *ioc;
 249 
 250         if (ret)
 251                 return ret;
 252 
 253         list_for_each_entry(ioc, &ioc_list, list)
 254                 ioc->debug_level = mpt_debug_level;
 255         return 0;
 256 }
 257 
 258 /**
 259  *      mpt_get_cb_idx - obtain cb_idx for registered driver
 260  *      @dclass: class driver enum
 261  *
 262  *      Returns cb_idx, or zero means it wasn't found
 263  **/
 264 static u8
 265 mpt_get_cb_idx(MPT_DRIVER_CLASS dclass)
 266 {
 267         u8 cb_idx;
 268 
 269         for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--)
 270                 if (MptDriverClass[cb_idx] == dclass)
 271                         return cb_idx;
 272         return 0;
 273 }
 274 
 275 /**
 276  * mpt_is_discovery_complete - determine if discovery has completed
 277  * @ioc: per adatper instance
 278  *
 279  * Returns 1 when discovery completed, else zero.
 280  */
 281 static int
 282 mpt_is_discovery_complete(MPT_ADAPTER *ioc)
 283 {
 284         ConfigExtendedPageHeader_t hdr;
 285         CONFIGPARMS cfg;
 286         SasIOUnitPage0_t *buffer;
 287         dma_addr_t dma_handle;
 288         int rc = 0;
 289 
 290         memset(&hdr, 0, sizeof(ConfigExtendedPageHeader_t));
 291         memset(&cfg, 0, sizeof(CONFIGPARMS));
 292         hdr.PageVersion = MPI_SASIOUNITPAGE0_PAGEVERSION;
 293         hdr.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
 294         hdr.ExtPageType = MPI_CONFIG_EXTPAGETYPE_SAS_IO_UNIT;
 295         cfg.cfghdr.ehdr = &hdr;
 296         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
 297 
 298         if ((mpt_config(ioc, &cfg)))
 299                 goto out;
 300         if (!hdr.ExtPageLength)
 301                 goto out;
 302 
 303         buffer = pci_alloc_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
 304             &dma_handle);
 305         if (!buffer)
 306                 goto out;
 307 
 308         cfg.physAddr = dma_handle;
 309         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
 310 
 311         if ((mpt_config(ioc, &cfg)))
 312                 goto out_free_consistent;
 313 
 314         if (!(buffer->PhyData[0].PortFlags &
 315             MPI_SAS_IOUNIT0_PORT_FLAGS_DISCOVERY_IN_PROGRESS))
 316                 rc = 1;
 317 
 318  out_free_consistent:
 319         pci_free_consistent(ioc->pcidev, hdr.ExtPageLength * 4,
 320             buffer, dma_handle);
 321  out:
 322         return rc;
 323 }
 324 
 325 
 326 /**
 327  *  mpt_remove_dead_ioc_func - kthread context to remove dead ioc
 328  * @arg: input argument, used to derive ioc
 329  *
 330  * Return 0 if controller is removed from pci subsystem.
 331  * Return -1 for other case.
 332  */
 333 static int mpt_remove_dead_ioc_func(void *arg)
 334 {
 335         MPT_ADAPTER *ioc = (MPT_ADAPTER *)arg;
 336         struct pci_dev *pdev;
 337 
 338         if (!ioc)
 339                 return -1;
 340 
 341         pdev = ioc->pcidev;
 342         if (!pdev)
 343                 return -1;
 344 
 345         pci_stop_and_remove_bus_device_locked(pdev);
 346         return 0;
 347 }
 348 
 349 
 350 
 351 /**
 352  *      mpt_fault_reset_work - work performed on workq after ioc fault
 353  *      @work: input argument, used to derive ioc
 354  *
 355 **/
 356 static void
 357 mpt_fault_reset_work(struct work_struct *work)
 358 {
 359         MPT_ADAPTER     *ioc =
 360             container_of(work, MPT_ADAPTER, fault_reset_work.work);
 361         u32              ioc_raw_state;
 362         int              rc;
 363         unsigned long    flags;
 364         MPT_SCSI_HOST   *hd;
 365         struct task_struct *p;
 366 
 367         if (ioc->ioc_reset_in_progress || !ioc->active)
 368                 goto out;
 369 
 370 
 371         ioc_raw_state = mpt_GetIocState(ioc, 0);
 372         if ((ioc_raw_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_MASK) {
 373                 printk(MYIOC_s_INFO_FMT "%s: IOC is non-operational !!!!\n",
 374                     ioc->name, __func__);
 375 
 376                 /*
 377                  * Call mptscsih_flush_pending_cmds callback so that we
 378                  * flush all pending commands back to OS.
 379                  * This call is required to aovid deadlock at block layer.
 380                  * Dead IOC will fail to do diag reset,and this call is safe
 381                  * since dead ioc will never return any command back from HW.
 382                  */
 383                 hd = shost_priv(ioc->sh);
 384                 ioc->schedule_dead_ioc_flush_running_cmds(hd);
 385 
 386                 /*Remove the Dead Host */
 387                 p = kthread_run(mpt_remove_dead_ioc_func, ioc,
 388                                 "mpt_dead_ioc_%d", ioc->id);
 389                 if (IS_ERR(p))  {
 390                         printk(MYIOC_s_ERR_FMT
 391                                 "%s: Running mpt_dead_ioc thread failed !\n",
 392                                 ioc->name, __func__);
 393                 } else {
 394                         printk(MYIOC_s_WARN_FMT
 395                                 "%s: Running mpt_dead_ioc thread success !\n",
 396                                 ioc->name, __func__);
 397                 }
 398                 return; /* don't rearm timer */
 399         }
 400 
 401         if ((ioc_raw_state & MPI_IOC_STATE_MASK)
 402                         == MPI_IOC_STATE_FAULT) {
 403                 printk(MYIOC_s_WARN_FMT "IOC is in FAULT state (%04xh)!!!\n",
 404                        ioc->name, ioc_raw_state & MPI_DOORBELL_DATA_MASK);
 405                 printk(MYIOC_s_WARN_FMT "Issuing HardReset from %s!!\n",
 406                        ioc->name, __func__);
 407                 rc = mpt_HardResetHandler(ioc, CAN_SLEEP);
 408                 printk(MYIOC_s_WARN_FMT "%s: HardReset: %s\n", ioc->name,
 409                        __func__, (rc == 0) ? "success" : "failed");
 410                 ioc_raw_state = mpt_GetIocState(ioc, 0);
 411                 if ((ioc_raw_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_FAULT)
 412                         printk(MYIOC_s_WARN_FMT "IOC is in FAULT state after "
 413                             "reset (%04xh)\n", ioc->name, ioc_raw_state &
 414                             MPI_DOORBELL_DATA_MASK);
 415         } else if (ioc->bus_type == SAS && ioc->sas_discovery_quiesce_io) {
 416                 if ((mpt_is_discovery_complete(ioc))) {
 417                         devtprintk(ioc, printk(MYIOC_s_DEBUG_FMT "clearing "
 418                             "discovery_quiesce_io flag\n", ioc->name));
 419                         ioc->sas_discovery_quiesce_io = 0;
 420                 }
 421         }
 422 
 423  out:
 424         /*
 425          * Take turns polling alternate controller
 426          */
 427         if (ioc->alt_ioc)
 428                 ioc = ioc->alt_ioc;
 429 
 430         /* rearm the timer */
 431         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
 432         if (ioc->reset_work_q)
 433                 queue_delayed_work(ioc->reset_work_q, &ioc->fault_reset_work,
 434                         msecs_to_jiffies(MPT_POLLING_INTERVAL));
 435         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
 436 }
 437 
 438 
 439 /*
 440  *  Process turbo (context) reply...
 441  */
 442 static void
 443 mpt_turbo_reply(MPT_ADAPTER *ioc, u32 pa)
 444 {
 445         MPT_FRAME_HDR *mf = NULL;
 446         MPT_FRAME_HDR *mr = NULL;
 447         u16 req_idx = 0;
 448         u8 cb_idx;
 449 
 450         dmfprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Got TURBO reply req_idx=%08x\n",
 451                                 ioc->name, pa));
 452 
 453         switch (pa >> MPI_CONTEXT_REPLY_TYPE_SHIFT) {
 454         case MPI_CONTEXT_REPLY_TYPE_SCSI_INIT:
 455                 req_idx = pa & 0x0000FFFF;
 456                 cb_idx = (pa & 0x00FF0000) >> 16;
 457                 mf = MPT_INDEX_2_MFPTR(ioc, req_idx);
 458                 break;
 459         case MPI_CONTEXT_REPLY_TYPE_LAN:
 460                 cb_idx = mpt_get_cb_idx(MPTLAN_DRIVER);
 461                 /*
 462                  *  Blind set of mf to NULL here was fatal
 463                  *  after lan_reply says "freeme"
 464                  *  Fix sort of combined with an optimization here;
 465                  *  added explicit check for case where lan_reply
 466                  *  was just returning 1 and doing nothing else.
 467                  *  For this case skip the callback, but set up
 468                  *  proper mf value first here:-)
 469                  */
 470                 if ((pa & 0x58000000) == 0x58000000) {
 471                         req_idx = pa & 0x0000FFFF;
 472                         mf = MPT_INDEX_2_MFPTR(ioc, req_idx);
 473                         mpt_free_msg_frame(ioc, mf);
 474                         mb();
 475                         return;
 476                         break;
 477                 }
 478                 mr = (MPT_FRAME_HDR *) CAST_U32_TO_PTR(pa);
 479                 break;
 480         case MPI_CONTEXT_REPLY_TYPE_SCSI_TARGET:
 481                 cb_idx = mpt_get_cb_idx(MPTSTM_DRIVER);
 482                 mr = (MPT_FRAME_HDR *) CAST_U32_TO_PTR(pa);
 483                 break;
 484         default:
 485                 cb_idx = 0;
 486                 BUG();
 487         }
 488 
 489         /*  Check for (valid) IO callback!  */
 490         if (!cb_idx || cb_idx >= MPT_MAX_PROTOCOL_DRIVERS ||
 491                 MptCallbacks[cb_idx] == NULL) {
 492                 printk(MYIOC_s_WARN_FMT "%s: Invalid cb_idx (%d)!\n",
 493                                 __func__, ioc->name, cb_idx);
 494                 goto out;
 495         }
 496 
 497         if (MptCallbacks[cb_idx](ioc, mf, mr))
 498                 mpt_free_msg_frame(ioc, mf);
 499  out:
 500         mb();
 501 }
 502 
 503 static void
 504 mpt_reply(MPT_ADAPTER *ioc, u32 pa)
 505 {
 506         MPT_FRAME_HDR   *mf;
 507         MPT_FRAME_HDR   *mr;
 508         u16              req_idx;
 509         u8               cb_idx;
 510         int              freeme;
 511 
 512         u32 reply_dma_low;
 513         u16 ioc_stat;
 514 
 515         /* non-TURBO reply!  Hmmm, something may be up...
 516          *  Newest turbo reply mechanism; get address
 517          *  via left shift 1 (get rid of MPI_ADDRESS_REPLY_A_BIT)!
 518          */
 519 
 520         /* Map DMA address of reply header to cpu address.
 521          * pa is 32 bits - but the dma address may be 32 or 64 bits
 522          * get offset based only only the low addresses
 523          */
 524 
 525         reply_dma_low = (pa <<= 1);
 526         mr = (MPT_FRAME_HDR *)((u8 *)ioc->reply_frames +
 527                          (reply_dma_low - ioc->reply_frames_low_dma));
 528 
 529         req_idx = le16_to_cpu(mr->u.frame.hwhdr.msgctxu.fld.req_idx);
 530         cb_idx = mr->u.frame.hwhdr.msgctxu.fld.cb_idx;
 531         mf = MPT_INDEX_2_MFPTR(ioc, req_idx);
 532 
 533         dmfprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Got non-TURBO reply=%p req_idx=%x cb_idx=%x Function=%x\n",
 534                         ioc->name, mr, req_idx, cb_idx, mr->u.hdr.Function));
 535         DBG_DUMP_REPLY_FRAME(ioc, (u32 *)mr);
 536 
 537          /*  Check/log IOC log info
 538          */
 539         ioc_stat = le16_to_cpu(mr->u.reply.IOCStatus);
 540         if (ioc_stat & MPI_IOCSTATUS_FLAG_LOG_INFO_AVAILABLE) {
 541                 u32      log_info = le32_to_cpu(mr->u.reply.IOCLogInfo);
 542                 if (ioc->bus_type == FC)
 543                         mpt_fc_log_info(ioc, log_info);
 544                 else if (ioc->bus_type == SPI)
 545                         mpt_spi_log_info(ioc, log_info);
 546                 else if (ioc->bus_type == SAS)
 547                         mpt_sas_log_info(ioc, log_info, cb_idx);
 548         }
 549 
 550         if (ioc_stat & MPI_IOCSTATUS_MASK)
 551                 mpt_iocstatus_info(ioc, (u32)ioc_stat, mf);
 552 
 553         /*  Check for (valid) IO callback!  */
 554         if (!cb_idx || cb_idx >= MPT_MAX_PROTOCOL_DRIVERS ||
 555                 MptCallbacks[cb_idx] == NULL) {
 556                 printk(MYIOC_s_WARN_FMT "%s: Invalid cb_idx (%d)!\n",
 557                                 __func__, ioc->name, cb_idx);
 558                 freeme = 0;
 559                 goto out;
 560         }
 561 
 562         freeme = MptCallbacks[cb_idx](ioc, mf, mr);
 563 
 564  out:
 565         /*  Flush (non-TURBO) reply with a WRITE!  */
 566         CHIPREG_WRITE32(&ioc->chip->ReplyFifo, pa);
 567 
 568         if (freeme)
 569                 mpt_free_msg_frame(ioc, mf);
 570         mb();
 571 }
 572 
 573 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 574 /**
 575  *      mpt_interrupt - MPT adapter (IOC) specific interrupt handler.
 576  *      @irq: irq number (not used)
 577  *      @bus_id: bus identifier cookie == pointer to MPT_ADAPTER structure
 578  *
 579  *      This routine is registered via the request_irq() kernel API call,
 580  *      and handles all interrupts generated from a specific MPT adapter
 581  *      (also referred to as a IO Controller or IOC).
 582  *      This routine must clear the interrupt from the adapter and does
 583  *      so by reading the reply FIFO.  Multiple replies may be processed
 584  *      per single call to this routine.
 585  *
 586  *      This routine handles register-level access of the adapter but
 587  *      dispatches (calls) a protocol-specific callback routine to handle
 588  *      the protocol-specific details of the MPT request completion.
 589  */
 590 static irqreturn_t
 591 mpt_interrupt(int irq, void *bus_id)
 592 {
 593         MPT_ADAPTER *ioc = bus_id;
 594         u32 pa = CHIPREG_READ32_dmasync(&ioc->chip->ReplyFifo);
 595 
 596         if (pa == 0xFFFFFFFF)
 597                 return IRQ_NONE;
 598 
 599         /*
 600          *  Drain the reply FIFO!
 601          */
 602         do {
 603                 if (pa & MPI_ADDRESS_REPLY_A_BIT)
 604                         mpt_reply(ioc, pa);
 605                 else
 606                         mpt_turbo_reply(ioc, pa);
 607                 pa = CHIPREG_READ32_dmasync(&ioc->chip->ReplyFifo);
 608         } while (pa != 0xFFFFFFFF);
 609 
 610         return IRQ_HANDLED;
 611 }
 612 
 613 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 614 /**
 615  *      mptbase_reply - MPT base driver's callback routine
 616  *      @ioc: Pointer to MPT_ADAPTER structure
 617  *      @req: Pointer to original MPT request frame
 618  *      @reply: Pointer to MPT reply frame (NULL if TurboReply)
 619  *
 620  *      MPT base driver's callback routine; all base driver
 621  *      "internal" request/reply processing is routed here.
 622  *      Currently used for EventNotification and EventAck handling.
 623  *
 624  *      Returns 1 indicating original alloc'd request frame ptr
 625  *      should be freed, or 0 if it shouldn't.
 626  */
 627 static int
 628 mptbase_reply(MPT_ADAPTER *ioc, MPT_FRAME_HDR *req, MPT_FRAME_HDR *reply)
 629 {
 630         EventNotificationReply_t *pEventReply;
 631         u8 event;
 632         int evHandlers;
 633         int freereq = 1;
 634 
 635         switch (reply->u.hdr.Function) {
 636         case MPI_FUNCTION_EVENT_NOTIFICATION:
 637                 pEventReply = (EventNotificationReply_t *)reply;
 638                 evHandlers = 0;
 639                 ProcessEventNotification(ioc, pEventReply, &evHandlers);
 640                 event = le32_to_cpu(pEventReply->Event) & 0xFF;
 641                 if (pEventReply->MsgFlags & MPI_MSGFLAGS_CONTINUATION_REPLY)
 642                         freereq = 0;
 643                 if (event != MPI_EVENT_EVENT_CHANGE)
 644                         break;
 645                 /* fall through */
 646         case MPI_FUNCTION_CONFIG:
 647         case MPI_FUNCTION_SAS_IO_UNIT_CONTROL:
 648                 ioc->mptbase_cmds.status |= MPT_MGMT_STATUS_COMMAND_GOOD;
 649                 ioc->mptbase_cmds.status |= MPT_MGMT_STATUS_RF_VALID;
 650                 memcpy(ioc->mptbase_cmds.reply, reply,
 651                     min(MPT_DEFAULT_FRAME_SIZE,
 652                         4 * reply->u.reply.MsgLength));
 653                 if (ioc->mptbase_cmds.status & MPT_MGMT_STATUS_PENDING) {
 654                         ioc->mptbase_cmds.status &= ~MPT_MGMT_STATUS_PENDING;
 655                         complete(&ioc->mptbase_cmds.done);
 656                 } else
 657                         freereq = 0;
 658                 if (ioc->mptbase_cmds.status & MPT_MGMT_STATUS_FREE_MF)
 659                         freereq = 1;
 660                 break;
 661         case MPI_FUNCTION_EVENT_ACK:
 662                 devtverboseprintk(ioc, printk(MYIOC_s_DEBUG_FMT
 663                     "EventAck reply received\n", ioc->name));
 664                 break;
 665         default:
 666                 printk(MYIOC_s_ERR_FMT
 667                     "Unexpected msg function (=%02Xh) reply received!\n",
 668                     ioc->name, reply->u.hdr.Function);
 669                 break;
 670         }
 671 
 672         /*
 673          *      Conditionally tell caller to free the original
 674          *      EventNotification/EventAck/unexpected request frame!
 675          */
 676         return freereq;
 677 }
 678 
 679 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 680 /**
 681  *      mpt_register - Register protocol-specific main callback handler.
 682  *      @cbfunc: callback function pointer
 683  *      @dclass: Protocol driver's class (%MPT_DRIVER_CLASS enum value)
 684  *      @func_name: call function's name
 685  *
 686  *      This routine is called by a protocol-specific driver (SCSI host,
 687  *      LAN, SCSI target) to register its reply callback routine.  Each
 688  *      protocol-specific driver must do this before it will be able to
 689  *      use any IOC resources, such as obtaining request frames.
 690  *
 691  *      NOTES: The SCSI protocol driver currently calls this routine thrice
 692  *      in order to register separate callbacks; one for "normal" SCSI IO;
 693  *      one for MptScsiTaskMgmt requests; one for Scan/DV requests.
 694  *
 695  *      Returns u8 valued "handle" in the range (and S.O.D. order)
 696  *      {N,...,7,6,5,...,1} if successful.
 697  *      A return value of MPT_MAX_PROTOCOL_DRIVERS (including zero!) should be
 698  *      considered an error by the caller.
 699  */
 700 u8
 701 mpt_register(MPT_CALLBACK cbfunc, MPT_DRIVER_CLASS dclass, char *func_name)
 702 {
 703         u8 cb_idx;
 704         last_drv_idx = MPT_MAX_PROTOCOL_DRIVERS;
 705 
 706         /*
 707          *  Search for empty callback slot in this order: {N,...,7,6,5,...,1}
 708          *  (slot/handle 0 is reserved!)
 709          */
 710         for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--) {
 711                 if (MptCallbacks[cb_idx] == NULL) {
 712                         MptCallbacks[cb_idx] = cbfunc;
 713                         MptDriverClass[cb_idx] = dclass;
 714                         MptEvHandlers[cb_idx] = NULL;
 715                         last_drv_idx = cb_idx;
 716                         strlcpy(MptCallbacksName[cb_idx], func_name,
 717                                 MPT_MAX_CALLBACKNAME_LEN+1);
 718                         break;
 719                 }
 720         }
 721 
 722         return last_drv_idx;
 723 }
 724 
 725 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 726 /**
 727  *      mpt_deregister - Deregister a protocol drivers resources.
 728  *      @cb_idx: previously registered callback handle
 729  *
 730  *      Each protocol-specific driver should call this routine when its
 731  *      module is unloaded.
 732  */
 733 void
 734 mpt_deregister(u8 cb_idx)
 735 {
 736         if (cb_idx && (cb_idx < MPT_MAX_PROTOCOL_DRIVERS)) {
 737                 MptCallbacks[cb_idx] = NULL;
 738                 MptDriverClass[cb_idx] = MPTUNKNOWN_DRIVER;
 739                 MptEvHandlers[cb_idx] = NULL;
 740 
 741                 last_drv_idx++;
 742         }
 743 }
 744 
 745 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 746 /**
 747  *      mpt_event_register - Register protocol-specific event callback handler.
 748  *      @cb_idx: previously registered (via mpt_register) callback handle
 749  *      @ev_cbfunc: callback function
 750  *
 751  *      This routine can be called by one or more protocol-specific drivers
 752  *      if/when they choose to be notified of MPT events.
 753  *
 754  *      Returns 0 for success.
 755  */
 756 int
 757 mpt_event_register(u8 cb_idx, MPT_EVHANDLER ev_cbfunc)
 758 {
 759         if (!cb_idx || cb_idx >= MPT_MAX_PROTOCOL_DRIVERS)
 760                 return -1;
 761 
 762         MptEvHandlers[cb_idx] = ev_cbfunc;
 763         return 0;
 764 }
 765 
 766 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 767 /**
 768  *      mpt_event_deregister - Deregister protocol-specific event callback handler
 769  *      @cb_idx: previously registered callback handle
 770  *
 771  *      Each protocol-specific driver should call this routine
 772  *      when it does not (or can no longer) handle events,
 773  *      or when its module is unloaded.
 774  */
 775 void
 776 mpt_event_deregister(u8 cb_idx)
 777 {
 778         if (!cb_idx || cb_idx >= MPT_MAX_PROTOCOL_DRIVERS)
 779                 return;
 780 
 781         MptEvHandlers[cb_idx] = NULL;
 782 }
 783 
 784 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 785 /**
 786  *      mpt_reset_register - Register protocol-specific IOC reset handler.
 787  *      @cb_idx: previously registered (via mpt_register) callback handle
 788  *      @reset_func: reset function
 789  *
 790  *      This routine can be called by one or more protocol-specific drivers
 791  *      if/when they choose to be notified of IOC resets.
 792  *
 793  *      Returns 0 for success.
 794  */
 795 int
 796 mpt_reset_register(u8 cb_idx, MPT_RESETHANDLER reset_func)
 797 {
 798         if (!cb_idx || cb_idx >= MPT_MAX_PROTOCOL_DRIVERS)
 799                 return -1;
 800 
 801         MptResetHandlers[cb_idx] = reset_func;
 802         return 0;
 803 }
 804 
 805 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 806 /**
 807  *      mpt_reset_deregister - Deregister protocol-specific IOC reset handler.
 808  *      @cb_idx: previously registered callback handle
 809  *
 810  *      Each protocol-specific driver should call this routine
 811  *      when it does not (or can no longer) handle IOC reset handling,
 812  *      or when its module is unloaded.
 813  */
 814 void
 815 mpt_reset_deregister(u8 cb_idx)
 816 {
 817         if (!cb_idx || cb_idx >= MPT_MAX_PROTOCOL_DRIVERS)
 818                 return;
 819 
 820         MptResetHandlers[cb_idx] = NULL;
 821 }
 822 
 823 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 824 /**
 825  *      mpt_device_driver_register - Register device driver hooks
 826  *      @dd_cbfunc: driver callbacks struct
 827  *      @cb_idx: MPT protocol driver index
 828  */
 829 int
 830 mpt_device_driver_register(struct mpt_pci_driver * dd_cbfunc, u8 cb_idx)
 831 {
 832         MPT_ADAPTER     *ioc;
 833         const struct pci_device_id *id;
 834 
 835         if (!cb_idx || cb_idx >= MPT_MAX_PROTOCOL_DRIVERS)
 836                 return -EINVAL;
 837 
 838         MptDeviceDriverHandlers[cb_idx] = dd_cbfunc;
 839 
 840         /* call per pci device probe entry point */
 841         list_for_each_entry(ioc, &ioc_list, list) {
 842                 id = ioc->pcidev->driver ?
 843                     ioc->pcidev->driver->id_table : NULL;
 844                 if (dd_cbfunc->probe)
 845                         dd_cbfunc->probe(ioc->pcidev, id);
 846          }
 847 
 848         return 0;
 849 }
 850 
 851 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 852 /**
 853  *      mpt_device_driver_deregister - DeRegister device driver hooks
 854  *      @cb_idx: MPT protocol driver index
 855  */
 856 void
 857 mpt_device_driver_deregister(u8 cb_idx)
 858 {
 859         struct mpt_pci_driver *dd_cbfunc;
 860         MPT_ADAPTER     *ioc;
 861 
 862         if (!cb_idx || cb_idx >= MPT_MAX_PROTOCOL_DRIVERS)
 863                 return;
 864 
 865         dd_cbfunc = MptDeviceDriverHandlers[cb_idx];
 866 
 867         list_for_each_entry(ioc, &ioc_list, list) {
 868                 if (dd_cbfunc->remove)
 869                         dd_cbfunc->remove(ioc->pcidev);
 870         }
 871 
 872         MptDeviceDriverHandlers[cb_idx] = NULL;
 873 }
 874 
 875 
 876 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 877 /**
 878  *      mpt_get_msg_frame - Obtain an MPT request frame from the pool
 879  *      @cb_idx: Handle of registered MPT protocol driver
 880  *      @ioc: Pointer to MPT adapter structure
 881  *
 882  *      Obtain an MPT request frame from the pool (of 1024) that are
 883  *      allocated per MPT adapter.
 884  *
 885  *      Returns pointer to a MPT request frame or %NULL if none are available
 886  *      or IOC is not active.
 887  */
 888 MPT_FRAME_HDR*
 889 mpt_get_msg_frame(u8 cb_idx, MPT_ADAPTER *ioc)
 890 {
 891         MPT_FRAME_HDR *mf;
 892         unsigned long flags;
 893         u16      req_idx;       /* Request index */
 894 
 895         /* validate handle and ioc identifier */
 896 
 897 #ifdef MFCNT
 898         if (!ioc->active)
 899                 printk(MYIOC_s_WARN_FMT "IOC Not Active! mpt_get_msg_frame "
 900                     "returning NULL!\n", ioc->name);
 901 #endif
 902 
 903         /* If interrupts are not attached, do not return a request frame */
 904         if (!ioc->active)
 905                 return NULL;
 906 
 907         spin_lock_irqsave(&ioc->FreeQlock, flags);
 908         if (!list_empty(&ioc->FreeQ)) {
 909                 int req_offset;
 910 
 911                 mf = list_entry(ioc->FreeQ.next, MPT_FRAME_HDR,
 912                                 u.frame.linkage.list);
 913                 list_del(&mf->u.frame.linkage.list);
 914                 mf->u.frame.linkage.arg1 = 0;
 915                 mf->u.frame.hwhdr.msgctxu.fld.cb_idx = cb_idx;  /* byte */
 916                 req_offset = (u8 *)mf - (u8 *)ioc->req_frames;
 917                                                                 /* u16! */
 918                 req_idx = req_offset / ioc->req_sz;
 919                 mf->u.frame.hwhdr.msgctxu.fld.req_idx = cpu_to_le16(req_idx);
 920                 mf->u.frame.hwhdr.msgctxu.fld.rsvd = 0;
 921                 /* Default, will be changed if necessary in SG generation */
 922                 ioc->RequestNB[req_idx] = ioc->NB_for_64_byte_frame;
 923 #ifdef MFCNT
 924                 ioc->mfcnt++;
 925 #endif
 926         }
 927         else
 928                 mf = NULL;
 929         spin_unlock_irqrestore(&ioc->FreeQlock, flags);
 930 
 931 #ifdef MFCNT
 932         if (mf == NULL)
 933                 printk(MYIOC_s_WARN_FMT "IOC Active. No free Msg Frames! "
 934                     "Count 0x%x Max 0x%x\n", ioc->name, ioc->mfcnt,
 935                     ioc->req_depth);
 936         mfcounter++;
 937         if (mfcounter == PRINT_MF_COUNT)
 938                 printk(MYIOC_s_INFO_FMT "MF Count 0x%x Max 0x%x \n", ioc->name,
 939                     ioc->mfcnt, ioc->req_depth);
 940 #endif
 941 
 942         dmfprintk(ioc, printk(MYIOC_s_DEBUG_FMT "mpt_get_msg_frame(%d,%d), got mf=%p\n",
 943             ioc->name, cb_idx, ioc->id, mf));
 944         return mf;
 945 }
 946 
 947 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
 948 /**
 949  *      mpt_put_msg_frame - Send a protocol-specific MPT request frame to an IOC
 950  *      @cb_idx: Handle of registered MPT protocol driver
 951  *      @ioc: Pointer to MPT adapter structure
 952  *      @mf: Pointer to MPT request frame
 953  *
 954  *      This routine posts an MPT request frame to the request post FIFO of a
 955  *      specific MPT adapter.
 956  */
 957 void
 958 mpt_put_msg_frame(u8 cb_idx, MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf)
 959 {
 960         u32 mf_dma_addr;
 961         int req_offset;
 962         u16 req_idx;    /* Request index */
 963 
 964         /* ensure values are reset properly! */
 965         mf->u.frame.hwhdr.msgctxu.fld.cb_idx = cb_idx;          /* byte */
 966         req_offset = (u8 *)mf - (u8 *)ioc->req_frames;
 967                                                                 /* u16! */
 968         req_idx = req_offset / ioc->req_sz;
 969         mf->u.frame.hwhdr.msgctxu.fld.req_idx = cpu_to_le16(req_idx);
 970         mf->u.frame.hwhdr.msgctxu.fld.rsvd = 0;
 971 
 972         DBG_DUMP_PUT_MSG_FRAME(ioc, (u32 *)mf);
 973 
 974         mf_dma_addr = (ioc->req_frames_low_dma + req_offset) | ioc->RequestNB[req_idx];
 975         dsgprintk(ioc, printk(MYIOC_s_DEBUG_FMT "mf_dma_addr=%x req_idx=%d "
 976             "RequestNB=%x\n", ioc->name, mf_dma_addr, req_idx,
 977             ioc->RequestNB[req_idx]));
 978         CHIPREG_WRITE32(&ioc->chip->RequestFifo, mf_dma_addr);
 979 }
 980 
 981 /**
 982  *      mpt_put_msg_frame_hi_pri - Send a hi-pri protocol-specific MPT request frame
 983  *      @cb_idx: Handle of registered MPT protocol driver
 984  *      @ioc: Pointer to MPT adapter structure
 985  *      @mf: Pointer to MPT request frame
 986  *
 987  *      Send a protocol-specific MPT request frame to an IOC using
 988  *      hi-priority request queue.
 989  *
 990  *      This routine posts an MPT request frame to the request post FIFO of a
 991  *      specific MPT adapter.
 992  **/
 993 void
 994 mpt_put_msg_frame_hi_pri(u8 cb_idx, MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf)
 995 {
 996         u32 mf_dma_addr;
 997         int req_offset;
 998         u16 req_idx;    /* Request index */
 999 
1000         /* ensure values are reset properly! */
1001         mf->u.frame.hwhdr.msgctxu.fld.cb_idx = cb_idx;
1002         req_offset = (u8 *)mf - (u8 *)ioc->req_frames;
1003         req_idx = req_offset / ioc->req_sz;
1004         mf->u.frame.hwhdr.msgctxu.fld.req_idx = cpu_to_le16(req_idx);
1005         mf->u.frame.hwhdr.msgctxu.fld.rsvd = 0;
1006 
1007         DBG_DUMP_PUT_MSG_FRAME(ioc, (u32 *)mf);
1008 
1009         mf_dma_addr = (ioc->req_frames_low_dma + req_offset);
1010         dsgprintk(ioc, printk(MYIOC_s_DEBUG_FMT "mf_dma_addr=%x req_idx=%d\n",
1011                 ioc->name, mf_dma_addr, req_idx));
1012         CHIPREG_WRITE32(&ioc->chip->RequestHiPriFifo, mf_dma_addr);
1013 }
1014 
1015 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
1016 /**
1017  *      mpt_free_msg_frame - Place MPT request frame back on FreeQ.
1018  *      @ioc: Pointer to MPT adapter structure
1019  *      @mf: Pointer to MPT request frame
1020  *
1021  *      This routine places a MPT request frame back on the MPT adapter's
1022  *      FreeQ.
1023  */
1024 void
1025 mpt_free_msg_frame(MPT_ADAPTER *ioc, MPT_FRAME_HDR *mf)
1026 {
1027         unsigned long flags;
1028 
1029         /*  Put Request back on FreeQ!  */
1030         spin_lock_irqsave(&ioc->FreeQlock, flags);
1031         if (cpu_to_le32(mf->u.frame.linkage.arg1) == 0xdeadbeaf)
1032                 goto out;
1033         /* signature to know if this mf is freed */
1034         mf->u.frame.linkage.arg1 = cpu_to_le32(0xdeadbeaf);
1035         list_add(&mf->u.frame.linkage.list, &ioc->FreeQ);
1036 #ifdef MFCNT
1037         ioc->mfcnt--;
1038 #endif
1039  out:
1040         spin_unlock_irqrestore(&ioc->FreeQlock, flags);
1041 }
1042 
1043 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
1044 /**
1045  *      mpt_add_sge - Place a simple 32 bit SGE at address pAddr.
1046  *      @pAddr: virtual address for SGE
1047  *      @flagslength: SGE flags and data transfer length
1048  *      @dma_addr: Physical address
1049  *
1050  *      This routine places a MPT request frame back on the MPT adapter's
1051  *      FreeQ.
1052  */
1053 static void
1054 mpt_add_sge(void *pAddr, u32 flagslength, dma_addr_t dma_addr)
1055 {
1056         SGESimple32_t *pSge = (SGESimple32_t *) pAddr;
1057         pSge->FlagsLength = cpu_to_le32(flagslength);
1058         pSge->Address = cpu_to_le32(dma_addr);
1059 }
1060 
1061 /**
1062  *      mpt_add_sge_64bit - Place a simple 64 bit SGE at address pAddr.
1063  *      @pAddr: virtual address for SGE
1064  *      @flagslength: SGE flags and data transfer length
1065  *      @dma_addr: Physical address
1066  *
1067  *      This routine places a MPT request frame back on the MPT adapter's
1068  *      FreeQ.
1069  **/
1070 static void
1071 mpt_add_sge_64bit(void *pAddr, u32 flagslength, dma_addr_t dma_addr)
1072 {
1073         SGESimple64_t *pSge = (SGESimple64_t *) pAddr;
1074         pSge->Address.Low = cpu_to_le32
1075                         (lower_32_bits(dma_addr));
1076         pSge->Address.High = cpu_to_le32
1077                         (upper_32_bits(dma_addr));
1078         pSge->FlagsLength = cpu_to_le32
1079                         ((flagslength | MPT_SGE_FLAGS_64_BIT_ADDRESSING));
1080 }
1081 
1082 /**
1083  *      mpt_add_sge_64bit_1078 - Place a simple 64 bit SGE at address pAddr (1078 workaround).
1084  *      @pAddr: virtual address for SGE
1085  *      @flagslength: SGE flags and data transfer length
1086  *      @dma_addr: Physical address
1087  *
1088  *      This routine places a MPT request frame back on the MPT adapter's
1089  *      FreeQ.
1090  **/
1091 static void
1092 mpt_add_sge_64bit_1078(void *pAddr, u32 flagslength, dma_addr_t dma_addr)
1093 {
1094         SGESimple64_t *pSge = (SGESimple64_t *) pAddr;
1095         u32 tmp;
1096 
1097         pSge->Address.Low = cpu_to_le32
1098                         (lower_32_bits(dma_addr));
1099         tmp = (u32)(upper_32_bits(dma_addr));
1100 
1101         /*
1102          * 1078 errata workaround for the 36GB limitation
1103          */
1104         if ((((u64)dma_addr + MPI_SGE_LENGTH(flagslength)) >> 32)  == 9) {
1105                 flagslength |=
1106                     MPI_SGE_SET_FLAGS(MPI_SGE_FLAGS_LOCAL_ADDRESS);
1107                 tmp |= (1<<31);
1108                 if (mpt_debug_level & MPT_DEBUG_36GB_MEM)
1109                         printk(KERN_DEBUG "1078 P0M2 addressing for "
1110                             "addr = 0x%llx len = %d\n",
1111                             (unsigned long long)dma_addr,
1112                             MPI_SGE_LENGTH(flagslength));
1113         }
1114 
1115         pSge->Address.High = cpu_to_le32(tmp);
1116         pSge->FlagsLength = cpu_to_le32(
1117                 (flagslength | MPT_SGE_FLAGS_64_BIT_ADDRESSING));
1118 }
1119 
1120 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
1121 /**
1122  *      mpt_add_chain - Place a 32 bit chain SGE at address pAddr.
1123  *      @pAddr: virtual address for SGE
1124  *      @next: nextChainOffset value (u32's)
1125  *      @length: length of next SGL segment
1126  *      @dma_addr: Physical address
1127  *
1128  */
1129 static void
1130 mpt_add_chain(void *pAddr, u8 next, u16 length, dma_addr_t dma_addr)
1131 {
1132         SGEChain32_t *pChain = (SGEChain32_t *) pAddr;
1133 
1134         pChain->Length = cpu_to_le16(length);
1135         pChain->Flags = MPI_SGE_FLAGS_CHAIN_ELEMENT;
1136         pChain->NextChainOffset = next;
1137         pChain->Address = cpu_to_le32(dma_addr);
1138 }
1139 
1140 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
1141 /**
1142  *      mpt_add_chain_64bit - Place a 64 bit chain SGE at address pAddr.
1143  *      @pAddr: virtual address for SGE
1144  *      @next: nextChainOffset value (u32's)
1145  *      @length: length of next SGL segment
1146  *      @dma_addr: Physical address
1147  *
1148  */
1149 static void
1150 mpt_add_chain_64bit(void *pAddr, u8 next, u16 length, dma_addr_t dma_addr)
1151 {
1152         SGEChain64_t *pChain = (SGEChain64_t *) pAddr;
1153         u32 tmp = dma_addr & 0xFFFFFFFF;
1154 
1155         pChain->Length = cpu_to_le16(length);
1156         pChain->Flags = (MPI_SGE_FLAGS_CHAIN_ELEMENT |
1157                          MPI_SGE_FLAGS_64_BIT_ADDRESSING);
1158 
1159         pChain->NextChainOffset = next;
1160 
1161         pChain->Address.Low = cpu_to_le32(tmp);
1162         tmp = (u32)(upper_32_bits(dma_addr));
1163         pChain->Address.High = cpu_to_le32(tmp);
1164 }
1165 
1166 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
1167 /**
1168  *      mpt_send_handshake_request - Send MPT request via doorbell handshake method.
1169  *      @cb_idx: Handle of registered MPT protocol driver
1170  *      @ioc: Pointer to MPT adapter structure
1171  *      @reqBytes: Size of the request in bytes
1172  *      @req: Pointer to MPT request frame
1173  *      @sleepFlag: Use schedule if CAN_SLEEP else use udelay.
1174  *
1175  *      This routine is used exclusively to send MptScsiTaskMgmt
1176  *      requests since they are required to be sent via doorbell handshake.
1177  *
1178  *      NOTE: It is the callers responsibility to byte-swap fields in the
1179  *      request which are greater than 1 byte in size.
1180  *
1181  *      Returns 0 for success, non-zero for failure.
1182  */
1183 int
1184 mpt_send_handshake_request(u8 cb_idx, MPT_ADAPTER *ioc, int reqBytes, u32 *req, int sleepFlag)
1185 {
1186         int     r = 0;
1187         u8      *req_as_bytes;
1188         int      ii;
1189 
1190         /* State is known to be good upon entering
1191          * this function so issue the bus reset
1192          * request.
1193          */
1194 
1195         /*
1196          * Emulate what mpt_put_msg_frame() does /wrt to sanity
1197          * setting cb_idx/req_idx.  But ONLY if this request
1198          * is in proper (pre-alloc'd) request buffer range...
1199          */
1200         ii = MFPTR_2_MPT_INDEX(ioc,(MPT_FRAME_HDR*)req);
1201         if (reqBytes >= 12 && ii >= 0 && ii < ioc->req_depth) {
1202                 MPT_FRAME_HDR *mf = (MPT_FRAME_HDR*)req;
1203                 mf->u.frame.hwhdr.msgctxu.fld.req_idx = cpu_to_le16(ii);
1204                 mf->u.frame.hwhdr.msgctxu.fld.cb_idx = cb_idx;
1205         }
1206 
1207         /* Make sure there are no doorbells */
1208         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
1209 
1210         CHIPREG_WRITE32(&ioc->chip->Doorbell,
1211                         ((MPI_FUNCTION_HANDSHAKE<<MPI_DOORBELL_FUNCTION_SHIFT) |
1212                          ((reqBytes/4)<<MPI_DOORBELL_ADD_DWORDS_SHIFT)));
1213 
1214         /* Wait for IOC doorbell int */
1215         if ((ii = WaitForDoorbellInt(ioc, 5, sleepFlag)) < 0) {
1216                 return ii;
1217         }
1218 
1219         /* Read doorbell and check for active bit */
1220         if (!(CHIPREG_READ32(&ioc->chip->Doorbell) & MPI_DOORBELL_ACTIVE))
1221                 return -5;
1222 
1223         dhsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "mpt_send_handshake_request start, WaitCnt=%d\n",
1224                 ioc->name, ii));
1225 
1226         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
1227 
1228         if ((r = WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0) {
1229                 return -2;
1230         }
1231 
1232         /* Send request via doorbell handshake */
1233         req_as_bytes = (u8 *) req;
1234         for (ii = 0; ii < reqBytes/4; ii++) {
1235                 u32 word;
1236 
1237                 word = ((req_as_bytes[(ii*4) + 0] <<  0) |
1238                         (req_as_bytes[(ii*4) + 1] <<  8) |
1239                         (req_as_bytes[(ii*4) + 2] << 16) |
1240                         (req_as_bytes[(ii*4) + 3] << 24));
1241                 CHIPREG_WRITE32(&ioc->chip->Doorbell, word);
1242                 if ((r = WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0) {
1243                         r = -3;
1244                         break;
1245                 }
1246         }
1247 
1248         if (r >= 0 && WaitForDoorbellInt(ioc, 10, sleepFlag) >= 0)
1249                 r = 0;
1250         else
1251                 r = -4;
1252 
1253         /* Make sure there are no doorbells */
1254         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
1255 
1256         return r;
1257 }
1258 
1259 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
1260 /**
1261  * mpt_host_page_access_control - control the IOC's Host Page Buffer access
1262  * @ioc: Pointer to MPT adapter structure
1263  * @access_control_value: define bits below
1264  * @sleepFlag: Specifies whether the process can sleep
1265  *
1266  * Provides mechanism for the host driver to control the IOC's
1267  * Host Page Buffer access.
1268  *
1269  * Access Control Value - bits[15:12]
1270  * 0h Reserved
1271  * 1h Enable Access { MPI_DB_HPBAC_ENABLE_ACCESS }
1272  * 2h Disable Access { MPI_DB_HPBAC_DISABLE_ACCESS }
1273  * 3h Free Buffer { MPI_DB_HPBAC_FREE_BUFFER }
1274  *
1275  * Returns 0 for success, non-zero for failure.
1276  */
1277 
1278 static int
1279 mpt_host_page_access_control(MPT_ADAPTER *ioc, u8 access_control_value, int sleepFlag)
1280 {
1281         int      r = 0;
1282 
1283         /* return if in use */
1284         if (CHIPREG_READ32(&ioc->chip->Doorbell)
1285             & MPI_DOORBELL_ACTIVE)
1286             return -1;
1287 
1288         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
1289 
1290         CHIPREG_WRITE32(&ioc->chip->Doorbell,
1291                 ((MPI_FUNCTION_HOST_PAGEBUF_ACCESS_CONTROL
1292                  <<MPI_DOORBELL_FUNCTION_SHIFT) |
1293                  (access_control_value<<12)));
1294 
1295         /* Wait for IOC to clear Doorbell Status bit */
1296         if ((r = WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0) {
1297                 return -2;
1298         }else
1299                 return 0;
1300 }
1301 
1302 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
1303 /**
1304  *      mpt_host_page_alloc - allocate system memory for the fw
1305  *      @ioc: Pointer to pointer to IOC adapter
1306  *      @ioc_init: Pointer to ioc init config page
1307  *
1308  *      If we already allocated memory in past, then resend the same pointer.
1309  *      Returns 0 for success, non-zero for failure.
1310  */
1311 static int
1312 mpt_host_page_alloc(MPT_ADAPTER *ioc, pIOCInit_t ioc_init)
1313 {
1314         char    *psge;
1315         int     flags_length;
1316         u32     host_page_buffer_sz=0;
1317 
1318         if(!ioc->HostPageBuffer) {
1319 
1320                 host_page_buffer_sz =
1321                     le32_to_cpu(ioc->facts.HostPageBufferSGE.FlagsLength) & 0xFFFFFF;
1322 
1323                 if(!host_page_buffer_sz)
1324                         return 0; /* fw doesn't need any host buffers */
1325 
1326                 /* spin till we get enough memory */
1327                 while(host_page_buffer_sz > 0) {
1328 
1329                         if((ioc->HostPageBuffer = pci_alloc_consistent(
1330                             ioc->pcidev,
1331                             host_page_buffer_sz,
1332                             &ioc->HostPageBuffer_dma)) != NULL) {
1333 
1334                                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT
1335                                     "host_page_buffer @ %p, dma @ %x, sz=%d bytes\n",
1336                                     ioc->name, ioc->HostPageBuffer,
1337                                     (u32)ioc->HostPageBuffer_dma,
1338                                     host_page_buffer_sz));
1339                                 ioc->alloc_total += host_page_buffer_sz;
1340                                 ioc->HostPageBuffer_sz = host_page_buffer_sz;
1341                                 break;
1342                         }
1343 
1344                         host_page_buffer_sz -= (4*1024);
1345                 }
1346         }
1347 
1348         if(!ioc->HostPageBuffer) {
1349                 printk(MYIOC_s_ERR_FMT
1350                     "Failed to alloc memory for host_page_buffer!\n",
1351                     ioc->name);
1352                 return -999;
1353         }
1354 
1355         psge = (char *)&ioc_init->HostPageBufferSGE;
1356         flags_length = MPI_SGE_FLAGS_SIMPLE_ELEMENT |
1357             MPI_SGE_FLAGS_SYSTEM_ADDRESS |
1358             MPI_SGE_FLAGS_HOST_TO_IOC |
1359             MPI_SGE_FLAGS_END_OF_BUFFER;
1360         flags_length = flags_length << MPI_SGE_FLAGS_SHIFT;
1361         flags_length |= ioc->HostPageBuffer_sz;
1362         ioc->add_sge(psge, flags_length, ioc->HostPageBuffer_dma);
1363         ioc->facts.HostPageBufferSGE = ioc_init->HostPageBufferSGE;
1364 
1365         return 0;
1366 }
1367 
1368 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
1369 /**
1370  *      mpt_verify_adapter - Given IOC identifier, set pointer to its adapter structure.
1371  *      @iocid: IOC unique identifier (integer)
1372  *      @iocpp: Pointer to pointer to IOC adapter
1373  *
1374  *      Given a unique IOC identifier, set pointer to the associated MPT
1375  *      adapter structure.
1376  *
1377  *      Returns iocid and sets iocpp if iocid is found.
1378  *      Returns -1 if iocid is not found.
1379  */
1380 int
1381 mpt_verify_adapter(int iocid, MPT_ADAPTER **iocpp)
1382 {
1383         MPT_ADAPTER *ioc;
1384 
1385         list_for_each_entry(ioc,&ioc_list,list) {
1386                 if (ioc->id == iocid) {
1387                         *iocpp =ioc;
1388                         return iocid;
1389                 }
1390         }
1391 
1392         *iocpp = NULL;
1393         return -1;
1394 }
1395 
1396 /**
1397  *      mpt_get_product_name - returns product string
1398  *      @vendor: pci vendor id
1399  *      @device: pci device id
1400  *      @revision: pci revision id
1401  *
1402  *      Returns product string displayed when driver loads,
1403  *      in /proc/mpt/summary and /sysfs/class/scsi_host/host<X>/version_product
1404  *
1405  **/
1406 static const char*
1407 mpt_get_product_name(u16 vendor, u16 device, u8 revision)
1408 {
1409         char *product_str = NULL;
1410 
1411         if (vendor == PCI_VENDOR_ID_BROCADE) {
1412                 switch (device)
1413                 {
1414                 case MPI_MANUFACTPAGE_DEVICEID_FC949E:
1415                         switch (revision)
1416                         {
1417                         case 0x00:
1418                                 product_str = "BRE040 A0";
1419                                 break;
1420                         case 0x01:
1421                                 product_str = "BRE040 A1";
1422                                 break;
1423                         default:
1424                                 product_str = "BRE040";
1425                                 break;
1426                         }
1427                         break;
1428                 }
1429                 goto out;
1430         }
1431 
1432         switch (device)
1433         {
1434         case MPI_MANUFACTPAGE_DEVICEID_FC909:
1435                 product_str = "LSIFC909 B1";
1436                 break;
1437         case MPI_MANUFACTPAGE_DEVICEID_FC919:
1438                 product_str = "LSIFC919 B0";
1439                 break;
1440         case MPI_MANUFACTPAGE_DEVICEID_FC929:
1441                 product_str = "LSIFC929 B0";
1442                 break;
1443         case MPI_MANUFACTPAGE_DEVICEID_FC919X:
1444                 if (revision < 0x80)
1445                         product_str = "LSIFC919X A0";
1446                 else
1447                         product_str = "LSIFC919XL A1";
1448                 break;
1449         case MPI_MANUFACTPAGE_DEVICEID_FC929X:
1450                 if (revision < 0x80)
1451                         product_str = "LSIFC929X A0";
1452                 else
1453                         product_str = "LSIFC929XL A1";
1454                 break;
1455         case MPI_MANUFACTPAGE_DEVICEID_FC939X:
1456                 product_str = "LSIFC939X A1";
1457                 break;
1458         case MPI_MANUFACTPAGE_DEVICEID_FC949X:
1459                 product_str = "LSIFC949X A1";
1460                 break;
1461         case MPI_MANUFACTPAGE_DEVICEID_FC949E:
1462                 switch (revision)
1463                 {
1464                 case 0x00:
1465                         product_str = "LSIFC949E A0";
1466                         break;
1467                 case 0x01:
1468                         product_str = "LSIFC949E A1";
1469                         break;
1470                 default:
1471                         product_str = "LSIFC949E";
1472                         break;
1473                 }
1474                 break;
1475         case MPI_MANUFACTPAGE_DEVID_53C1030:
1476                 switch (revision)
1477                 {
1478                 case 0x00:
1479                         product_str = "LSI53C1030 A0";
1480                         break;
1481                 case 0x01:
1482                         product_str = "LSI53C1030 B0";
1483                         break;
1484                 case 0x03:
1485                         product_str = "LSI53C1030 B1";
1486                         break;
1487                 case 0x07:
1488                         product_str = "LSI53C1030 B2";
1489                         break;
1490                 case 0x08:
1491                         product_str = "LSI53C1030 C0";
1492                         break;
1493                 case 0x80:
1494                         product_str = "LSI53C1030T A0";
1495                         break;
1496                 case 0x83:
1497                         product_str = "LSI53C1030T A2";
1498                         break;
1499                 case 0x87:
1500                         product_str = "LSI53C1030T A3";
1501                         break;
1502                 case 0xc1:
1503                         product_str = "LSI53C1020A A1";
1504                         break;
1505                 default:
1506                         product_str = "LSI53C1030";
1507                         break;
1508                 }
1509                 break;
1510         case MPI_MANUFACTPAGE_DEVID_1030_53C1035:
1511                 switch (revision)
1512                 {
1513                 case 0x03:
1514                         product_str = "LSI53C1035 A2";
1515                         break;
1516                 case 0x04:
1517                         product_str = "LSI53C1035 B0";
1518                         break;
1519                 default:
1520                         product_str = "LSI53C1035";
1521                         break;
1522                 }
1523                 break;
1524         case MPI_MANUFACTPAGE_DEVID_SAS1064:
1525                 switch (revision)
1526                 {
1527                 case 0x00:
1528                         product_str = "LSISAS1064 A1";
1529                         break;
1530                 case 0x01:
1531                         product_str = "LSISAS1064 A2";
1532                         break;
1533                 case 0x02:
1534                         product_str = "LSISAS1064 A3";
1535                         break;
1536                 case 0x03:
1537                         product_str = "LSISAS1064 A4";
1538                         break;
1539                 default:
1540                         product_str = "LSISAS1064";
1541                         break;
1542                 }
1543                 break;
1544         case MPI_MANUFACTPAGE_DEVID_SAS1064E:
1545                 switch (revision)
1546                 {
1547                 case 0x00:
1548                         product_str = "LSISAS1064E A0";
1549                         break;
1550                 case 0x01:
1551                         product_str = "LSISAS1064E B0";
1552                         break;
1553                 case 0x02:
1554                         product_str = "LSISAS1064E B1";
1555                         break;
1556                 case 0x04:
1557                         product_str = "LSISAS1064E B2";
1558                         break;
1559                 case 0x08:
1560                         product_str = "LSISAS1064E B3";
1561                         break;
1562                 default:
1563                         product_str = "LSISAS1064E";
1564                         break;
1565                 }
1566                 break;
1567         case MPI_MANUFACTPAGE_DEVID_SAS1068:
1568                 switch (revision)
1569                 {
1570                 case 0x00:
1571                         product_str = "LSISAS1068 A0";
1572                         break;
1573                 case 0x01:
1574                         product_str = "LSISAS1068 B0";
1575                         break;
1576                 case 0x02:
1577                         product_str = "LSISAS1068 B1";
1578                         break;
1579                 default:
1580                         product_str = "LSISAS1068";
1581                         break;
1582                 }
1583                 break;
1584         case MPI_MANUFACTPAGE_DEVID_SAS1068E:
1585                 switch (revision)
1586                 {
1587                 case 0x00:
1588                         product_str = "LSISAS1068E A0";
1589                         break;
1590                 case 0x01:
1591                         product_str = "LSISAS1068E B0";
1592                         break;
1593                 case 0x02:
1594                         product_str = "LSISAS1068E B1";
1595                         break;
1596                 case 0x04:
1597                         product_str = "LSISAS1068E B2";
1598                         break;
1599                 case 0x08:
1600                         product_str = "LSISAS1068E B3";
1601                         break;
1602                 default:
1603                         product_str = "LSISAS1068E";
1604                         break;
1605                 }
1606                 break;
1607         case MPI_MANUFACTPAGE_DEVID_SAS1078:
1608                 switch (revision)
1609                 {
1610                 case 0x00:
1611                         product_str = "LSISAS1078 A0";
1612                         break;
1613                 case 0x01:
1614                         product_str = "LSISAS1078 B0";
1615                         break;
1616                 case 0x02:
1617                         product_str = "LSISAS1078 C0";
1618                         break;
1619                 case 0x03:
1620                         product_str = "LSISAS1078 C1";
1621                         break;
1622                 case 0x04:
1623                         product_str = "LSISAS1078 C2";
1624                         break;
1625                 default:
1626                         product_str = "LSISAS1078";
1627                         break;
1628                 }
1629                 break;
1630         }
1631 
1632  out:
1633         return product_str;
1634 }
1635 
1636 /**
1637  *      mpt_mapresources - map in memory mapped io
1638  *      @ioc: Pointer to pointer to IOC adapter
1639  *
1640  **/
1641 static int
1642 mpt_mapresources(MPT_ADAPTER *ioc)
1643 {
1644         u8              __iomem *mem;
1645         int              ii;
1646         resource_size_t  mem_phys;
1647         unsigned long    port;
1648         u32              msize;
1649         u32              psize;
1650         int              r = -ENODEV;
1651         struct pci_dev *pdev;
1652 
1653         pdev = ioc->pcidev;
1654         ioc->bars = pci_select_bars(pdev, IORESOURCE_MEM);
1655         if (pci_enable_device_mem(pdev)) {
1656                 printk(MYIOC_s_ERR_FMT "pci_enable_device_mem() "
1657                     "failed\n", ioc->name);
1658                 return r;
1659         }
1660         if (pci_request_selected_regions(pdev, ioc->bars, "mpt")) {
1661                 printk(MYIOC_s_ERR_FMT "pci_request_selected_regions() with "
1662                     "MEM failed\n", ioc->name);
1663                 goto out_pci_disable_device;
1664         }
1665 
1666         if (sizeof(dma_addr_t) > 4) {
1667                 const uint64_t required_mask = dma_get_required_mask
1668                     (&pdev->dev);
1669                 if (required_mask > DMA_BIT_MASK(32)
1670                         && !pci_set_dma_mask(pdev, DMA_BIT_MASK(64))
1671                         && !pci_set_consistent_dma_mask(pdev,
1672                                                  DMA_BIT_MASK(64))) {
1673                         ioc->dma_mask = DMA_BIT_MASK(64);
1674                         dinitprintk(ioc, printk(MYIOC_s_INFO_FMT
1675                                 ": 64 BIT PCI BUS DMA ADDRESSING SUPPORTED\n",
1676                                 ioc->name));
1677                 } else if (!pci_set_dma_mask(pdev, DMA_BIT_MASK(32))
1678                         && !pci_set_consistent_dma_mask(pdev,
1679                                                 DMA_BIT_MASK(32))) {
1680                         ioc->dma_mask = DMA_BIT_MASK(32);
1681                         dinitprintk(ioc, printk(MYIOC_s_INFO_FMT
1682                                 ": 32 BIT PCI BUS DMA ADDRESSING SUPPORTED\n",
1683                                 ioc->name));
1684                 } else {
1685                         printk(MYIOC_s_WARN_FMT "no suitable DMA mask for %s\n",
1686                             ioc->name, pci_name(pdev));
1687                         goto out_pci_release_region;
1688                 }
1689         } else {
1690                 if (!pci_set_dma_mask(pdev, DMA_BIT_MASK(32))
1691                         && !pci_set_consistent_dma_mask(pdev,
1692                                                 DMA_BIT_MASK(32))) {
1693                         ioc->dma_mask = DMA_BIT_MASK(32);
1694                         dinitprintk(ioc, printk(MYIOC_s_INFO_FMT
1695                                 ": 32 BIT PCI BUS DMA ADDRESSING SUPPORTED\n",
1696                                 ioc->name));
1697                 } else {
1698                         printk(MYIOC_s_WARN_FMT "no suitable DMA mask for %s\n",
1699                             ioc->name, pci_name(pdev));
1700                         goto out_pci_release_region;
1701                 }
1702         }
1703 
1704         mem_phys = msize = 0;
1705         port = psize = 0;
1706         for (ii = 0; ii < DEVICE_COUNT_RESOURCE; ii++) {
1707                 if (pci_resource_flags(pdev, ii) & PCI_BASE_ADDRESS_SPACE_IO) {
1708                         if (psize)
1709                                 continue;
1710                         /* Get I/O space! */
1711                         port = pci_resource_start(pdev, ii);
1712                         psize = pci_resource_len(pdev, ii);
1713                 } else {
1714                         if (msize)
1715                                 continue;
1716                         /* Get memmap */
1717                         mem_phys = pci_resource_start(pdev, ii);
1718                         msize = pci_resource_len(pdev, ii);
1719                 }
1720         }
1721         ioc->mem_size = msize;
1722 
1723         mem = NULL;
1724         /* Get logical ptr for PciMem0 space */
1725         /*mem = ioremap(mem_phys, msize);*/
1726         mem = ioremap(mem_phys, msize);
1727         if (mem == NULL) {
1728                 printk(MYIOC_s_ERR_FMT ": ERROR - Unable to map adapter"
1729                         " memory!\n", ioc->name);
1730                 r = -EINVAL;
1731                 goto out_pci_release_region;
1732         }
1733         ioc->memmap = mem;
1734         dinitprintk(ioc, printk(MYIOC_s_INFO_FMT "mem = %p, mem_phys = %llx\n",
1735             ioc->name, mem, (unsigned long long)mem_phys));
1736 
1737         ioc->mem_phys = mem_phys;
1738         ioc->chip = (SYSIF_REGS __iomem *)mem;
1739 
1740         /* Save Port IO values in case we need to do downloadboot */
1741         ioc->pio_mem_phys = port;
1742         ioc->pio_chip = (SYSIF_REGS __iomem *)port;
1743 
1744         return 0;
1745 
1746 out_pci_release_region:
1747         pci_release_selected_regions(pdev, ioc->bars);
1748 out_pci_disable_device:
1749         pci_disable_device(pdev);
1750         return r;
1751 }
1752 
1753 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
1754 /**
1755  *      mpt_attach - Install a PCI intelligent MPT adapter.
1756  *      @pdev: Pointer to pci_dev structure
1757  *      @id: PCI device ID information
1758  *
1759  *      This routine performs all the steps necessary to bring the IOC of
1760  *      a MPT adapter to a OPERATIONAL state.  This includes registering
1761  *      memory regions, registering the interrupt, and allocating request
1762  *      and reply memory pools.
1763  *
1764  *      This routine also pre-fetches the LAN MAC address of a Fibre Channel
1765  *      MPT adapter.
1766  *
1767  *      Returns 0 for success, non-zero for failure.
1768  *
1769  *      TODO: Add support for polled controllers
1770  */
1771 int
1772 mpt_attach(struct pci_dev *pdev, const struct pci_device_id *id)
1773 {
1774         MPT_ADAPTER     *ioc;
1775         u8               cb_idx;
1776         int              r = -ENODEV;
1777         u8               pcixcmd;
1778         static int       mpt_ids = 0;
1779 #ifdef CONFIG_PROC_FS
1780         struct proc_dir_entry *dent;
1781 #endif
1782 
1783         ioc = kzalloc(sizeof(MPT_ADAPTER), GFP_KERNEL);
1784         if (ioc == NULL) {
1785                 printk(KERN_ERR MYNAM ": ERROR - Insufficient memory to add adapter!\n");
1786                 return -ENOMEM;
1787         }
1788 
1789         ioc->id = mpt_ids++;
1790         sprintf(ioc->name, "ioc%d", ioc->id);
1791         dinitprintk(ioc, printk(KERN_WARNING MYNAM ": mpt_adapter_install\n"));
1792 
1793         /*
1794          * set initial debug level
1795          * (refer to mptdebug.h)
1796          *
1797          */
1798         ioc->debug_level = mpt_debug_level;
1799         if (mpt_debug_level)
1800                 printk(KERN_INFO "mpt_debug_level=%xh\n", mpt_debug_level);
1801 
1802         dinitprintk(ioc, printk(MYIOC_s_INFO_FMT ": mpt_adapter_install\n", ioc->name));
1803 
1804         ioc->pcidev = pdev;
1805         if (mpt_mapresources(ioc)) {
1806                 goto out_free_ioc;
1807         }
1808 
1809         /*
1810          * Setting up proper handlers for scatter gather handling
1811          */
1812         if (ioc->dma_mask == DMA_BIT_MASK(64)) {
1813                 if (pdev->device == MPI_MANUFACTPAGE_DEVID_SAS1078)
1814                         ioc->add_sge = &mpt_add_sge_64bit_1078;
1815                 else
1816                         ioc->add_sge = &mpt_add_sge_64bit;
1817                 ioc->add_chain = &mpt_add_chain_64bit;
1818                 ioc->sg_addr_size = 8;
1819         } else {
1820                 ioc->add_sge = &mpt_add_sge;
1821                 ioc->add_chain = &mpt_add_chain;
1822                 ioc->sg_addr_size = 4;
1823         }
1824         ioc->SGE_size = sizeof(u32) + ioc->sg_addr_size;
1825 
1826         ioc->alloc_total = sizeof(MPT_ADAPTER);
1827         ioc->req_sz = MPT_DEFAULT_FRAME_SIZE;           /* avoid div by zero! */
1828         ioc->reply_sz = MPT_REPLY_FRAME_SIZE;
1829 
1830 
1831         spin_lock_init(&ioc->taskmgmt_lock);
1832         mutex_init(&ioc->internal_cmds.mutex);
1833         init_completion(&ioc->internal_cmds.done);
1834         mutex_init(&ioc->mptbase_cmds.mutex);
1835         init_completion(&ioc->mptbase_cmds.done);
1836         mutex_init(&ioc->taskmgmt_cmds.mutex);
1837         init_completion(&ioc->taskmgmt_cmds.done);
1838 
1839         /* Initialize the event logging.
1840          */
1841         ioc->eventTypes = 0;    /* None */
1842         ioc->eventContext = 0;
1843         ioc->eventLogSize = 0;
1844         ioc->events = NULL;
1845 
1846 #ifdef MFCNT
1847         ioc->mfcnt = 0;
1848 #endif
1849 
1850         ioc->sh = NULL;
1851         ioc->cached_fw = NULL;
1852 
1853         /* Initialize SCSI Config Data structure
1854          */
1855         memset(&ioc->spi_data, 0, sizeof(SpiCfgData));
1856 
1857         /* Initialize the fc rport list head.
1858          */
1859         INIT_LIST_HEAD(&ioc->fc_rports);
1860 
1861         /* Find lookup slot. */
1862         INIT_LIST_HEAD(&ioc->list);
1863 
1864 
1865         /* Initialize workqueue */
1866         INIT_DELAYED_WORK(&ioc->fault_reset_work, mpt_fault_reset_work);
1867 
1868         snprintf(ioc->reset_work_q_name, MPT_KOBJ_NAME_LEN,
1869                  "mpt_poll_%d", ioc->id);
1870         ioc->reset_work_q = alloc_workqueue(ioc->reset_work_q_name,
1871                                             WQ_MEM_RECLAIM, 0);
1872         if (!ioc->reset_work_q) {
1873                 printk(MYIOC_s_ERR_FMT "Insufficient memory to add adapter!\n",
1874                     ioc->name);
1875                 r = -ENOMEM;
1876                 goto out_unmap_resources;
1877         }
1878 
1879         dinitprintk(ioc, printk(MYIOC_s_INFO_FMT "facts @ %p, pfacts[0] @ %p\n",
1880             ioc->name, &ioc->facts, &ioc->pfacts[0]));
1881 
1882         ioc->prod_name = mpt_get_product_name(pdev->vendor, pdev->device,
1883                                               pdev->revision);
1884 
1885         switch (pdev->device)
1886         {
1887         case MPI_MANUFACTPAGE_DEVICEID_FC939X:
1888         case MPI_MANUFACTPAGE_DEVICEID_FC949X:
1889                 ioc->errata_flag_1064 = 1;
1890                 /* fall through */
1891         case MPI_MANUFACTPAGE_DEVICEID_FC909:
1892         case MPI_MANUFACTPAGE_DEVICEID_FC929:
1893         case MPI_MANUFACTPAGE_DEVICEID_FC919:
1894         case MPI_MANUFACTPAGE_DEVICEID_FC949E:
1895                 ioc->bus_type = FC;
1896                 break;
1897 
1898         case MPI_MANUFACTPAGE_DEVICEID_FC929X:
1899                 if (pdev->revision < XL_929) {
1900                         /* 929X Chip Fix. Set Split transactions level
1901                         * for PCIX. Set MOST bits to zero.
1902                         */
1903                         pci_read_config_byte(pdev, 0x6a, &pcixcmd);
1904                         pcixcmd &= 0x8F;
1905                         pci_write_config_byte(pdev, 0x6a, pcixcmd);
1906                 } else {
1907                         /* 929XL Chip Fix. Set MMRBC to 0x08.
1908                         */
1909                         pci_read_config_byte(pdev, 0x6a, &pcixcmd);
1910                         pcixcmd |= 0x08;
1911                         pci_write_config_byte(pdev, 0x6a, pcixcmd);
1912                 }
1913                 ioc->bus_type = FC;
1914                 break;
1915 
1916         case MPI_MANUFACTPAGE_DEVICEID_FC919X:
1917                 /* 919X Chip Fix. Set Split transactions level
1918                  * for PCIX. Set MOST bits to zero.
1919                  */
1920                 pci_read_config_byte(pdev, 0x6a, &pcixcmd);
1921                 pcixcmd &= 0x8F;
1922                 pci_write_config_byte(pdev, 0x6a, pcixcmd);
1923                 ioc->bus_type = FC;
1924                 break;
1925 
1926         case MPI_MANUFACTPAGE_DEVID_53C1030:
1927                 /* 1030 Chip Fix. Disable Split transactions
1928                  * for PCIX. Set MOST bits to zero if Rev < C0( = 8).
1929                  */
1930                 if (pdev->revision < C0_1030) {
1931                         pci_read_config_byte(pdev, 0x6a, &pcixcmd);
1932                         pcixcmd &= 0x8F;
1933                         pci_write_config_byte(pdev, 0x6a, pcixcmd);
1934                 }
1935                 /* fall through */
1936 
1937         case MPI_MANUFACTPAGE_DEVID_1030_53C1035:
1938                 ioc->bus_type = SPI;
1939                 break;
1940 
1941         case MPI_MANUFACTPAGE_DEVID_SAS1064:
1942         case MPI_MANUFACTPAGE_DEVID_SAS1068:
1943                 ioc->errata_flag_1064 = 1;
1944                 ioc->bus_type = SAS;
1945                 break;
1946 
1947         case MPI_MANUFACTPAGE_DEVID_SAS1064E:
1948         case MPI_MANUFACTPAGE_DEVID_SAS1068E:
1949         case MPI_MANUFACTPAGE_DEVID_SAS1078:
1950                 ioc->bus_type = SAS;
1951                 break;
1952         }
1953 
1954 
1955         switch (ioc->bus_type) {
1956 
1957         case SAS:
1958                 ioc->msi_enable = mpt_msi_enable_sas;
1959                 break;
1960 
1961         case SPI:
1962                 ioc->msi_enable = mpt_msi_enable_spi;
1963                 break;
1964 
1965         case FC:
1966                 ioc->msi_enable = mpt_msi_enable_fc;
1967                 break;
1968 
1969         default:
1970                 ioc->msi_enable = 0;
1971                 break;
1972         }
1973 
1974         ioc->fw_events_off = 1;
1975 
1976         if (ioc->errata_flag_1064)
1977                 pci_disable_io_access(pdev);
1978 
1979         spin_lock_init(&ioc->FreeQlock);
1980 
1981         /* Disable all! */
1982         CHIPREG_WRITE32(&ioc->chip->IntMask, 0xFFFFFFFF);
1983         ioc->active = 0;
1984         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
1985 
1986         /* Set IOC ptr in the pcidev's driver data. */
1987         pci_set_drvdata(ioc->pcidev, ioc);
1988 
1989         /* Set lookup ptr. */
1990         list_add_tail(&ioc->list, &ioc_list);
1991 
1992         /* Check for "bound ports" (929, 929X, 1030, 1035) to reduce redundant resets.
1993          */
1994         mpt_detect_bound_ports(ioc, pdev);
1995 
1996         INIT_LIST_HEAD(&ioc->fw_event_list);
1997         spin_lock_init(&ioc->fw_event_lock);
1998         snprintf(ioc->fw_event_q_name, MPT_KOBJ_NAME_LEN, "mpt/%d", ioc->id);
1999         ioc->fw_event_q = alloc_workqueue(ioc->fw_event_q_name,
2000                                           WQ_MEM_RECLAIM, 0);
2001         if (!ioc->fw_event_q) {
2002                 printk(MYIOC_s_ERR_FMT "Insufficient memory to add adapter!\n",
2003                     ioc->name);
2004                 r = -ENOMEM;
2005                 goto out_remove_ioc;
2006         }
2007 
2008         if ((r = mpt_do_ioc_recovery(ioc, MPT_HOSTEVENT_IOC_BRINGUP,
2009             CAN_SLEEP)) != 0){
2010                 printk(MYIOC_s_ERR_FMT "didn't initialize properly! (%d)\n",
2011                     ioc->name, r);
2012 
2013                 destroy_workqueue(ioc->fw_event_q);
2014                 ioc->fw_event_q = NULL;
2015 
2016                 list_del(&ioc->list);
2017                 if (ioc->alt_ioc)
2018                         ioc->alt_ioc->alt_ioc = NULL;
2019                 iounmap(ioc->memmap);
2020                 if (pci_is_enabled(pdev))
2021                         pci_disable_device(pdev);
2022                 if (r != -5)
2023                         pci_release_selected_regions(pdev, ioc->bars);
2024 
2025                 destroy_workqueue(ioc->reset_work_q);
2026                 ioc->reset_work_q = NULL;
2027 
2028                 kfree(ioc);
2029                 return r;
2030         }
2031 
2032         /* call per device driver probe entry point */
2033         for(cb_idx = 0; cb_idx < MPT_MAX_PROTOCOL_DRIVERS; cb_idx++) {
2034                 if(MptDeviceDriverHandlers[cb_idx] &&
2035                   MptDeviceDriverHandlers[cb_idx]->probe) {
2036                         MptDeviceDriverHandlers[cb_idx]->probe(pdev,id);
2037                 }
2038         }
2039 
2040 #ifdef CONFIG_PROC_FS
2041         /*
2042          *  Create "/proc/mpt/iocN" subdirectory entry for each MPT adapter.
2043          */
2044         dent = proc_mkdir(ioc->name, mpt_proc_root_dir);
2045         if (dent) {
2046                 proc_create_single_data("info", S_IRUGO, dent,
2047                                 mpt_iocinfo_proc_show, ioc);
2048                 proc_create_single_data("summary", S_IRUGO, dent,
2049                                 mpt_summary_proc_show, ioc);
2050         }
2051 #endif
2052 
2053         if (!ioc->alt_ioc)
2054                 queue_delayed_work(ioc->reset_work_q, &ioc->fault_reset_work,
2055                         msecs_to_jiffies(MPT_POLLING_INTERVAL));
2056 
2057         return 0;
2058 
2059 out_remove_ioc:
2060         list_del(&ioc->list);
2061         if (ioc->alt_ioc)
2062                 ioc->alt_ioc->alt_ioc = NULL;
2063 
2064         destroy_workqueue(ioc->reset_work_q);
2065         ioc->reset_work_q = NULL;
2066 
2067 out_unmap_resources:
2068         iounmap(ioc->memmap);
2069         pci_disable_device(pdev);
2070         pci_release_selected_regions(pdev, ioc->bars);
2071 
2072 out_free_ioc:
2073         kfree(ioc);
2074 
2075         return r;
2076 }
2077 
2078 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
2079 /**
2080  *      mpt_detach - Remove a PCI intelligent MPT adapter.
2081  *      @pdev: Pointer to pci_dev structure
2082  */
2083 
2084 void
2085 mpt_detach(struct pci_dev *pdev)
2086 {
2087         MPT_ADAPTER     *ioc = pci_get_drvdata(pdev);
2088         char pname[64];
2089         u8 cb_idx;
2090         unsigned long flags;
2091         struct workqueue_struct *wq;
2092 
2093         /*
2094          * Stop polling ioc for fault condition
2095          */
2096         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
2097         wq = ioc->reset_work_q;
2098         ioc->reset_work_q = NULL;
2099         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
2100         cancel_delayed_work(&ioc->fault_reset_work);
2101         destroy_workqueue(wq);
2102 
2103         spin_lock_irqsave(&ioc->fw_event_lock, flags);
2104         wq = ioc->fw_event_q;
2105         ioc->fw_event_q = NULL;
2106         spin_unlock_irqrestore(&ioc->fw_event_lock, flags);
2107         destroy_workqueue(wq);
2108 
2109         snprintf(pname, sizeof(pname), MPT_PROCFS_MPTBASEDIR "/%s/summary", ioc->name);
2110         remove_proc_entry(pname, NULL);
2111         snprintf(pname, sizeof(pname), MPT_PROCFS_MPTBASEDIR "/%s/info", ioc->name);
2112         remove_proc_entry(pname, NULL);
2113         snprintf(pname, sizeof(pname), MPT_PROCFS_MPTBASEDIR "/%s", ioc->name);
2114         remove_proc_entry(pname, NULL);
2115 
2116         /* call per device driver remove entry point */
2117         for(cb_idx = 0; cb_idx < MPT_MAX_PROTOCOL_DRIVERS; cb_idx++) {
2118                 if(MptDeviceDriverHandlers[cb_idx] &&
2119                   MptDeviceDriverHandlers[cb_idx]->remove) {
2120                         MptDeviceDriverHandlers[cb_idx]->remove(pdev);
2121                 }
2122         }
2123 
2124         /* Disable interrupts! */
2125         CHIPREG_WRITE32(&ioc->chip->IntMask, 0xFFFFFFFF);
2126 
2127         ioc->active = 0;
2128         synchronize_irq(pdev->irq);
2129 
2130         /* Clear any lingering interrupt */
2131         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
2132 
2133         CHIPREG_READ32(&ioc->chip->IntStatus);
2134 
2135         mpt_adapter_dispose(ioc);
2136 
2137 }
2138 
2139 /**************************************************************************
2140  * Power Management
2141  */
2142 #ifdef CONFIG_PM
2143 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
2144 /**
2145  *      mpt_suspend - Fusion MPT base driver suspend routine.
2146  *      @pdev: Pointer to pci_dev structure
2147  *      @state: new state to enter
2148  */
2149 int
2150 mpt_suspend(struct pci_dev *pdev, pm_message_t state)
2151 {
2152         u32 device_state;
2153         MPT_ADAPTER *ioc = pci_get_drvdata(pdev);
2154 
2155         device_state = pci_choose_state(pdev, state);
2156         printk(MYIOC_s_INFO_FMT "pci-suspend: pdev=0x%p, slot=%s, Entering "
2157             "operating state [D%d]\n", ioc->name, pdev, pci_name(pdev),
2158             device_state);
2159 
2160         /* put ioc into READY_STATE */
2161         if (SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, CAN_SLEEP)) {
2162                 printk(MYIOC_s_ERR_FMT
2163                 "pci-suspend:  IOC msg unit reset failed!\n", ioc->name);
2164         }
2165 
2166         /* disable interrupts */
2167         CHIPREG_WRITE32(&ioc->chip->IntMask, 0xFFFFFFFF);
2168         ioc->active = 0;
2169 
2170         /* Clear any lingering interrupt */
2171         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
2172 
2173         free_irq(ioc->pci_irq, ioc);
2174         if (ioc->msi_enable)
2175                 pci_disable_msi(ioc->pcidev);
2176         ioc->pci_irq = -1;
2177         pci_save_state(pdev);
2178         pci_disable_device(pdev);
2179         pci_release_selected_regions(pdev, ioc->bars);
2180         pci_set_power_state(pdev, device_state);
2181         return 0;
2182 }
2183 
2184 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
2185 /**
2186  *      mpt_resume - Fusion MPT base driver resume routine.
2187  *      @pdev: Pointer to pci_dev structure
2188  */
2189 int
2190 mpt_resume(struct pci_dev *pdev)
2191 {
2192         MPT_ADAPTER *ioc = pci_get_drvdata(pdev);
2193         u32 device_state = pdev->current_state;
2194         int recovery_state;
2195         int err;
2196 
2197         printk(MYIOC_s_INFO_FMT "pci-resume: pdev=0x%p, slot=%s, Previous "
2198             "operating state [D%d]\n", ioc->name, pdev, pci_name(pdev),
2199             device_state);
2200 
2201         pci_set_power_state(pdev, PCI_D0);
2202         pci_enable_wake(pdev, PCI_D0, 0);
2203         pci_restore_state(pdev);
2204         ioc->pcidev = pdev;
2205         err = mpt_mapresources(ioc);
2206         if (err)
2207                 return err;
2208 
2209         if (ioc->dma_mask == DMA_BIT_MASK(64)) {
2210                 if (pdev->device == MPI_MANUFACTPAGE_DEVID_SAS1078)
2211                         ioc->add_sge = &mpt_add_sge_64bit_1078;
2212                 else
2213                         ioc->add_sge = &mpt_add_sge_64bit;
2214                 ioc->add_chain = &mpt_add_chain_64bit;
2215                 ioc->sg_addr_size = 8;
2216         } else {
2217 
2218                 ioc->add_sge = &mpt_add_sge;
2219                 ioc->add_chain = &mpt_add_chain;
2220                 ioc->sg_addr_size = 4;
2221         }
2222         ioc->SGE_size = sizeof(u32) + ioc->sg_addr_size;
2223 
2224         printk(MYIOC_s_INFO_FMT "pci-resume: ioc-state=0x%x,doorbell=0x%x\n",
2225             ioc->name, (mpt_GetIocState(ioc, 1) >> MPI_IOC_STATE_SHIFT),
2226             CHIPREG_READ32(&ioc->chip->Doorbell));
2227 
2228         /*
2229          * Errata workaround for SAS pci express:
2230          * Upon returning to the D0 state, the contents of the doorbell will be
2231          * stale data, and this will incorrectly signal to the host driver that
2232          * the firmware is ready to process mpt commands.   The workaround is
2233          * to issue a diagnostic reset.
2234          */
2235         if (ioc->bus_type == SAS && (pdev->device ==
2236             MPI_MANUFACTPAGE_DEVID_SAS1068E || pdev->device ==
2237             MPI_MANUFACTPAGE_DEVID_SAS1064E)) {
2238                 if (KickStart(ioc, 1, CAN_SLEEP) < 0) {
2239                         printk(MYIOC_s_WARN_FMT "pci-resume: Cannot recover\n",
2240                             ioc->name);
2241                         goto out;
2242                 }
2243         }
2244 
2245         /* bring ioc to operational state */
2246         printk(MYIOC_s_INFO_FMT "Sending mpt_do_ioc_recovery\n", ioc->name);
2247         recovery_state = mpt_do_ioc_recovery(ioc, MPT_HOSTEVENT_IOC_BRINGUP,
2248                                                  CAN_SLEEP);
2249         if (recovery_state != 0)
2250                 printk(MYIOC_s_WARN_FMT "pci-resume: Cannot recover, "
2251                     "error:[%x]\n", ioc->name, recovery_state);
2252         else
2253                 printk(MYIOC_s_INFO_FMT
2254                     "pci-resume: success\n", ioc->name);
2255  out:
2256         return 0;
2257 
2258 }
2259 #endif
2260 
2261 static int
2262 mpt_signal_reset(u8 index, MPT_ADAPTER *ioc, int reset_phase)
2263 {
2264         if ((MptDriverClass[index] == MPTSPI_DRIVER &&
2265              ioc->bus_type != SPI) ||
2266             (MptDriverClass[index] == MPTFC_DRIVER &&
2267              ioc->bus_type != FC) ||
2268             (MptDriverClass[index] == MPTSAS_DRIVER &&
2269              ioc->bus_type != SAS))
2270                 /* make sure we only call the relevant reset handler
2271                  * for the bus */
2272                 return 0;
2273         return (MptResetHandlers[index])(ioc, reset_phase);
2274 }
2275 
2276 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
2277 /**
2278  *      mpt_do_ioc_recovery - Initialize or recover MPT adapter.
2279  *      @ioc: Pointer to MPT adapter structure
2280  *      @reason: Event word / reason
2281  *      @sleepFlag: Use schedule if CAN_SLEEP else use udelay.
2282  *
2283  *      This routine performs all the steps necessary to bring the IOC
2284  *      to a OPERATIONAL state.
2285  *
2286  *      This routine also pre-fetches the LAN MAC address of a Fibre Channel
2287  *      MPT adapter.
2288  *
2289  *      Returns:
2290  *               0 for success
2291  *              -1 if failed to get board READY
2292  *              -2 if READY but IOCFacts Failed
2293  *              -3 if READY but PrimeIOCFifos Failed
2294  *              -4 if READY but IOCInit Failed
2295  *              -5 if failed to enable_device and/or request_selected_regions
2296  *              -6 if failed to upload firmware
2297  */
2298 static int
2299 mpt_do_ioc_recovery(MPT_ADAPTER *ioc, u32 reason, int sleepFlag)
2300 {
2301         int      hard_reset_done = 0;
2302         int      alt_ioc_ready = 0;
2303         int      hard;
2304         int      rc=0;
2305         int      ii;
2306         int      ret = 0;
2307         int      reset_alt_ioc_active = 0;
2308         int      irq_allocated = 0;
2309         u8      *a;
2310 
2311         printk(MYIOC_s_INFO_FMT "Initiating %s\n", ioc->name,
2312             reason == MPT_HOSTEVENT_IOC_BRINGUP ? "bringup" : "recovery");
2313 
2314         /* Disable reply interrupts (also blocks FreeQ) */
2315         CHIPREG_WRITE32(&ioc->chip->IntMask, 0xFFFFFFFF);
2316         ioc->active = 0;
2317 
2318         if (ioc->alt_ioc) {
2319                 if (ioc->alt_ioc->active ||
2320                     reason == MPT_HOSTEVENT_IOC_RECOVER) {
2321                         reset_alt_ioc_active = 1;
2322                         /* Disable alt-IOC's reply interrupts
2323                          *  (and FreeQ) for a bit
2324                          **/
2325                         CHIPREG_WRITE32(&ioc->alt_ioc->chip->IntMask,
2326                                 0xFFFFFFFF);
2327                         ioc->alt_ioc->active = 0;
2328                 }
2329         }
2330 
2331         hard = 1;
2332         if (reason == MPT_HOSTEVENT_IOC_BRINGUP)
2333                 hard = 0;
2334 
2335         if ((hard_reset_done = MakeIocReady(ioc, hard, sleepFlag)) < 0) {
2336                 if (hard_reset_done == -4) {
2337                         printk(MYIOC_s_WARN_FMT "Owned by PEER..skipping!\n",
2338                             ioc->name);
2339 
2340                         if (reset_alt_ioc_active && ioc->alt_ioc) {
2341                                 /* (re)Enable alt-IOC! (reply interrupt, FreeQ) */
2342                                 dprintk(ioc, printk(MYIOC_s_INFO_FMT
2343                                     "alt_ioc reply irq re-enabled\n", ioc->alt_ioc->name));
2344                                 CHIPREG_WRITE32(&ioc->alt_ioc->chip->IntMask, MPI_HIM_DIM);
2345                                 ioc->alt_ioc->active = 1;
2346                         }
2347 
2348                 } else {
2349                         printk(MYIOC_s_WARN_FMT
2350                             "NOT READY WARNING!\n", ioc->name);
2351                 }
2352                 ret = -1;
2353                 goto out;
2354         }
2355 
2356         /* hard_reset_done = 0 if a soft reset was performed
2357          * and 1 if a hard reset was performed.
2358          */
2359         if (hard_reset_done && reset_alt_ioc_active && ioc->alt_ioc) {
2360                 if ((rc = MakeIocReady(ioc->alt_ioc, 0, sleepFlag)) == 0)
2361                         alt_ioc_ready = 1;
2362                 else
2363                         printk(MYIOC_s_WARN_FMT
2364                             ": alt-ioc Not ready WARNING!\n",
2365                             ioc->alt_ioc->name);
2366         }
2367 
2368         for (ii=0; ii<5; ii++) {
2369                 /* Get IOC facts! Allow 5 retries */
2370                 if ((rc = GetIocFacts(ioc, sleepFlag, reason)) == 0)
2371                         break;
2372         }
2373 
2374 
2375         if (ii == 5) {
2376                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT
2377                     "Retry IocFacts failed rc=%x\n", ioc->name, rc));
2378                 ret = -2;
2379         } else if (reason == MPT_HOSTEVENT_IOC_BRINGUP) {
2380                 MptDisplayIocCapabilities(ioc);
2381         }
2382 
2383         if (alt_ioc_ready) {
2384                 if ((rc = GetIocFacts(ioc->alt_ioc, sleepFlag, reason)) != 0) {
2385                         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT
2386                             "Initial Alt IocFacts failed rc=%x\n",
2387                             ioc->name, rc));
2388                         /* Retry - alt IOC was initialized once
2389                          */
2390                         rc = GetIocFacts(ioc->alt_ioc, sleepFlag, reason);
2391                 }
2392                 if (rc) {
2393                         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT
2394                             "Retry Alt IocFacts failed rc=%x\n", ioc->name, rc));
2395                         alt_ioc_ready = 0;
2396                         reset_alt_ioc_active = 0;
2397                 } else if (reason == MPT_HOSTEVENT_IOC_BRINGUP) {
2398                         MptDisplayIocCapabilities(ioc->alt_ioc);
2399                 }
2400         }
2401 
2402         if ((ret == 0) && (reason == MPT_HOSTEVENT_IOC_BRINGUP) &&
2403             (ioc->facts.Flags & MPI_IOCFACTS_FLAGS_FW_DOWNLOAD_BOOT)) {
2404                 pci_release_selected_regions(ioc->pcidev, ioc->bars);
2405                 ioc->bars = pci_select_bars(ioc->pcidev, IORESOURCE_MEM |
2406                     IORESOURCE_IO);
2407                 if (pci_enable_device(ioc->pcidev))
2408                         return -5;
2409                 if (pci_request_selected_regions(ioc->pcidev, ioc->bars,
2410                         "mpt"))
2411                         return -5;
2412         }
2413 
2414         /*
2415          * Device is reset now. It must have de-asserted the interrupt line
2416          * (if it was asserted) and it should be safe to register for the
2417          * interrupt now.
2418          */
2419         if ((ret == 0) && (reason == MPT_HOSTEVENT_IOC_BRINGUP)) {
2420                 ioc->pci_irq = -1;
2421                 if (ioc->pcidev->irq) {
2422                         if (ioc->msi_enable && !pci_enable_msi(ioc->pcidev))
2423                                 printk(MYIOC_s_INFO_FMT "PCI-MSI enabled\n",
2424                                     ioc->name);
2425                         else
2426                                 ioc->msi_enable = 0;
2427                         rc = request_irq(ioc->pcidev->irq, mpt_interrupt,
2428                             IRQF_SHARED, ioc->name, ioc);
2429                         if (rc < 0) {
2430                                 printk(MYIOC_s_ERR_FMT "Unable to allocate "
2431                                     "interrupt %d!\n",
2432                                     ioc->name, ioc->pcidev->irq);
2433                                 if (ioc->msi_enable)
2434                                         pci_disable_msi(ioc->pcidev);
2435                                 ret = -EBUSY;
2436                                 goto out;
2437                         }
2438                         irq_allocated = 1;
2439                         ioc->pci_irq = ioc->pcidev->irq;
2440                         pci_set_master(ioc->pcidev);            /* ?? */
2441                         pci_set_drvdata(ioc->pcidev, ioc);
2442                         dinitprintk(ioc, printk(MYIOC_s_INFO_FMT
2443                             "installed at interrupt %d\n", ioc->name,
2444                             ioc->pcidev->irq));
2445                 }
2446         }
2447 
2448         /* Prime reply & request queues!
2449          * (mucho alloc's) Must be done prior to
2450          * init as upper addresses are needed for init.
2451          * If fails, continue with alt-ioc processing
2452          */
2453         dinitprintk(ioc, printk(MYIOC_s_INFO_FMT "PrimeIocFifos\n",
2454             ioc->name));
2455         if ((ret == 0) && ((rc = PrimeIocFifos(ioc)) != 0))
2456                 ret = -3;
2457 
2458         /* May need to check/upload firmware & data here!
2459          * If fails, continue with alt-ioc processing
2460          */
2461         dinitprintk(ioc, printk(MYIOC_s_INFO_FMT "SendIocInit\n",
2462             ioc->name));
2463         if ((ret == 0) && ((rc = SendIocInit(ioc, sleepFlag)) != 0))
2464                 ret = -4;
2465 // NEW!
2466         if (alt_ioc_ready && ((rc = PrimeIocFifos(ioc->alt_ioc)) != 0)) {
2467                 printk(MYIOC_s_WARN_FMT
2468                     ": alt-ioc (%d) FIFO mgmt alloc WARNING!\n",
2469                     ioc->alt_ioc->name, rc);
2470                 alt_ioc_ready = 0;
2471                 reset_alt_ioc_active = 0;
2472         }
2473 
2474         if (alt_ioc_ready) {
2475                 if ((rc = SendIocInit(ioc->alt_ioc, sleepFlag)) != 0) {
2476                         alt_ioc_ready = 0;
2477                         reset_alt_ioc_active = 0;
2478                         printk(MYIOC_s_WARN_FMT
2479                                 ": alt-ioc: (%d) init failure WARNING!\n",
2480                                         ioc->alt_ioc->name, rc);
2481                 }
2482         }
2483 
2484         if (reason == MPT_HOSTEVENT_IOC_BRINGUP){
2485                 if (ioc->upload_fw) {
2486                         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT
2487                             "firmware upload required!\n", ioc->name));
2488 
2489                         /* Controller is not operational, cannot do upload
2490                          */
2491                         if (ret == 0) {
2492                                 rc = mpt_do_upload(ioc, sleepFlag);
2493                                 if (rc == 0) {
2494                                         if (ioc->alt_ioc && ioc->alt_ioc->cached_fw) {
2495                                                 /*
2496                                                  * Maintain only one pointer to FW memory
2497                                                  * so there will not be two attempt to
2498                                                  * downloadboot onboard dual function
2499                                                  * chips (mpt_adapter_disable,
2500                                                  * mpt_diag_reset)
2501                                                  */
2502                                                 ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT
2503                                                     "mpt_upload:  alt_%s has cached_fw=%p \n",
2504                                                     ioc->name, ioc->alt_ioc->name, ioc->alt_ioc->cached_fw));
2505                                                 ioc->cached_fw = NULL;
2506                                         }
2507                                 } else {
2508                                         printk(MYIOC_s_WARN_FMT
2509                                             "firmware upload failure!\n", ioc->name);
2510                                         ret = -6;
2511                                 }
2512                         }
2513                 }
2514         }
2515 
2516         /*  Enable MPT base driver management of EventNotification
2517          *  and EventAck handling.
2518          */
2519         if ((ret == 0) && (!ioc->facts.EventState)) {
2520                 dinitprintk(ioc, printk(MYIOC_s_INFO_FMT
2521                         "SendEventNotification\n",
2522                     ioc->name));
2523                 ret = SendEventNotification(ioc, 1, sleepFlag); /* 1=Enable */
2524         }
2525 
2526         if (ioc->alt_ioc && alt_ioc_ready && !ioc->alt_ioc->facts.EventState)
2527                 rc = SendEventNotification(ioc->alt_ioc, 1, sleepFlag);
2528 
2529         if (ret == 0) {
2530                 /* Enable! (reply interrupt) */
2531                 CHIPREG_WRITE32(&ioc->chip->IntMask, MPI_HIM_DIM);
2532                 ioc->active = 1;
2533         }
2534         if (rc == 0) {  /* alt ioc */
2535                 if (reset_alt_ioc_active && ioc->alt_ioc) {
2536                         /* (re)Enable alt-IOC! (reply interrupt) */
2537                         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "alt-ioc"
2538                                 "reply irq re-enabled\n",
2539                                 ioc->alt_ioc->name));
2540                         CHIPREG_WRITE32(&ioc->alt_ioc->chip->IntMask,
2541                                 MPI_HIM_DIM);
2542                         ioc->alt_ioc->active = 1;
2543                 }
2544         }
2545 
2546 
2547         /*      Add additional "reason" check before call to GetLanConfigPages
2548          *      (combined with GetIoUnitPage2 call).  This prevents a somewhat
2549          *      recursive scenario; GetLanConfigPages times out, timer expired
2550          *      routine calls HardResetHandler, which calls into here again,
2551          *      and we try GetLanConfigPages again...
2552          */
2553         if ((ret == 0) && (reason == MPT_HOSTEVENT_IOC_BRINGUP)) {
2554 
2555                 /*
2556                  * Initialize link list for inactive raid volumes.
2557                  */
2558                 mutex_init(&ioc->raid_data.inactive_list_mutex);
2559                 INIT_LIST_HEAD(&ioc->raid_data.inactive_list);
2560 
2561                 switch (ioc->bus_type) {
2562 
2563                 case SAS:
2564                         /* clear persistency table */
2565                         if(ioc->facts.IOCExceptions &
2566                             MPI_IOCFACTS_EXCEPT_PERSISTENT_TABLE_FULL) {
2567                                 ret = mptbase_sas_persist_operation(ioc,
2568                                     MPI_SAS_OP_CLEAR_NOT_PRESENT);
2569                                 if(ret != 0)
2570                                         goto out;
2571                         }
2572 
2573                         /* Find IM volumes
2574                          */
2575                         mpt_findImVolumes(ioc);
2576 
2577                         /* Check, and possibly reset, the coalescing value
2578                          */
2579                         mpt_read_ioc_pg_1(ioc);
2580 
2581                         break;
2582 
2583                 case FC:
2584                         if ((ioc->pfacts[0].ProtocolFlags &
2585                                 MPI_PORTFACTS_PROTOCOL_LAN) &&
2586                             (ioc->lan_cnfg_page0.Header.PageLength == 0)) {
2587                                 /*
2588                                  *  Pre-fetch the ports LAN MAC address!
2589                                  *  (LANPage1_t stuff)
2590                                  */
2591                                 (void) GetLanConfigPages(ioc);
2592                                 a = (u8*)&ioc->lan_cnfg_page1.HardwareAddressLow;
2593                                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT
2594                                         "LanAddr = %pMR\n", ioc->name, a));
2595                         }
2596                         break;
2597 
2598                 case SPI:
2599                         /* Get NVRAM and adapter maximums from SPP 0 and 2
2600                          */
2601                         mpt_GetScsiPortSettings(ioc, 0);
2602 
2603                         /* Get version and length of SDP 1
2604                          */
2605                         mpt_readScsiDevicePageHeaders(ioc, 0);
2606 
2607                         /* Find IM volumes
2608                          */
2609                         if (ioc->facts.MsgVersion >= MPI_VERSION_01_02)
2610                                 mpt_findImVolumes(ioc);
2611 
2612                         /* Check, and possibly reset, the coalescing value
2613                          */
2614                         mpt_read_ioc_pg_1(ioc);
2615 
2616                         mpt_read_ioc_pg_4(ioc);
2617 
2618                         break;
2619                 }
2620 
2621                 GetIoUnitPage2(ioc);
2622                 mpt_get_manufacturing_pg_0(ioc);
2623         }
2624 
2625  out:
2626         if ((ret != 0) && irq_allocated) {
2627                 free_irq(ioc->pci_irq, ioc);
2628                 if (ioc->msi_enable)
2629                         pci_disable_msi(ioc->pcidev);
2630         }
2631         return ret;
2632 }
2633 
2634 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
2635 /**
2636  *      mpt_detect_bound_ports - Search for matching PCI bus/dev_function
2637  *      @ioc: Pointer to MPT adapter structure
2638  *      @pdev: Pointer to (struct pci_dev) structure
2639  *
2640  *      Search for PCI bus/dev_function which matches
2641  *      PCI bus/dev_function (+/-1) for newly discovered 929,
2642  *      929X, 1030 or 1035.
2643  *
2644  *      If match on PCI dev_function +/-1 is found, bind the two MPT adapters
2645  *      using alt_ioc pointer fields in their %MPT_ADAPTER structures.
2646  */
2647 static void
2648 mpt_detect_bound_ports(MPT_ADAPTER *ioc, struct pci_dev *pdev)
2649 {
2650         struct pci_dev *peer=NULL;
2651         unsigned int slot = PCI_SLOT(pdev->devfn);
2652         unsigned int func = PCI_FUNC(pdev->devfn);
2653         MPT_ADAPTER *ioc_srch;
2654 
2655         dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "PCI device %s devfn=%x/%x,"
2656             " searching for devfn match on %x or %x\n",
2657             ioc->name, pci_name(pdev), pdev->bus->number,
2658             pdev->devfn, func-1, func+1));
2659 
2660         peer = pci_get_slot(pdev->bus, PCI_DEVFN(slot,func-1));
2661         if (!peer) {
2662                 peer = pci_get_slot(pdev->bus, PCI_DEVFN(slot,func+1));
2663                 if (!peer)
2664                         return;
2665         }
2666 
2667         list_for_each_entry(ioc_srch, &ioc_list, list) {
2668                 struct pci_dev *_pcidev = ioc_srch->pcidev;
2669                 if (_pcidev == peer) {
2670                         /* Paranoia checks */
2671                         if (ioc->alt_ioc != NULL) {
2672                                 printk(MYIOC_s_WARN_FMT
2673                                     "Oops, already bound (%s <==> %s)!\n",
2674                                     ioc->name, ioc->name, ioc->alt_ioc->name);
2675                                 break;
2676                         } else if (ioc_srch->alt_ioc != NULL) {
2677                                 printk(MYIOC_s_WARN_FMT
2678                                     "Oops, already bound (%s <==> %s)!\n",
2679                                     ioc_srch->name, ioc_srch->name,
2680                                     ioc_srch->alt_ioc->name);
2681                                 break;
2682                         }
2683                         dprintk(ioc, printk(MYIOC_s_DEBUG_FMT
2684                                 "FOUND! binding %s <==> %s\n",
2685                                 ioc->name, ioc->name, ioc_srch->name));
2686                         ioc_srch->alt_ioc = ioc;
2687                         ioc->alt_ioc = ioc_srch;
2688                 }
2689         }
2690         pci_dev_put(peer);
2691 }
2692 
2693 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
2694 /**
2695  *      mpt_adapter_disable - Disable misbehaving MPT adapter.
2696  *      @ioc: Pointer to MPT adapter structure
2697  */
2698 static void
2699 mpt_adapter_disable(MPT_ADAPTER *ioc)
2700 {
2701         int sz;
2702         int ret;
2703 
2704         if (ioc->cached_fw != NULL) {
2705                 ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT
2706                         "%s: Pushing FW onto adapter\n", __func__, ioc->name));
2707                 if ((ret = mpt_downloadboot(ioc, (MpiFwHeader_t *)
2708                     ioc->cached_fw, CAN_SLEEP)) < 0) {
2709                         printk(MYIOC_s_WARN_FMT
2710                             ": firmware downloadboot failure (%d)!\n",
2711                             ioc->name, ret);
2712                 }
2713         }
2714 
2715         /*
2716          * Put the controller into ready state (if its not already)
2717          */
2718         if (mpt_GetIocState(ioc, 1) != MPI_IOC_STATE_READY) {
2719                 if (!SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET,
2720                     CAN_SLEEP)) {
2721                         if (mpt_GetIocState(ioc, 1) != MPI_IOC_STATE_READY)
2722                                 printk(MYIOC_s_ERR_FMT "%s:  IOC msg unit "
2723                                     "reset failed to put ioc in ready state!\n",
2724                                     ioc->name, __func__);
2725                 } else
2726                         printk(MYIOC_s_ERR_FMT "%s:  IOC msg unit reset "
2727                             "failed!\n", ioc->name, __func__);
2728         }
2729 
2730 
2731         /* Disable adapter interrupts! */
2732         synchronize_irq(ioc->pcidev->irq);
2733         CHIPREG_WRITE32(&ioc->chip->IntMask, 0xFFFFFFFF);
2734         ioc->active = 0;
2735 
2736         /* Clear any lingering interrupt */
2737         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
2738         CHIPREG_READ32(&ioc->chip->IntStatus);
2739 
2740         if (ioc->alloc != NULL) {
2741                 sz = ioc->alloc_sz;
2742                 dexitprintk(ioc, printk(MYIOC_s_INFO_FMT "free  @ %p, sz=%d bytes\n",
2743                     ioc->name, ioc->alloc, ioc->alloc_sz));
2744                 pci_free_consistent(ioc->pcidev, sz,
2745                                 ioc->alloc, ioc->alloc_dma);
2746                 ioc->reply_frames = NULL;
2747                 ioc->req_frames = NULL;
2748                 ioc->alloc = NULL;
2749                 ioc->alloc_total -= sz;
2750         }
2751 
2752         if (ioc->sense_buf_pool != NULL) {
2753                 sz = (ioc->req_depth * MPT_SENSE_BUFFER_ALLOC);
2754                 pci_free_consistent(ioc->pcidev, sz,
2755                                 ioc->sense_buf_pool, ioc->sense_buf_pool_dma);
2756                 ioc->sense_buf_pool = NULL;
2757                 ioc->alloc_total -= sz;
2758         }
2759 
2760         if (ioc->events != NULL){
2761                 sz = MPTCTL_EVENT_LOG_SIZE * sizeof(MPT_IOCTL_EVENTS);
2762                 kfree(ioc->events);
2763                 ioc->events = NULL;
2764                 ioc->alloc_total -= sz;
2765         }
2766 
2767         mpt_free_fw_memory(ioc);
2768 
2769         kfree(ioc->spi_data.nvram);
2770         mpt_inactive_raid_list_free(ioc);
2771         kfree(ioc->raid_data.pIocPg2);
2772         kfree(ioc->raid_data.pIocPg3);
2773         ioc->spi_data.nvram = NULL;
2774         ioc->raid_data.pIocPg3 = NULL;
2775 
2776         if (ioc->spi_data.pIocPg4 != NULL) {
2777                 sz = ioc->spi_data.IocPg4Sz;
2778                 pci_free_consistent(ioc->pcidev, sz,
2779                         ioc->spi_data.pIocPg4,
2780                         ioc->spi_data.IocPg4_dma);
2781                 ioc->spi_data.pIocPg4 = NULL;
2782                 ioc->alloc_total -= sz;
2783         }
2784 
2785         if (ioc->ReqToChain != NULL) {
2786                 kfree(ioc->ReqToChain);
2787                 kfree(ioc->RequestNB);
2788                 ioc->ReqToChain = NULL;
2789         }
2790 
2791         kfree(ioc->ChainToChain);
2792         ioc->ChainToChain = NULL;
2793 
2794         if (ioc->HostPageBuffer != NULL) {
2795                 if((ret = mpt_host_page_access_control(ioc,
2796                     MPI_DB_HPBAC_FREE_BUFFER, NO_SLEEP)) != 0) {
2797                         printk(MYIOC_s_ERR_FMT
2798                            ": %s: host page buffers free failed (%d)!\n",
2799                             ioc->name, __func__, ret);
2800                 }
2801                 dexitprintk(ioc, printk(MYIOC_s_DEBUG_FMT
2802                         "HostPageBuffer free  @ %p, sz=%d bytes\n",
2803                         ioc->name, ioc->HostPageBuffer,
2804                         ioc->HostPageBuffer_sz));
2805                 pci_free_consistent(ioc->pcidev, ioc->HostPageBuffer_sz,
2806                     ioc->HostPageBuffer, ioc->HostPageBuffer_dma);
2807                 ioc->HostPageBuffer = NULL;
2808                 ioc->HostPageBuffer_sz = 0;
2809                 ioc->alloc_total -= ioc->HostPageBuffer_sz;
2810         }
2811 
2812         pci_set_drvdata(ioc->pcidev, NULL);
2813 }
2814 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
2815 /**
2816  *      mpt_adapter_dispose - Free all resources associated with an MPT adapter
2817  *      @ioc: Pointer to MPT adapter structure
2818  *
2819  *      This routine unregisters h/w resources and frees all alloc'd memory
2820  *      associated with a MPT adapter structure.
2821  */
2822 static void
2823 mpt_adapter_dispose(MPT_ADAPTER *ioc)
2824 {
2825         int sz_first, sz_last;
2826 
2827         if (ioc == NULL)
2828                 return;
2829 
2830         sz_first = ioc->alloc_total;
2831 
2832         mpt_adapter_disable(ioc);
2833 
2834         if (ioc->pci_irq != -1) {
2835                 free_irq(ioc->pci_irq, ioc);
2836                 if (ioc->msi_enable)
2837                         pci_disable_msi(ioc->pcidev);
2838                 ioc->pci_irq = -1;
2839         }
2840 
2841         if (ioc->memmap != NULL) {
2842                 iounmap(ioc->memmap);
2843                 ioc->memmap = NULL;
2844         }
2845 
2846         pci_disable_device(ioc->pcidev);
2847         pci_release_selected_regions(ioc->pcidev, ioc->bars);
2848 
2849         /*  Zap the adapter lookup ptr!  */
2850         list_del(&ioc->list);
2851 
2852         sz_last = ioc->alloc_total;
2853         dprintk(ioc, printk(MYIOC_s_INFO_FMT "free'd %d of %d bytes\n",
2854             ioc->name, sz_first-sz_last+(int)sizeof(*ioc), sz_first));
2855 
2856         if (ioc->alt_ioc)
2857                 ioc->alt_ioc->alt_ioc = NULL;
2858 
2859         kfree(ioc);
2860 }
2861 
2862 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
2863 /**
2864  *      MptDisplayIocCapabilities - Disply IOC's capabilities.
2865  *      @ioc: Pointer to MPT adapter structure
2866  */
2867 static void
2868 MptDisplayIocCapabilities(MPT_ADAPTER *ioc)
2869 {
2870         int i = 0;
2871 
2872         printk(KERN_INFO "%s: ", ioc->name);
2873         if (ioc->prod_name)
2874                 pr_cont("%s: ", ioc->prod_name);
2875         pr_cont("Capabilities={");
2876 
2877         if (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_INITIATOR) {
2878                 pr_cont("Initiator");
2879                 i++;
2880         }
2881 
2882         if (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_TARGET) {
2883                 pr_cont("%sTarget", i ? "," : "");
2884                 i++;
2885         }
2886 
2887         if (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) {
2888                 pr_cont("%sLAN", i ? "," : "");
2889                 i++;
2890         }
2891 
2892 #if 0
2893         /*
2894          *  This would probably evoke more questions than it's worth
2895          */
2896         if (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_TARGET) {
2897                 pr_cont("%sLogBusAddr", i ? "," : "");
2898                 i++;
2899         }
2900 #endif
2901 
2902         pr_cont("}\n");
2903 }
2904 
2905 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
2906 /**
2907  *      MakeIocReady - Get IOC to a READY state, using KickStart if needed.
2908  *      @ioc: Pointer to MPT_ADAPTER structure
2909  *      @force: Force hard KickStart of IOC
2910  *      @sleepFlag: Specifies whether the process can sleep
2911  *
2912  *      Returns:
2913  *               1 - DIAG reset and READY
2914  *               0 - READY initially OR soft reset and READY
2915  *              -1 - Any failure on KickStart
2916  *              -2 - Msg Unit Reset Failed
2917  *              -3 - IO Unit Reset Failed
2918  *              -4 - IOC owned by a PEER
2919  */
2920 static int
2921 MakeIocReady(MPT_ADAPTER *ioc, int force, int sleepFlag)
2922 {
2923         u32      ioc_state;
2924         int      statefault = 0;
2925         int      cntdn;
2926         int      hard_reset_done = 0;
2927         int      r;
2928         int      ii;
2929         int      whoinit;
2930 
2931         /* Get current [raw] IOC state  */
2932         ioc_state = mpt_GetIocState(ioc, 0);
2933         dhsprintk(ioc, printk(MYIOC_s_INFO_FMT "MakeIocReady [raw] state=%08x\n", ioc->name, ioc_state));
2934 
2935         /*
2936          *      Check to see if IOC got left/stuck in doorbell handshake
2937          *      grip of death.  If so, hard reset the IOC.
2938          */
2939         if (ioc_state & MPI_DOORBELL_ACTIVE) {
2940                 statefault = 1;
2941                 printk(MYIOC_s_WARN_FMT "Unexpected doorbell active!\n",
2942                                 ioc->name);
2943         }
2944 
2945         /* Is it already READY? */
2946         if (!statefault &&
2947             ((ioc_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_READY)) {
2948                 dinitprintk(ioc, printk(MYIOC_s_INFO_FMT
2949                     "IOC is in READY state\n", ioc->name));
2950                 return 0;
2951         }
2952 
2953         /*
2954          *      Check to see if IOC is in FAULT state.
2955          */
2956         if ((ioc_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_FAULT) {
2957                 statefault = 2;
2958                 printk(MYIOC_s_WARN_FMT "IOC is in FAULT state!!!\n",
2959                     ioc->name);
2960                 printk(MYIOC_s_WARN_FMT "           FAULT code = %04xh\n",
2961                     ioc->name, ioc_state & MPI_DOORBELL_DATA_MASK);
2962         }
2963 
2964         /*
2965          *      Hmmm...  Did it get left operational?
2966          */
2967         if ((ioc_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_OPERATIONAL) {
2968                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "IOC operational unexpected\n",
2969                                 ioc->name));
2970 
2971                 /* Check WhoInit.
2972                  * If PCI Peer, exit.
2973                  * Else, if no fault conditions are present, issue a MessageUnitReset
2974                  * Else, fall through to KickStart case
2975                  */
2976                 whoinit = (ioc_state & MPI_DOORBELL_WHO_INIT_MASK) >> MPI_DOORBELL_WHO_INIT_SHIFT;
2977                 dinitprintk(ioc, printk(MYIOC_s_INFO_FMT
2978                         "whoinit 0x%x statefault %d force %d\n",
2979                         ioc->name, whoinit, statefault, force));
2980                 if (whoinit == MPI_WHOINIT_PCI_PEER)
2981                         return -4;
2982                 else {
2983                         if ((statefault == 0 ) && (force == 0)) {
2984                                 if ((r = SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, sleepFlag)) == 0)
2985                                         return 0;
2986                         }
2987                         statefault = 3;
2988                 }
2989         }
2990 
2991         hard_reset_done = KickStart(ioc, statefault||force, sleepFlag);
2992         if (hard_reset_done < 0)
2993                 return -1;
2994 
2995         /*
2996          *  Loop here waiting for IOC to come READY.
2997          */
2998         ii = 0;
2999         cntdn = ((sleepFlag == CAN_SLEEP) ? HZ : 1000) * 5;     /* 5 seconds */
3000 
3001         while ((ioc_state = mpt_GetIocState(ioc, 1)) != MPI_IOC_STATE_READY) {
3002                 if (ioc_state == MPI_IOC_STATE_OPERATIONAL) {
3003                         /*
3004                          *  BIOS or previous driver load left IOC in OP state.
3005                          *  Reset messaging FIFOs.
3006                          */
3007                         if ((r = SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, sleepFlag)) != 0) {
3008                                 printk(MYIOC_s_ERR_FMT "IOC msg unit reset failed!\n", ioc->name);
3009                                 return -2;
3010                         }
3011                 } else if (ioc_state == MPI_IOC_STATE_RESET) {
3012                         /*
3013                          *  Something is wrong.  Try to get IOC back
3014                          *  to a known state.
3015                          */
3016                         if ((r = SendIocReset(ioc, MPI_FUNCTION_IO_UNIT_RESET, sleepFlag)) != 0) {
3017                                 printk(MYIOC_s_ERR_FMT "IO unit reset failed!\n", ioc->name);
3018                                 return -3;
3019                         }
3020                 }
3021 
3022                 ii++; cntdn--;
3023                 if (!cntdn) {
3024                         printk(MYIOC_s_ERR_FMT
3025                                 "Wait IOC_READY state (0x%x) timeout(%d)!\n",
3026                                 ioc->name, ioc_state, (int)((ii+5)/HZ));
3027                         return -ETIME;
3028                 }
3029 
3030                 if (sleepFlag == CAN_SLEEP) {
3031                         msleep(1);
3032                 } else {
3033                         mdelay (1);     /* 1 msec delay */
3034                 }
3035 
3036         }
3037 
3038         if (statefault < 3) {
3039                 printk(MYIOC_s_INFO_FMT "Recovered from %s\n", ioc->name,
3040                         statefault == 1 ? "stuck handshake" : "IOC FAULT");
3041         }
3042 
3043         return hard_reset_done;
3044 }
3045 
3046 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
3047 /**
3048  *      mpt_GetIocState - Get the current state of a MPT adapter.
3049  *      @ioc: Pointer to MPT_ADAPTER structure
3050  *      @cooked: Request raw or cooked IOC state
3051  *
3052  *      Returns all IOC Doorbell register bits if cooked==0, else just the
3053  *      Doorbell bits in MPI_IOC_STATE_MASK.
3054  */
3055 u32
3056 mpt_GetIocState(MPT_ADAPTER *ioc, int cooked)
3057 {
3058         u32 s, sc;
3059 
3060         /*  Get!  */
3061         s = CHIPREG_READ32(&ioc->chip->Doorbell);
3062         sc = s & MPI_IOC_STATE_MASK;
3063 
3064         /*  Save!  */
3065         ioc->last_state = sc;
3066 
3067         return cooked ? sc : s;
3068 }
3069 
3070 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
3071 /**
3072  *      GetIocFacts - Send IOCFacts request to MPT adapter.
3073  *      @ioc: Pointer to MPT_ADAPTER structure
3074  *      @sleepFlag: Specifies whether the process can sleep
3075  *      @reason: If recovery, only update facts.
3076  *
3077  *      Returns 0 for success, non-zero for failure.
3078  */
3079 static int
3080 GetIocFacts(MPT_ADAPTER *ioc, int sleepFlag, int reason)
3081 {
3082         IOCFacts_t               get_facts;
3083         IOCFactsReply_t         *facts;
3084         int                      r;
3085         int                      req_sz;
3086         int                      reply_sz;
3087         int                      sz;
3088         u32                      status, vv;
3089         u8                       shiftFactor=1;
3090 
3091         /* IOC *must* NOT be in RESET state! */
3092         if (ioc->last_state == MPI_IOC_STATE_RESET) {
3093                 printk(KERN_ERR MYNAM
3094                     ": ERROR - Can't get IOCFacts, %s NOT READY! (%08x)\n",
3095                     ioc->name, ioc->last_state);
3096                 return -44;
3097         }
3098 
3099         facts = &ioc->facts;
3100 
3101         /* Destination (reply area)... */
3102         reply_sz = sizeof(*facts);
3103         memset(facts, 0, reply_sz);
3104 
3105         /* Request area (get_facts on the stack right now!) */
3106         req_sz = sizeof(get_facts);
3107         memset(&get_facts, 0, req_sz);
3108 
3109         get_facts.Function = MPI_FUNCTION_IOC_FACTS;
3110         /* Assert: All other get_facts fields are zero! */
3111 
3112         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT
3113             "Sending get IocFacts request req_sz=%d reply_sz=%d\n",
3114             ioc->name, req_sz, reply_sz));
3115 
3116         /* No non-zero fields in the get_facts request are greater than
3117          * 1 byte in size, so we can just fire it off as is.
3118          */
3119         r = mpt_handshake_req_reply_wait(ioc, req_sz, (u32*)&get_facts,
3120                         reply_sz, (u16*)facts, 5 /*seconds*/, sleepFlag);
3121         if (r != 0)
3122                 return r;
3123 
3124         /*
3125          * Now byte swap (GRRR) the necessary fields before any further
3126          * inspection of reply contents.
3127          *
3128          * But need to do some sanity checks on MsgLength (byte) field
3129          * to make sure we don't zero IOC's req_sz!
3130          */
3131         /* Did we get a valid reply? */
3132         if (facts->MsgLength > offsetof(IOCFactsReply_t, RequestFrameSize)/sizeof(u32)) {
3133                 if (reason == MPT_HOSTEVENT_IOC_BRINGUP) {
3134                         /*
3135                          * If not been here, done that, save off first WhoInit value
3136                          */
3137                         if (ioc->FirstWhoInit == WHOINIT_UNKNOWN)
3138                                 ioc->FirstWhoInit = facts->WhoInit;
3139                 }
3140 
3141                 facts->MsgVersion = le16_to_cpu(facts->MsgVersion);
3142                 facts->MsgContext = le32_to_cpu(facts->MsgContext);
3143                 facts->IOCExceptions = le16_to_cpu(facts->IOCExceptions);
3144                 facts->IOCStatus = le16_to_cpu(facts->IOCStatus);
3145                 facts->IOCLogInfo = le32_to_cpu(facts->IOCLogInfo);
3146                 status = le16_to_cpu(facts->IOCStatus) & MPI_IOCSTATUS_MASK;
3147                 /* CHECKME! IOCStatus, IOCLogInfo */
3148 
3149                 facts->ReplyQueueDepth = le16_to_cpu(facts->ReplyQueueDepth);
3150                 facts->RequestFrameSize = le16_to_cpu(facts->RequestFrameSize);
3151 
3152                 /*
3153                  * FC f/w version changed between 1.1 and 1.2
3154                  *      Old: u16{Major(4),Minor(4),SubMinor(8)}
3155                  *      New: u32{Major(8),Minor(8),Unit(8),Dev(8)}
3156                  */
3157                 if (facts->MsgVersion < MPI_VERSION_01_02) {
3158                         /*
3159                          *      Handle old FC f/w style, convert to new...
3160                          */
3161                         u16      oldv = le16_to_cpu(facts->Reserved_0101_FWVersion);
3162                         facts->FWVersion.Word =
3163                                         ((oldv<<12) & 0xFF000000) |
3164                                         ((oldv<<8)  & 0x000FFF00);
3165                 } else
3166                         facts->FWVersion.Word = le32_to_cpu(facts->FWVersion.Word);
3167 
3168                 facts->ProductID = le16_to_cpu(facts->ProductID);
3169 
3170                 if ((ioc->facts.ProductID & MPI_FW_HEADER_PID_PROD_MASK)
3171                     > MPI_FW_HEADER_PID_PROD_TARGET_SCSI)
3172                         ioc->ir_firmware = 1;
3173 
3174                 facts->CurrentHostMfaHighAddr =
3175                                 le32_to_cpu(facts->CurrentHostMfaHighAddr);
3176                 facts->GlobalCredits = le16_to_cpu(facts->GlobalCredits);
3177                 facts->CurrentSenseBufferHighAddr =
3178                                 le32_to_cpu(facts->CurrentSenseBufferHighAddr);
3179                 facts->CurReplyFrameSize =
3180                                 le16_to_cpu(facts->CurReplyFrameSize);
3181                 facts->IOCCapabilities = le32_to_cpu(facts->IOCCapabilities);
3182 
3183                 /*
3184                  * Handle NEW (!) IOCFactsReply fields in MPI-1.01.xx
3185                  * Older MPI-1.00.xx struct had 13 dwords, and enlarged
3186                  * to 14 in MPI-1.01.0x.
3187                  */
3188                 if (facts->MsgLength >= (offsetof(IOCFactsReply_t,FWImageSize) + 7)/4 &&
3189                     facts->MsgVersion > MPI_VERSION_01_00) {
3190                         facts->FWImageSize = le32_to_cpu(facts->FWImageSize);
3191                 }
3192 
3193                 facts->FWImageSize = ALIGN(facts->FWImageSize, 4);
3194 
3195                 if (!facts->RequestFrameSize) {
3196                         /*  Something is wrong!  */
3197                         printk(MYIOC_s_ERR_FMT "IOC reported invalid 0 request size!\n",
3198                                         ioc->name);
3199                         return -55;
3200                 }
3201 
3202                 r = sz = facts->BlockSize;
3203                 vv = ((63 / (sz * 4)) + 1) & 0x03;
3204                 ioc->NB_for_64_byte_frame = vv;
3205                 while ( sz )
3206                 {
3207                         shiftFactor++;
3208                         sz = sz >> 1;
3209                 }
3210                 ioc->NBShiftFactor  = shiftFactor;
3211                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT
3212                     "NB_for_64_byte_frame=%x NBShiftFactor=%x BlockSize=%x\n",
3213                     ioc->name, vv, shiftFactor, r));
3214 
3215                 if (reason == MPT_HOSTEVENT_IOC_BRINGUP) {
3216                         /*
3217                          * Set values for this IOC's request & reply frame sizes,
3218                          * and request & reply queue depths...
3219                          */
3220                         ioc->req_sz = min(MPT_DEFAULT_FRAME_SIZE, facts->RequestFrameSize * 4);
3221                         ioc->req_depth = min_t(int, MPT_MAX_REQ_DEPTH, facts->GlobalCredits);
3222                         ioc->reply_sz = MPT_REPLY_FRAME_SIZE;
3223                         ioc->reply_depth = min_t(int, MPT_DEFAULT_REPLY_DEPTH, facts->ReplyQueueDepth);
3224 
3225                         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "reply_sz=%3d, reply_depth=%4d\n",
3226                                 ioc->name, ioc->reply_sz, ioc->reply_depth));
3227                         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "req_sz  =%3d, req_depth  =%4d\n",
3228                                 ioc->name, ioc->req_sz, ioc->req_depth));
3229 
3230                         /* Get port facts! */
3231                         if ( (r = GetPortFacts(ioc, 0, sleepFlag)) != 0 )
3232                                 return r;
3233                 }
3234         } else {
3235                 printk(MYIOC_s_ERR_FMT
3236                      "Invalid IOC facts reply, msgLength=%d offsetof=%zd!\n",
3237                      ioc->name, facts->MsgLength, (offsetof(IOCFactsReply_t,
3238                      RequestFrameSize)/sizeof(u32)));
3239                 return -66;
3240         }
3241 
3242         return 0;
3243 }
3244 
3245 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
3246 /**
3247  *      GetPortFacts - Send PortFacts request to MPT adapter.
3248  *      @ioc: Pointer to MPT_ADAPTER structure
3249  *      @portnum: Port number
3250  *      @sleepFlag: Specifies whether the process can sleep
3251  *
3252  *      Returns 0 for success, non-zero for failure.
3253  */
3254 static int
3255 GetPortFacts(MPT_ADAPTER *ioc, int portnum, int sleepFlag)
3256 {
3257         PortFacts_t              get_pfacts;
3258         PortFactsReply_t        *pfacts;
3259         int                      ii;
3260         int                      req_sz;
3261         int                      reply_sz;
3262         int                      max_id;
3263 
3264         /* IOC *must* NOT be in RESET state! */
3265         if (ioc->last_state == MPI_IOC_STATE_RESET) {
3266                 printk(MYIOC_s_ERR_FMT "Can't get PortFacts NOT READY! (%08x)\n",
3267                     ioc->name, ioc->last_state );
3268                 return -4;
3269         }
3270 
3271         pfacts = &ioc->pfacts[portnum];
3272 
3273         /* Destination (reply area)...  */
3274         reply_sz = sizeof(*pfacts);
3275         memset(pfacts, 0, reply_sz);
3276 
3277         /* Request area (get_pfacts on the stack right now!) */
3278         req_sz = sizeof(get_pfacts);
3279         memset(&get_pfacts, 0, req_sz);
3280 
3281         get_pfacts.Function = MPI_FUNCTION_PORT_FACTS;
3282         get_pfacts.PortNumber = portnum;
3283         /* Assert: All other get_pfacts fields are zero! */
3284 
3285         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Sending get PortFacts(%d) request\n",
3286                         ioc->name, portnum));
3287 
3288         /* No non-zero fields in the get_pfacts request are greater than
3289          * 1 byte in size, so we can just fire it off as is.
3290          */
3291         ii = mpt_handshake_req_reply_wait(ioc, req_sz, (u32*)&get_pfacts,
3292                                 reply_sz, (u16*)pfacts, 5 /*seconds*/, sleepFlag);
3293         if (ii != 0)
3294                 return ii;
3295 
3296         /* Did we get a valid reply? */
3297 
3298         /* Now byte swap the necessary fields in the response. */
3299         pfacts->MsgContext = le32_to_cpu(pfacts->MsgContext);
3300         pfacts->IOCStatus = le16_to_cpu(pfacts->IOCStatus);
3301         pfacts->IOCLogInfo = le32_to_cpu(pfacts->IOCLogInfo);
3302         pfacts->MaxDevices = le16_to_cpu(pfacts->MaxDevices);
3303         pfacts->PortSCSIID = le16_to_cpu(pfacts->PortSCSIID);
3304         pfacts->ProtocolFlags = le16_to_cpu(pfacts->ProtocolFlags);
3305         pfacts->MaxPostedCmdBuffers = le16_to_cpu(pfacts->MaxPostedCmdBuffers);
3306         pfacts->MaxPersistentIDs = le16_to_cpu(pfacts->MaxPersistentIDs);
3307         pfacts->MaxLanBuckets = le16_to_cpu(pfacts->MaxLanBuckets);
3308 
3309         max_id = (ioc->bus_type == SAS) ? pfacts->PortSCSIID :
3310             pfacts->MaxDevices;
3311         ioc->devices_per_bus = (max_id > 255) ? 256 : max_id;
3312         ioc->number_of_buses = (ioc->devices_per_bus < 256) ? 1 : max_id/256;
3313 
3314         /*
3315          * Place all the devices on channels
3316          *
3317          * (for debuging)
3318          */
3319         if (mpt_channel_mapping) {
3320                 ioc->devices_per_bus = 1;
3321                 ioc->number_of_buses = (max_id > 255) ? 255 : max_id;
3322         }
3323 
3324         return 0;
3325 }
3326 
3327 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
3328 /**
3329  *      SendIocInit - Send IOCInit request to MPT adapter.
3330  *      @ioc: Pointer to MPT_ADAPTER structure
3331  *      @sleepFlag: Specifies whether the process can sleep
3332  *
3333  *      Send IOCInit followed by PortEnable to bring IOC to OPERATIONAL state.
3334  *
3335  *      Returns 0 for success, non-zero for failure.
3336  */
3337 static int
3338 SendIocInit(MPT_ADAPTER *ioc, int sleepFlag)
3339 {
3340         IOCInit_t                ioc_init;
3341         MPIDefaultReply_t        init_reply;
3342         u32                      state;
3343         int                      r;
3344         int                      count;
3345         int                      cntdn;
3346 
3347         memset(&ioc_init, 0, sizeof(ioc_init));
3348         memset(&init_reply, 0, sizeof(init_reply));
3349 
3350         ioc_init.WhoInit = MPI_WHOINIT_HOST_DRIVER;
3351         ioc_init.Function = MPI_FUNCTION_IOC_INIT;
3352 
3353         /* If we are in a recovery mode and we uploaded the FW image,
3354          * then this pointer is not NULL. Skip the upload a second time.
3355          * Set this flag if cached_fw set for either IOC.
3356          */
3357         if (ioc->facts.Flags & MPI_IOCFACTS_FLAGS_FW_DOWNLOAD_BOOT)
3358                 ioc->upload_fw = 1;
3359         else
3360                 ioc->upload_fw = 0;
3361         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "upload_fw %d facts.Flags=%x\n",
3362                    ioc->name, ioc->upload_fw, ioc->facts.Flags));
3363 
3364         ioc_init.MaxDevices = (U8)ioc->devices_per_bus;
3365         ioc_init.MaxBuses = (U8)ioc->number_of_buses;
3366 
3367         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "facts.MsgVersion=%x\n",
3368                    ioc->name, ioc->facts.MsgVersion));
3369         if (ioc->facts.MsgVersion >= MPI_VERSION_01_05) {
3370                 // set MsgVersion and HeaderVersion host driver was built with
3371                 ioc_init.MsgVersion = cpu_to_le16(MPI_VERSION);
3372                 ioc_init.HeaderVersion = cpu_to_le16(MPI_HEADER_VERSION);
3373 
3374                 if (ioc->facts.Flags & MPI_IOCFACTS_FLAGS_HOST_PAGE_BUFFER_PERSISTENT) {
3375                         ioc_init.HostPageBufferSGE = ioc->facts.HostPageBufferSGE;
3376                 } else if(mpt_host_page_alloc(ioc, &ioc_init))
3377                         return -99;
3378         }
3379         ioc_init.ReplyFrameSize = cpu_to_le16(ioc->reply_sz);   /* in BYTES */
3380 
3381         if (ioc->sg_addr_size == sizeof(u64)) {
3382                 /* Save the upper 32-bits of the request
3383                  * (reply) and sense buffers.
3384                  */
3385                 ioc_init.HostMfaHighAddr = cpu_to_le32((u32)((u64)ioc->alloc_dma >> 32));
3386                 ioc_init.SenseBufferHighAddr = cpu_to_le32((u32)((u64)ioc->sense_buf_pool_dma >> 32));
3387         } else {
3388                 /* Force 32-bit addressing */
3389                 ioc_init.HostMfaHighAddr = cpu_to_le32(0);
3390                 ioc_init.SenseBufferHighAddr = cpu_to_le32(0);
3391         }
3392 
3393         ioc->facts.CurrentHostMfaHighAddr = ioc_init.HostMfaHighAddr;
3394         ioc->facts.CurrentSenseBufferHighAddr = ioc_init.SenseBufferHighAddr;
3395         ioc->facts.MaxDevices = ioc_init.MaxDevices;
3396         ioc->facts.MaxBuses = ioc_init.MaxBuses;
3397 
3398         dhsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Sending IOCInit (req @ %p)\n",
3399                         ioc->name, &ioc_init));
3400 
3401         r = mpt_handshake_req_reply_wait(ioc, sizeof(IOCInit_t), (u32*)&ioc_init,
3402                                 sizeof(MPIDefaultReply_t), (u16*)&init_reply, 10 /*seconds*/, sleepFlag);
3403         if (r != 0) {
3404                 printk(MYIOC_s_ERR_FMT "Sending IOCInit failed(%d)!\n",ioc->name, r);
3405                 return r;
3406         }
3407 
3408         /* No need to byte swap the multibyte fields in the reply
3409          * since we don't even look at its contents.
3410          */
3411 
3412         dhsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Sending PortEnable (req @ %p)\n",
3413                         ioc->name, &ioc_init));
3414 
3415         if ((r = SendPortEnable(ioc, 0, sleepFlag)) != 0) {
3416                 printk(MYIOC_s_ERR_FMT "Sending PortEnable failed(%d)!\n",ioc->name, r);
3417                 return r;
3418         }
3419 
3420         /* YIKES!  SUPER IMPORTANT!!!
3421          *  Poll IocState until _OPERATIONAL while IOC is doing
3422          *  LoopInit and TargetDiscovery!
3423          */
3424         count = 0;
3425         cntdn = ((sleepFlag == CAN_SLEEP) ? HZ : 1000) * 60;    /* 60 seconds */
3426         state = mpt_GetIocState(ioc, 1);
3427         while (state != MPI_IOC_STATE_OPERATIONAL && --cntdn) {
3428                 if (sleepFlag == CAN_SLEEP) {
3429                         msleep(1);
3430                 } else {
3431                         mdelay(1);
3432                 }
3433 
3434                 if (!cntdn) {
3435                         printk(MYIOC_s_ERR_FMT "Wait IOC_OP state timeout(%d)!\n",
3436                                         ioc->name, (int)((count+5)/HZ));
3437                         return -9;
3438                 }
3439 
3440                 state = mpt_GetIocState(ioc, 1);
3441                 count++;
3442         }
3443         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Wait IOC_OPERATIONAL state (cnt=%d)\n",
3444                         ioc->name, count));
3445 
3446         ioc->aen_event_read_flag=0;
3447         return r;
3448 }
3449 
3450 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
3451 /**
3452  *      SendPortEnable - Send PortEnable request to MPT adapter port.
3453  *      @ioc: Pointer to MPT_ADAPTER structure
3454  *      @portnum: Port number to enable
3455  *      @sleepFlag: Specifies whether the process can sleep
3456  *
3457  *      Send PortEnable to bring IOC to OPERATIONAL state.
3458  *
3459  *      Returns 0 for success, non-zero for failure.
3460  */
3461 static int
3462 SendPortEnable(MPT_ADAPTER *ioc, int portnum, int sleepFlag)
3463 {
3464         PortEnable_t             port_enable;
3465         MPIDefaultReply_t        reply_buf;
3466         int      rc;
3467         int      req_sz;
3468         int      reply_sz;
3469 
3470         /*  Destination...  */
3471         reply_sz = sizeof(MPIDefaultReply_t);
3472         memset(&reply_buf, 0, reply_sz);
3473 
3474         req_sz = sizeof(PortEnable_t);
3475         memset(&port_enable, 0, req_sz);
3476 
3477         port_enable.Function = MPI_FUNCTION_PORT_ENABLE;
3478         port_enable.PortNumber = portnum;
3479 /*      port_enable.ChainOffset = 0;            */
3480 /*      port_enable.MsgFlags = 0;               */
3481 /*      port_enable.MsgContext = 0;             */
3482 
3483         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Sending Port(%d)Enable (req @ %p)\n",
3484                         ioc->name, portnum, &port_enable));
3485 
3486         /* RAID FW may take a long time to enable
3487          */
3488         if (ioc->ir_firmware || ioc->bus_type == SAS) {
3489                 rc = mpt_handshake_req_reply_wait(ioc, req_sz,
3490                 (u32*)&port_enable, reply_sz, (u16*)&reply_buf,
3491                 300 /*seconds*/, sleepFlag);
3492         } else {
3493                 rc = mpt_handshake_req_reply_wait(ioc, req_sz,
3494                 (u32*)&port_enable, reply_sz, (u16*)&reply_buf,
3495                 30 /*seconds*/, sleepFlag);
3496         }
3497         return rc;
3498 }
3499 
3500 /**
3501  *      mpt_alloc_fw_memory - allocate firmware memory
3502  *      @ioc: Pointer to MPT_ADAPTER structure
3503  *      @size: total FW bytes
3504  *
3505  *      If memory has already been allocated, the same (cached) value
3506  *      is returned.
3507  *
3508  *      Return 0 if successful, or non-zero for failure
3509  **/
3510 int
3511 mpt_alloc_fw_memory(MPT_ADAPTER *ioc, int size)
3512 {
3513         int rc;
3514 
3515         if (ioc->cached_fw) {
3516                 rc = 0;  /* use already allocated memory */
3517                 goto out;
3518         }
3519         else if (ioc->alt_ioc && ioc->alt_ioc->cached_fw) {
3520                 ioc->cached_fw = ioc->alt_ioc->cached_fw;  /* use alt_ioc's memory */
3521                 ioc->cached_fw_dma = ioc->alt_ioc->cached_fw_dma;
3522                 rc = 0;
3523                 goto out;
3524         }
3525         ioc->cached_fw = pci_alloc_consistent(ioc->pcidev, size, &ioc->cached_fw_dma);
3526         if (!ioc->cached_fw) {
3527                 printk(MYIOC_s_ERR_FMT "Unable to allocate memory for the cached firmware image!\n",
3528                     ioc->name);
3529                 rc = -1;
3530         } else {
3531                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "FW Image  @ %p[%p], sz=%d[%x] bytes\n",
3532                     ioc->name, ioc->cached_fw, (void *)(ulong)ioc->cached_fw_dma, size, size));
3533                 ioc->alloc_total += size;
3534                 rc = 0;
3535         }
3536  out:
3537         return rc;
3538 }
3539 
3540 /**
3541  *      mpt_free_fw_memory - free firmware memory
3542  *      @ioc: Pointer to MPT_ADAPTER structure
3543  *
3544  *      If alt_img is NULL, delete from ioc structure.
3545  *      Else, delete a secondary image in same format.
3546  **/
3547 void
3548 mpt_free_fw_memory(MPT_ADAPTER *ioc)
3549 {
3550         int sz;
3551 
3552         if (!ioc->cached_fw)
3553                 return;
3554 
3555         sz = ioc->facts.FWImageSize;
3556         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "free_fw_memory: FW Image  @ %p[%p], sz=%d[%x] bytes\n",
3557                  ioc->name, ioc->cached_fw, (void *)(ulong)ioc->cached_fw_dma, sz, sz));
3558         pci_free_consistent(ioc->pcidev, sz, ioc->cached_fw, ioc->cached_fw_dma);
3559         ioc->alloc_total -= sz;
3560         ioc->cached_fw = NULL;
3561 }
3562 
3563 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
3564 /**
3565  *      mpt_do_upload - Construct and Send FWUpload request to MPT adapter port.
3566  *      @ioc: Pointer to MPT_ADAPTER structure
3567  *      @sleepFlag: Specifies whether the process can sleep
3568  *
3569  *      Returns 0 for success, >0 for handshake failure
3570  *              <0 for fw upload failure.
3571  *
3572  *      Remark: If bound IOC and a successful FWUpload was performed
3573  *      on the bound IOC, the second image is discarded
3574  *      and memory is free'd. Both channels must upload to prevent
3575  *      IOC from running in degraded mode.
3576  */
3577 static int
3578 mpt_do_upload(MPT_ADAPTER *ioc, int sleepFlag)
3579 {
3580         u8                       reply[sizeof(FWUploadReply_t)];
3581         FWUpload_t              *prequest;
3582         FWUploadReply_t         *preply;
3583         FWUploadTCSGE_t         *ptcsge;
3584         u32                      flagsLength;
3585         int                      ii, sz, reply_sz;
3586         int                      cmdStatus;
3587         int                     request_size;
3588         /* If the image size is 0, we are done.
3589          */
3590         if ((sz = ioc->facts.FWImageSize) == 0)
3591                 return 0;
3592 
3593         if (mpt_alloc_fw_memory(ioc, ioc->facts.FWImageSize) != 0)
3594                 return -ENOMEM;
3595 
3596         dinitprintk(ioc, printk(MYIOC_s_INFO_FMT ": FW Image  @ %p[%p], sz=%d[%x] bytes\n",
3597             ioc->name, ioc->cached_fw, (void *)(ulong)ioc->cached_fw_dma, sz, sz));
3598 
3599         prequest = (sleepFlag == NO_SLEEP) ? kzalloc(ioc->req_sz, GFP_ATOMIC) :
3600             kzalloc(ioc->req_sz, GFP_KERNEL);
3601         if (!prequest) {
3602                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "fw upload failed "
3603                     "while allocating memory \n", ioc->name));
3604                 mpt_free_fw_memory(ioc);
3605                 return -ENOMEM;
3606         }
3607 
3608         preply = (FWUploadReply_t *)&reply;
3609 
3610         reply_sz = sizeof(reply);
3611         memset(preply, 0, reply_sz);
3612 
3613         prequest->ImageType = MPI_FW_UPLOAD_ITYPE_FW_IOC_MEM;
3614         prequest->Function = MPI_FUNCTION_FW_UPLOAD;
3615 
3616         ptcsge = (FWUploadTCSGE_t *) &prequest->SGL;
3617         ptcsge->DetailsLength = 12;
3618         ptcsge->Flags = MPI_SGE_FLAGS_TRANSACTION_ELEMENT;
3619         ptcsge->ImageSize = cpu_to_le32(sz);
3620         ptcsge++;
3621 
3622         flagsLength = MPT_SGE_FLAGS_SSIMPLE_READ | sz;
3623         ioc->add_sge((char *)ptcsge, flagsLength, ioc->cached_fw_dma);
3624         request_size = offsetof(FWUpload_t, SGL) + sizeof(FWUploadTCSGE_t) +
3625             ioc->SGE_size;
3626         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Sending FW Upload "
3627             " (req @ %p) fw_size=%d mf_request_size=%d\n", ioc->name, prequest,
3628             ioc->facts.FWImageSize, request_size));
3629         DBG_DUMP_FW_REQUEST_FRAME(ioc, (u32 *)prequest);
3630 
3631         ii = mpt_handshake_req_reply_wait(ioc, request_size, (u32 *)prequest,
3632             reply_sz, (u16 *)preply, 65 /*seconds*/, sleepFlag);
3633 
3634         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "FW Upload completed "
3635             "rc=%x \n", ioc->name, ii));
3636 
3637         cmdStatus = -EFAULT;
3638         if (ii == 0) {
3639                 /* Handshake transfer was complete and successful.
3640                  * Check the Reply Frame.
3641                  */
3642                 int status;
3643                 status = le16_to_cpu(preply->IOCStatus) &
3644                                 MPI_IOCSTATUS_MASK;
3645                 if (status == MPI_IOCSTATUS_SUCCESS &&
3646                     ioc->facts.FWImageSize ==
3647                     le32_to_cpu(preply->ActualImageSize))
3648                                 cmdStatus = 0;
3649         }
3650         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT ": do_upload cmdStatus=%d \n",
3651                         ioc->name, cmdStatus));
3652 
3653 
3654         if (cmdStatus) {
3655                 ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "fw upload failed, "
3656                     "freeing image \n", ioc->name));
3657                 mpt_free_fw_memory(ioc);
3658         }
3659         kfree(prequest);
3660 
3661         return cmdStatus;
3662 }
3663 
3664 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
3665 /**
3666  *      mpt_downloadboot - DownloadBoot code
3667  *      @ioc: Pointer to MPT_ADAPTER structure
3668  *      @pFwHeader: Pointer to firmware header info
3669  *      @sleepFlag: Specifies whether the process can sleep
3670  *
3671  *      FwDownloadBoot requires Programmed IO access.
3672  *
3673  *      Returns 0 for success
3674  *              -1 FW Image size is 0
3675  *              -2 No valid cached_fw Pointer
3676  *              <0 for fw upload failure.
3677  */
3678 static int
3679 mpt_downloadboot(MPT_ADAPTER *ioc, MpiFwHeader_t *pFwHeader, int sleepFlag)
3680 {
3681         MpiExtImageHeader_t     *pExtImage;
3682         u32                      fwSize;
3683         u32                      diag0val;
3684         int                      count;
3685         u32                     *ptrFw;
3686         u32                      diagRwData;
3687         u32                      nextImage;
3688         u32                      load_addr;
3689         u32                      ioc_state=0;
3690 
3691         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "downloadboot: fw size 0x%x (%d), FW Ptr %p\n",
3692                                 ioc->name, pFwHeader->ImageSize, pFwHeader->ImageSize, pFwHeader));
3693 
3694         CHIPREG_WRITE32(&ioc->chip->WriteSequence, 0xFF);
3695         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_1ST_KEY_VALUE);
3696         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_2ND_KEY_VALUE);
3697         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_3RD_KEY_VALUE);
3698         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_4TH_KEY_VALUE);
3699         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_5TH_KEY_VALUE);
3700 
3701         CHIPREG_WRITE32(&ioc->chip->Diagnostic, (MPI_DIAG_PREVENT_IOC_BOOT | MPI_DIAG_DISABLE_ARM));
3702 
3703         /* wait 1 msec */
3704         if (sleepFlag == CAN_SLEEP) {
3705                 msleep(1);
3706         } else {
3707                 mdelay (1);
3708         }
3709 
3710         diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
3711         CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val | MPI_DIAG_RESET_ADAPTER);
3712 
3713         for (count = 0; count < 30; count ++) {
3714                 diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
3715                 if (!(diag0val & MPI_DIAG_RESET_ADAPTER)) {
3716                         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "RESET_ADAPTER cleared, count=%d\n",
3717                                 ioc->name, count));
3718                         break;
3719                 }
3720                 /* wait .1 sec */
3721                 if (sleepFlag == CAN_SLEEP) {
3722                         msleep (100);
3723                 } else {
3724                         mdelay (100);
3725                 }
3726         }
3727 
3728         if ( count == 30 ) {
3729                 ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "downloadboot failed! "
3730                 "Unable to get MPI_DIAG_DRWE mode, diag0val=%x\n",
3731                 ioc->name, diag0val));
3732                 return -3;
3733         }
3734 
3735         CHIPREG_WRITE32(&ioc->chip->WriteSequence, 0xFF);
3736         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_1ST_KEY_VALUE);
3737         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_2ND_KEY_VALUE);
3738         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_3RD_KEY_VALUE);
3739         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_4TH_KEY_VALUE);
3740         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_5TH_KEY_VALUE);
3741 
3742         /* Set the DiagRwEn and Disable ARM bits */
3743         CHIPREG_WRITE32(&ioc->chip->Diagnostic, (MPI_DIAG_RW_ENABLE | MPI_DIAG_DISABLE_ARM));
3744 
3745         fwSize = (pFwHeader->ImageSize + 3)/4;
3746         ptrFw = (u32 *) pFwHeader;
3747 
3748         /* Write the LoadStartAddress to the DiagRw Address Register
3749          * using Programmed IO
3750          */
3751         if (ioc->errata_flag_1064)
3752                 pci_enable_io_access(ioc->pcidev);
3753 
3754         CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, pFwHeader->LoadStartAddress);
3755         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "LoadStart addr written 0x%x \n",
3756                 ioc->name, pFwHeader->LoadStartAddress));
3757 
3758         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Write FW Image: 0x%x bytes @ %p\n",
3759                                 ioc->name, fwSize*4, ptrFw));
3760         while (fwSize--) {
3761                 CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwData, *ptrFw++);
3762         }
3763 
3764         nextImage = pFwHeader->NextImageHeaderOffset;
3765         while (nextImage) {
3766                 pExtImage = (MpiExtImageHeader_t *) ((char *)pFwHeader + nextImage);
3767 
3768                 load_addr = pExtImage->LoadStartAddress;
3769 
3770                 fwSize = (pExtImage->ImageSize + 3) >> 2;
3771                 ptrFw = (u32 *)pExtImage;
3772 
3773                 ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Write Ext Image: 0x%x (%d) bytes @ %p load_addr=%x\n",
3774                                                 ioc->name, fwSize*4, fwSize*4, ptrFw, load_addr));
3775                 CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, load_addr);
3776 
3777                 while (fwSize--) {
3778                         CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwData, *ptrFw++);
3779                 }
3780                 nextImage = pExtImage->NextImageHeaderOffset;
3781         }
3782 
3783         /* Write the IopResetVectorRegAddr */
3784         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Write IopResetVector Addr=%x! \n", ioc->name,  pFwHeader->IopResetRegAddr));
3785         CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, pFwHeader->IopResetRegAddr);
3786 
3787         /* Write the IopResetVectorValue */
3788         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Write IopResetVector Value=%x! \n", ioc->name, pFwHeader->IopResetVectorValue));
3789         CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwData, pFwHeader->IopResetVectorValue);
3790 
3791         /* Clear the internal flash bad bit - autoincrementing register,
3792          * so must do two writes.
3793          */
3794         if (ioc->bus_type == SPI) {
3795                 /*
3796                  * 1030 and 1035 H/W errata, workaround to access
3797                  * the ClearFlashBadSignatureBit
3798                  */
3799                 CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, 0x3F000000);
3800                 diagRwData = CHIPREG_PIO_READ32(&ioc->pio_chip->DiagRwData);
3801                 diagRwData |= 0x40000000;
3802                 CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwAddress, 0x3F000000);
3803                 CHIPREG_PIO_WRITE32(&ioc->pio_chip->DiagRwData, diagRwData);
3804 
3805         } else /* if((ioc->bus_type == SAS) || (ioc->bus_type == FC)) */ {
3806                 diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
3807                 CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val |
3808                     MPI_DIAG_CLEAR_FLASH_BAD_SIG);
3809 
3810                 /* wait 1 msec */
3811                 if (sleepFlag == CAN_SLEEP) {
3812                         msleep (1);
3813                 } else {
3814                         mdelay (1);
3815                 }
3816         }
3817 
3818         if (ioc->errata_flag_1064)
3819                 pci_disable_io_access(ioc->pcidev);
3820 
3821         diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
3822         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "downloadboot diag0val=%x, "
3823                 "turning off PREVENT_IOC_BOOT, DISABLE_ARM, RW_ENABLE\n",
3824                 ioc->name, diag0val));
3825         diag0val &= ~(MPI_DIAG_PREVENT_IOC_BOOT | MPI_DIAG_DISABLE_ARM | MPI_DIAG_RW_ENABLE);
3826         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "downloadboot now diag0val=%x\n",
3827                 ioc->name, diag0val));
3828         CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val);
3829 
3830         /* Write 0xFF to reset the sequencer */
3831         CHIPREG_WRITE32(&ioc->chip->WriteSequence, 0xFF);
3832 
3833         if (ioc->bus_type == SAS) {
3834                 ioc_state = mpt_GetIocState(ioc, 0);
3835                 if ( (GetIocFacts(ioc, sleepFlag,
3836                                 MPT_HOSTEVENT_IOC_BRINGUP)) != 0 ) {
3837                         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "GetIocFacts failed: IocState=%x\n",
3838                                         ioc->name, ioc_state));
3839                         return -EFAULT;
3840                 }
3841         }
3842 
3843         for (count=0; count<HZ*20; count++) {
3844                 if ((ioc_state = mpt_GetIocState(ioc, 0)) & MPI_IOC_STATE_READY) {
3845                         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT
3846                                 "downloadboot successful! (count=%d) IocState=%x\n",
3847                                 ioc->name, count, ioc_state));
3848                         if (ioc->bus_type == SAS) {
3849                                 return 0;
3850                         }
3851                         if ((SendIocInit(ioc, sleepFlag)) != 0) {
3852                                 ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT
3853                                         "downloadboot: SendIocInit failed\n",
3854                                         ioc->name));
3855                                 return -EFAULT;
3856                         }
3857                         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT
3858                                         "downloadboot: SendIocInit successful\n",
3859                                         ioc->name));
3860                         return 0;
3861                 }
3862                 if (sleepFlag == CAN_SLEEP) {
3863                         msleep (10);
3864                 } else {
3865                         mdelay (10);
3866                 }
3867         }
3868         ddlprintk(ioc, printk(MYIOC_s_DEBUG_FMT
3869                 "downloadboot failed! IocState=%x\n",ioc->name, ioc_state));
3870         return -EFAULT;
3871 }
3872 
3873 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
3874 /**
3875  *      KickStart - Perform hard reset of MPT adapter.
3876  *      @ioc: Pointer to MPT_ADAPTER structure
3877  *      @force: Force hard reset
3878  *      @sleepFlag: Specifies whether the process can sleep
3879  *
3880  *      This routine places MPT adapter in diagnostic mode via the
3881  *      WriteSequence register, and then performs a hard reset of adapter
3882  *      via the Diagnostic register.
3883  *
3884  *      Inputs:   sleepflag - CAN_SLEEP (non-interrupt thread)
3885  *                      or NO_SLEEP (interrupt thread, use mdelay)
3886  *                force - 1 if doorbell active, board fault state
3887  *                              board operational, IOC_RECOVERY or
3888  *                              IOC_BRINGUP and there is an alt_ioc.
3889  *                        0 else
3890  *
3891  *      Returns:
3892  *               1 - hard reset, READY
3893  *               0 - no reset due to History bit, READY
3894  *              -1 - no reset due to History bit but not READY
3895  *                   OR reset but failed to come READY
3896  *              -2 - no reset, could not enter DIAG mode
3897  *              -3 - reset but bad FW bit
3898  */
3899 static int
3900 KickStart(MPT_ADAPTER *ioc, int force, int sleepFlag)
3901 {
3902         int hard_reset_done = 0;
3903         u32 ioc_state=0;
3904         int cnt,cntdn;
3905 
3906         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "KickStarting!\n", ioc->name));
3907         if (ioc->bus_type == SPI) {
3908                 /* Always issue a Msg Unit Reset first. This will clear some
3909                  * SCSI bus hang conditions.
3910                  */
3911                 SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, sleepFlag);
3912 
3913                 if (sleepFlag == CAN_SLEEP) {
3914                         msleep (1000);
3915                 } else {
3916                         mdelay (1000);
3917                 }
3918         }
3919 
3920         hard_reset_done = mpt_diag_reset(ioc, force, sleepFlag);
3921         if (hard_reset_done < 0)
3922                 return hard_reset_done;
3923 
3924         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Diagnostic reset successful!\n",
3925                 ioc->name));
3926 
3927         cntdn = ((sleepFlag == CAN_SLEEP) ? HZ : 1000) * 2;     /* 2 seconds */
3928         for (cnt=0; cnt<cntdn; cnt++) {
3929                 ioc_state = mpt_GetIocState(ioc, 1);
3930                 if ((ioc_state == MPI_IOC_STATE_READY) || (ioc_state == MPI_IOC_STATE_OPERATIONAL)) {
3931                         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "KickStart successful! (cnt=%d)\n",
3932                                         ioc->name, cnt));
3933                         return hard_reset_done;
3934                 }
3935                 if (sleepFlag == CAN_SLEEP) {
3936                         msleep (10);
3937                 } else {
3938                         mdelay (10);
3939                 }
3940         }
3941 
3942         dinitprintk(ioc, printk(MYIOC_s_ERR_FMT "Failed to come READY after reset! IocState=%x\n",
3943                 ioc->name, mpt_GetIocState(ioc, 0)));
3944         return -1;
3945 }
3946 
3947 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
3948 /**
3949  *      mpt_diag_reset - Perform hard reset of the adapter.
3950  *      @ioc: Pointer to MPT_ADAPTER structure
3951  *      @ignore: Set if to honor and clear to ignore
3952  *              the reset history bit
3953  *      @sleepFlag: CAN_SLEEP if called in a non-interrupt thread,
3954  *              else set to NO_SLEEP (use mdelay instead)
3955  *
3956  *      This routine places the adapter in diagnostic mode via the
3957  *      WriteSequence register and then performs a hard reset of adapter
3958  *      via the Diagnostic register. Adapter should be in ready state
3959  *      upon successful completion.
3960  *
3961  *      Returns:  1  hard reset successful
3962  *                0  no reset performed because reset history bit set
3963  *               -2  enabling diagnostic mode failed
3964  *               -3  diagnostic reset failed
3965  */
3966 static int
3967 mpt_diag_reset(MPT_ADAPTER *ioc, int ignore, int sleepFlag)
3968 {
3969         u32 diag0val;
3970         u32 doorbell;
3971         int hard_reset_done = 0;
3972         int count = 0;
3973         u32 diag1val = 0;
3974         MpiFwHeader_t *cached_fw;       /* Pointer to FW */
3975         u8       cb_idx;
3976 
3977         /* Clear any existing interrupts */
3978         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
3979 
3980         if (ioc->pcidev->device == MPI_MANUFACTPAGE_DEVID_SAS1078) {
3981 
3982                 if (!ignore)
3983                         return 0;
3984 
3985                 drsprintk(ioc, printk(MYIOC_s_WARN_FMT "%s: Doorbell=%p; 1078 reset "
3986                         "address=%p\n",  ioc->name, __func__,
3987                         &ioc->chip->Doorbell, &ioc->chip->Reset_1078));
3988                 CHIPREG_WRITE32(&ioc->chip->Reset_1078, 0x07);
3989                 if (sleepFlag == CAN_SLEEP)
3990                         msleep(1);
3991                 else
3992                         mdelay(1);
3993 
3994                 /*
3995                  * Call each currently registered protocol IOC reset handler
3996                  * with pre-reset indication.
3997                  * NOTE: If we're doing _IOC_BRINGUP, there can be no
3998                  * MptResetHandlers[] registered yet.
3999                  */
4000                 for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--) {
4001                         if (MptResetHandlers[cb_idx])
4002                                 (*(MptResetHandlers[cb_idx]))(ioc,
4003                                                 MPT_IOC_PRE_RESET);
4004                 }
4005 
4006                 for (count = 0; count < 60; count ++) {
4007                         doorbell = CHIPREG_READ32(&ioc->chip->Doorbell);
4008                         doorbell &= MPI_IOC_STATE_MASK;
4009 
4010                         drsprintk(ioc, printk(MYIOC_s_DEBUG_FMT
4011                                 "looking for READY STATE: doorbell=%x"
4012                                 " count=%d\n",
4013                                 ioc->name, doorbell, count));
4014 
4015                         if (doorbell == MPI_IOC_STATE_READY) {
4016                                 return 1;
4017                         }
4018 
4019                         /* wait 1 sec */
4020                         if (sleepFlag == CAN_SLEEP)
4021                                 msleep(1000);
4022                         else
4023                                 mdelay(1000);
4024                 }
4025                 return -1;
4026         }
4027 
4028         /* Use "Diagnostic reset" method! (only thing available!) */
4029         diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
4030 
4031         if (ioc->debug_level & MPT_DEBUG) {
4032                 if (ioc->alt_ioc)
4033                         diag1val = CHIPREG_READ32(&ioc->alt_ioc->chip->Diagnostic);
4034                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "DbG1: diag0=%08x, diag1=%08x\n",
4035                         ioc->name, diag0val, diag1val));
4036         }
4037 
4038         /* Do the reset if we are told to ignore the reset history
4039          * or if the reset history is 0
4040          */
4041         if (ignore || !(diag0val & MPI_DIAG_RESET_HISTORY)) {
4042                 while ((diag0val & MPI_DIAG_DRWE) == 0) {
4043                         /* Write magic sequence to WriteSequence register
4044                          * Loop until in diagnostic mode
4045                          */
4046                         CHIPREG_WRITE32(&ioc->chip->WriteSequence, 0xFF);
4047                         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_1ST_KEY_VALUE);
4048                         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_2ND_KEY_VALUE);
4049                         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_3RD_KEY_VALUE);
4050                         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_4TH_KEY_VALUE);
4051                         CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_5TH_KEY_VALUE);
4052 
4053                         /* wait 100 msec */
4054                         if (sleepFlag == CAN_SLEEP) {
4055                                 msleep (100);
4056                         } else {
4057                                 mdelay (100);
4058                         }
4059 
4060                         count++;
4061                         if (count > 20) {
4062                                 printk(MYIOC_s_ERR_FMT "Enable Diagnostic mode FAILED! (%02xh)\n",
4063                                                 ioc->name, diag0val);
4064                                 return -2;
4065 
4066                         }
4067 
4068                         diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
4069 
4070                         dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Wrote magic DiagWriteEn sequence (%x)\n",
4071                                         ioc->name, diag0val));
4072                 }
4073 
4074                 if (ioc->debug_level & MPT_DEBUG) {
4075                         if (ioc->alt_ioc)
4076                                 diag1val = CHIPREG_READ32(&ioc->alt_ioc->chip->Diagnostic);
4077                         dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "DbG2: diag0=%08x, diag1=%08x\n",
4078                                 ioc->name, diag0val, diag1val));
4079                 }
4080                 /*
4081                  * Disable the ARM (Bug fix)
4082                  *
4083                  */
4084                 CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val | MPI_DIAG_DISABLE_ARM);
4085                 mdelay(1);
4086 
4087                 /*
4088                  * Now hit the reset bit in the Diagnostic register
4089                  * (THE BIG HAMMER!) (Clears DRWE bit).
4090                  */
4091                 CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val | MPI_DIAG_RESET_ADAPTER);
4092                 hard_reset_done = 1;
4093                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Diagnostic reset performed\n",
4094                                 ioc->name));
4095 
4096                 /*
4097                  * Call each currently registered protocol IOC reset handler
4098                  * with pre-reset indication.
4099                  * NOTE: If we're doing _IOC_BRINGUP, there can be no
4100                  * MptResetHandlers[] registered yet.
4101                  */
4102                 for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--) {
4103                         if (MptResetHandlers[cb_idx]) {
4104                                 mpt_signal_reset(cb_idx,
4105                                         ioc, MPT_IOC_PRE_RESET);
4106                                 if (ioc->alt_ioc) {
4107                                         mpt_signal_reset(cb_idx,
4108                                         ioc->alt_ioc, MPT_IOC_PRE_RESET);
4109                                 }
4110                         }
4111                 }
4112 
4113                 if (ioc->cached_fw)
4114                         cached_fw = (MpiFwHeader_t *)ioc->cached_fw;
4115                 else if (ioc->alt_ioc && ioc->alt_ioc->cached_fw)
4116                         cached_fw = (MpiFwHeader_t *)ioc->alt_ioc->cached_fw;
4117                 else
4118                         cached_fw = NULL;
4119                 if (cached_fw) {
4120                         /* If the DownloadBoot operation fails, the
4121                          * IOC will be left unusable. This is a fatal error
4122                          * case.  _diag_reset will return < 0
4123                          */
4124                         for (count = 0; count < 30; count ++) {
4125                                 diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
4126                                 if (!(diag0val & MPI_DIAG_RESET_ADAPTER)) {
4127                                         break;
4128                                 }
4129 
4130                                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "cached_fw: diag0val=%x count=%d\n",
4131                                         ioc->name, diag0val, count));
4132                                 /* wait 1 sec */
4133                                 if (sleepFlag == CAN_SLEEP) {
4134                                         msleep (1000);
4135                                 } else {
4136                                         mdelay (1000);
4137                                 }
4138                         }
4139                         if ((count = mpt_downloadboot(ioc, cached_fw, sleepFlag)) < 0) {
4140                                 printk(MYIOC_s_WARN_FMT
4141                                         "firmware downloadboot failure (%d)!\n", ioc->name, count);
4142                         }
4143 
4144                 } else {
4145                         /* Wait for FW to reload and for board
4146                          * to go to the READY state.
4147                          * Maximum wait is 60 seconds.
4148                          * If fail, no error will check again
4149                          * with calling program.
4150                          */
4151                         for (count = 0; count < 60; count ++) {
4152                                 doorbell = CHIPREG_READ32(&ioc->chip->Doorbell);
4153                                 doorbell &= MPI_IOC_STATE_MASK;
4154 
4155                                 drsprintk(ioc, printk(MYIOC_s_DEBUG_FMT
4156                                     "looking for READY STATE: doorbell=%x"
4157                                     " count=%d\n", ioc->name, doorbell, count));
4158 
4159                                 if (doorbell == MPI_IOC_STATE_READY) {
4160                                         break;
4161                                 }
4162 
4163                                 /* wait 1 sec */
4164                                 if (sleepFlag == CAN_SLEEP) {
4165                                         msleep (1000);
4166                                 } else {
4167                                         mdelay (1000);
4168                                 }
4169                         }
4170 
4171                         if (doorbell != MPI_IOC_STATE_READY)
4172                                 printk(MYIOC_s_ERR_FMT "Failed to come READY "
4173                                     "after reset! IocState=%x", ioc->name,
4174                                     doorbell);
4175                 }
4176         }
4177 
4178         diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
4179         if (ioc->debug_level & MPT_DEBUG) {
4180                 if (ioc->alt_ioc)
4181                         diag1val = CHIPREG_READ32(&ioc->alt_ioc->chip->Diagnostic);
4182                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "DbG3: diag0=%08x, diag1=%08x\n",
4183                         ioc->name, diag0val, diag1val));
4184         }
4185 
4186         /* Clear RESET_HISTORY bit!  Place board in the
4187          * diagnostic mode to update the diag register.
4188          */
4189         diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
4190         count = 0;
4191         while ((diag0val & MPI_DIAG_DRWE) == 0) {
4192                 /* Write magic sequence to WriteSequence register
4193                  * Loop until in diagnostic mode
4194                  */
4195                 CHIPREG_WRITE32(&ioc->chip->WriteSequence, 0xFF);
4196                 CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_1ST_KEY_VALUE);
4197                 CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_2ND_KEY_VALUE);
4198                 CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_3RD_KEY_VALUE);
4199                 CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_4TH_KEY_VALUE);
4200                 CHIPREG_WRITE32(&ioc->chip->WriteSequence, MPI_WRSEQ_5TH_KEY_VALUE);
4201 
4202                 /* wait 100 msec */
4203                 if (sleepFlag == CAN_SLEEP) {
4204                         msleep (100);
4205                 } else {
4206                         mdelay (100);
4207                 }
4208 
4209                 count++;
4210                 if (count > 20) {
4211                         printk(MYIOC_s_ERR_FMT "Enable Diagnostic mode FAILED! (%02xh)\n",
4212                                         ioc->name, diag0val);
4213                         break;
4214                 }
4215                 diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
4216         }
4217         diag0val &= ~MPI_DIAG_RESET_HISTORY;
4218         CHIPREG_WRITE32(&ioc->chip->Diagnostic, diag0val);
4219         diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
4220         if (diag0val & MPI_DIAG_RESET_HISTORY) {
4221                 printk(MYIOC_s_WARN_FMT "ResetHistory bit failed to clear!\n",
4222                                 ioc->name);
4223         }
4224 
4225         /* Disable Diagnostic Mode
4226          */
4227         CHIPREG_WRITE32(&ioc->chip->WriteSequence, 0xFFFFFFFF);
4228 
4229         /* Check FW reload status flags.
4230          */
4231         diag0val = CHIPREG_READ32(&ioc->chip->Diagnostic);
4232         if (diag0val & (MPI_DIAG_FLASH_BAD_SIG | MPI_DIAG_RESET_ADAPTER | MPI_DIAG_DISABLE_ARM)) {
4233                 printk(MYIOC_s_ERR_FMT "Diagnostic reset FAILED! (%02xh)\n",
4234                                 ioc->name, diag0val);
4235                 return -3;
4236         }
4237 
4238         if (ioc->debug_level & MPT_DEBUG) {
4239                 if (ioc->alt_ioc)
4240                         diag1val = CHIPREG_READ32(&ioc->alt_ioc->chip->Diagnostic);
4241                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "DbG4: diag0=%08x, diag1=%08x\n",
4242                         ioc->name, diag0val, diag1val));
4243         }
4244 
4245         /*
4246          * Reset flag that says we've enabled event notification
4247          */
4248         ioc->facts.EventState = 0;
4249 
4250         if (ioc->alt_ioc)
4251                 ioc->alt_ioc->facts.EventState = 0;
4252 
4253         return hard_reset_done;
4254 }
4255 
4256 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
4257 /**
4258  *      SendIocReset - Send IOCReset request to MPT adapter.
4259  *      @ioc: Pointer to MPT_ADAPTER structure
4260  *      @reset_type: reset type, expected values are
4261  *      %MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET or %MPI_FUNCTION_IO_UNIT_RESET
4262  *      @sleepFlag: Specifies whether the process can sleep
4263  *
4264  *      Send IOCReset request to the MPT adapter.
4265  *
4266  *      Returns 0 for success, non-zero for failure.
4267  */
4268 static int
4269 SendIocReset(MPT_ADAPTER *ioc, u8 reset_type, int sleepFlag)
4270 {
4271         int r;
4272         u32 state;
4273         int cntdn, count;
4274 
4275         drsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Sending IOC reset(0x%02x)!\n",
4276                         ioc->name, reset_type));
4277         CHIPREG_WRITE32(&ioc->chip->Doorbell, reset_type<<MPI_DOORBELL_FUNCTION_SHIFT);
4278         if ((r = WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0)
4279                 return r;
4280 
4281         /* FW ACK'd request, wait for READY state
4282          */
4283         count = 0;
4284         cntdn = ((sleepFlag == CAN_SLEEP) ? HZ : 1000) * 15;    /* 15 seconds */
4285 
4286         while ((state = mpt_GetIocState(ioc, 1)) != MPI_IOC_STATE_READY) {
4287                 cntdn--;
4288                 count++;
4289                 if (!cntdn) {
4290                         if (sleepFlag != CAN_SLEEP)
4291                                 count *= 10;
4292 
4293                         printk(MYIOC_s_ERR_FMT
4294                             "Wait IOC_READY state (0x%x) timeout(%d)!\n",
4295                             ioc->name, state, (int)((count+5)/HZ));
4296                         return -ETIME;
4297                 }
4298 
4299                 if (sleepFlag == CAN_SLEEP) {
4300                         msleep(1);
4301                 } else {
4302                         mdelay (1);     /* 1 msec delay */
4303                 }
4304         }
4305 
4306         /* TODO!
4307          *  Cleanup all event stuff for this IOC; re-issue EventNotification
4308          *  request if needed.
4309          */
4310         if (ioc->facts.Function)
4311                 ioc->facts.EventState = 0;
4312 
4313         return 0;
4314 }
4315 
4316 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
4317 /**
4318  *      initChainBuffers - Allocate memory for and initialize chain buffers
4319  *      @ioc: Pointer to MPT_ADAPTER structure
4320  *
4321  *      Allocates memory for and initializes chain buffers,
4322  *      chain buffer control arrays and spinlock.
4323  */
4324 static int
4325 initChainBuffers(MPT_ADAPTER *ioc)
4326 {
4327         u8              *mem;
4328         int             sz, ii, num_chain;
4329         int             scale, num_sge, numSGE;
4330 
4331         /* ReqToChain size must equal the req_depth
4332          * index = req_idx
4333          */
4334         if (ioc->ReqToChain == NULL) {
4335                 sz = ioc->req_depth * sizeof(int);
4336                 mem = kmalloc(sz, GFP_ATOMIC);
4337                 if (mem == NULL)
4338                         return -1;
4339 
4340                 ioc->ReqToChain = (int *) mem;
4341                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "ReqToChain alloc  @ %p, sz=%d bytes\n",
4342                                 ioc->name, mem, sz));
4343                 mem = kmalloc(sz, GFP_ATOMIC);
4344                 if (mem == NULL)
4345                         return -1;
4346 
4347                 ioc->RequestNB = (int *) mem;
4348                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "RequestNB alloc  @ %p, sz=%d bytes\n",
4349                                 ioc->name, mem, sz));
4350         }
4351         for (ii = 0; ii < ioc->req_depth; ii++) {
4352                 ioc->ReqToChain[ii] = MPT_HOST_NO_CHAIN;
4353         }
4354 
4355         /* ChainToChain size must equal the total number
4356          * of chain buffers to be allocated.
4357          * index = chain_idx
4358          *
4359          * Calculate the number of chain buffers needed(plus 1) per I/O
4360          * then multiply the maximum number of simultaneous cmds
4361          *
4362          * num_sge = num sge in request frame + last chain buffer
4363          * scale = num sge per chain buffer if no chain element
4364          */
4365         scale = ioc->req_sz / ioc->SGE_size;
4366         if (ioc->sg_addr_size == sizeof(u64))
4367                 num_sge =  scale + (ioc->req_sz - 60) / ioc->SGE_size;
4368         else
4369                 num_sge =  1 + scale + (ioc->req_sz - 64) / ioc->SGE_size;
4370 
4371         if (ioc->sg_addr_size == sizeof(u64)) {
4372                 numSGE = (scale - 1) * (ioc->facts.MaxChainDepth-1) + scale +
4373                         (ioc->req_sz - 60) / ioc->SGE_size;
4374         } else {
4375                 numSGE = 1 + (scale - 1) * (ioc->facts.MaxChainDepth-1) +
4376                     scale + (ioc->req_sz - 64) / ioc->SGE_size;
4377         }
4378         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "num_sge=%d numSGE=%d\n",
4379                 ioc->name, num_sge, numSGE));
4380 
4381         if (ioc->bus_type == FC) {
4382                 if (numSGE > MPT_SCSI_FC_SG_DEPTH)
4383                         numSGE = MPT_SCSI_FC_SG_DEPTH;
4384         } else {
4385                 if (numSGE > MPT_SCSI_SG_DEPTH)
4386                         numSGE = MPT_SCSI_SG_DEPTH;
4387         }
4388 
4389         num_chain = 1;
4390         while (numSGE - num_sge > 0) {
4391                 num_chain++;
4392                 num_sge += (scale - 1);
4393         }
4394         num_chain++;
4395 
4396         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Now numSGE=%d num_sge=%d num_chain=%d\n",
4397                 ioc->name, numSGE, num_sge, num_chain));
4398 
4399         if (ioc->bus_type == SPI)
4400                 num_chain *= MPT_SCSI_CAN_QUEUE;
4401         else if (ioc->bus_type == SAS)
4402                 num_chain *= MPT_SAS_CAN_QUEUE;
4403         else
4404                 num_chain *= MPT_FC_CAN_QUEUE;
4405 
4406         ioc->num_chain = num_chain;
4407 
4408         sz = num_chain * sizeof(int);
4409         if (ioc->ChainToChain == NULL) {
4410                 mem = kmalloc(sz, GFP_ATOMIC);
4411                 if (mem == NULL)
4412                         return -1;
4413 
4414                 ioc->ChainToChain = (int *) mem;
4415                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "ChainToChain alloc @ %p, sz=%d bytes\n",
4416                                 ioc->name, mem, sz));
4417         } else {
4418                 mem = (u8 *) ioc->ChainToChain;
4419         }
4420         memset(mem, 0xFF, sz);
4421         return num_chain;
4422 }
4423 
4424 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
4425 /**
4426  *      PrimeIocFifos - Initialize IOC request and reply FIFOs.
4427  *      @ioc: Pointer to MPT_ADAPTER structure
4428  *
4429  *      This routine allocates memory for the MPT reply and request frame
4430  *      pools (if necessary), and primes the IOC reply FIFO with
4431  *      reply frames.
4432  *
4433  *      Returns 0 for success, non-zero for failure.
4434  */
4435 static int
4436 PrimeIocFifos(MPT_ADAPTER *ioc)
4437 {
4438         MPT_FRAME_HDR *mf;
4439         unsigned long flags;
4440         dma_addr_t alloc_dma;
4441         u8 *mem;
4442         int i, reply_sz, sz, total_size, num_chain;
4443         u64     dma_mask;
4444 
4445         dma_mask = 0;
4446 
4447         /*  Prime reply FIFO...  */
4448 
4449         if (ioc->reply_frames == NULL) {
4450                 if ( (num_chain = initChainBuffers(ioc)) < 0)
4451                         return -1;
4452                 /*
4453                  * 1078 errata workaround for the 36GB limitation
4454                  */
4455                 if (ioc->pcidev->device == MPI_MANUFACTPAGE_DEVID_SAS1078 &&
4456                     ioc->dma_mask > DMA_BIT_MASK(35)) {
4457                         if (!pci_set_dma_mask(ioc->pcidev, DMA_BIT_MASK(32))
4458                             && !pci_set_consistent_dma_mask(ioc->pcidev,
4459                             DMA_BIT_MASK(32))) {
4460                                 dma_mask = DMA_BIT_MASK(35);
4461                                 d36memprintk(ioc, printk(MYIOC_s_DEBUG_FMT
4462                                     "setting 35 bit addressing for "
4463                                     "Request/Reply/Chain and Sense Buffers\n",
4464                                     ioc->name));
4465                         } else {
4466                                 /*Reseting DMA mask to 64 bit*/
4467                                 pci_set_dma_mask(ioc->pcidev,
4468                                         DMA_BIT_MASK(64));
4469                                 pci_set_consistent_dma_mask(ioc->pcidev,
4470                                         DMA_BIT_MASK(64));
4471 
4472                                 printk(MYIOC_s_ERR_FMT
4473                                     "failed setting 35 bit addressing for "
4474                                     "Request/Reply/Chain and Sense Buffers\n",
4475                                     ioc->name);
4476                                 return -1;
4477                         }
4478                 }
4479 
4480                 total_size = reply_sz = (ioc->reply_sz * ioc->reply_depth);
4481                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "ReplyBuffer sz=%d bytes, ReplyDepth=%d\n",
4482                                 ioc->name, ioc->reply_sz, ioc->reply_depth));
4483                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "ReplyBuffer sz=%d[%x] bytes\n",
4484                                 ioc->name, reply_sz, reply_sz));
4485 
4486                 sz = (ioc->req_sz * ioc->req_depth);
4487                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "RequestBuffer sz=%d bytes, RequestDepth=%d\n",
4488                                 ioc->name, ioc->req_sz, ioc->req_depth));
4489                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "RequestBuffer sz=%d[%x] bytes\n",
4490                                 ioc->name, sz, sz));
4491                 total_size += sz;
4492 
4493                 sz = num_chain * ioc->req_sz; /* chain buffer pool size */
4494                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "ChainBuffer sz=%d bytes, ChainDepth=%d\n",
4495                                 ioc->name, ioc->req_sz, num_chain));
4496                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "ChainBuffer sz=%d[%x] bytes num_chain=%d\n",
4497                                 ioc->name, sz, sz, num_chain));
4498 
4499                 total_size += sz;
4500                 mem = pci_alloc_consistent(ioc->pcidev, total_size, &alloc_dma);
4501                 if (mem == NULL) {
4502                         printk(MYIOC_s_ERR_FMT "Unable to allocate Reply, Request, Chain Buffers!\n",
4503                                 ioc->name);
4504                         goto out_fail;
4505                 }
4506 
4507                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Total alloc @ %p[%p], sz=%d[%x] bytes\n",
4508                                 ioc->name, mem, (void *)(ulong)alloc_dma, total_size, total_size));
4509 
4510                 memset(mem, 0, total_size);
4511                 ioc->alloc_total += total_size;
4512                 ioc->alloc = mem;
4513                 ioc->alloc_dma = alloc_dma;
4514                 ioc->alloc_sz = total_size;
4515                 ioc->reply_frames = (MPT_FRAME_HDR *) mem;
4516                 ioc->reply_frames_low_dma = (u32) (alloc_dma & 0xFFFFFFFF);
4517 
4518                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "ReplyBuffers @ %p[%p]\n",
4519                         ioc->name, ioc->reply_frames, (void *)(ulong)alloc_dma));
4520 
4521                 alloc_dma += reply_sz;
4522                 mem += reply_sz;
4523 
4524                 /*  Request FIFO - WE manage this!  */
4525 
4526                 ioc->req_frames = (MPT_FRAME_HDR *) mem;
4527                 ioc->req_frames_dma = alloc_dma;
4528 
4529                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "RequestBuffers @ %p[%p]\n",
4530                                 ioc->name, mem, (void *)(ulong)alloc_dma));
4531 
4532                 ioc->req_frames_low_dma = (u32) (alloc_dma & 0xFFFFFFFF);
4533 
4534                 for (i = 0; i < ioc->req_depth; i++) {
4535                         alloc_dma += ioc->req_sz;
4536                         mem += ioc->req_sz;
4537                 }
4538 
4539                 ioc->ChainBuffer = mem;
4540                 ioc->ChainBufferDMA = alloc_dma;
4541 
4542                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "ChainBuffers @ %p(%p)\n",
4543                         ioc->name, ioc->ChainBuffer, (void *)(ulong)ioc->ChainBufferDMA));
4544 
4545                 /* Initialize the free chain Q.
4546                 */
4547 
4548                 INIT_LIST_HEAD(&ioc->FreeChainQ);
4549 
4550                 /* Post the chain buffers to the FreeChainQ.
4551                 */
4552                 mem = (u8 *)ioc->ChainBuffer;
4553                 for (i=0; i < num_chain; i++) {
4554                         mf = (MPT_FRAME_HDR *) mem;
4555                         list_add_tail(&mf->u.frame.linkage.list, &ioc->FreeChainQ);
4556                         mem += ioc->req_sz;
4557                 }
4558 
4559                 /* Initialize Request frames linked list
4560                  */
4561                 alloc_dma = ioc->req_frames_dma;
4562                 mem = (u8 *) ioc->req_frames;
4563 
4564                 spin_lock_irqsave(&ioc->FreeQlock, flags);
4565                 INIT_LIST_HEAD(&ioc->FreeQ);
4566                 for (i = 0; i < ioc->req_depth; i++) {
4567                         mf = (MPT_FRAME_HDR *) mem;
4568 
4569                         /*  Queue REQUESTs *internally*!  */
4570                         list_add_tail(&mf->u.frame.linkage.list, &ioc->FreeQ);
4571 
4572                         mem += ioc->req_sz;
4573                 }
4574                 spin_unlock_irqrestore(&ioc->FreeQlock, flags);
4575 
4576                 sz = (ioc->req_depth * MPT_SENSE_BUFFER_ALLOC);
4577                 ioc->sense_buf_pool =
4578                         pci_alloc_consistent(ioc->pcidev, sz, &ioc->sense_buf_pool_dma);
4579                 if (ioc->sense_buf_pool == NULL) {
4580                         printk(MYIOC_s_ERR_FMT "Unable to allocate Sense Buffers!\n",
4581                                 ioc->name);
4582                         goto out_fail;
4583                 }
4584 
4585                 ioc->sense_buf_low_dma = (u32) (ioc->sense_buf_pool_dma & 0xFFFFFFFF);
4586                 ioc->alloc_total += sz;
4587                 dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "SenseBuffers @ %p[%p]\n",
4588                         ioc->name, ioc->sense_buf_pool, (void *)(ulong)ioc->sense_buf_pool_dma));
4589 
4590         }
4591 
4592         /* Post Reply frames to FIFO
4593          */
4594         alloc_dma = ioc->alloc_dma;
4595         dinitprintk(ioc, printk(MYIOC_s_DEBUG_FMT "ReplyBuffers @ %p[%p]\n",
4596                 ioc->name, ioc->reply_frames, (void *)(ulong)alloc_dma));
4597 
4598         for (i = 0; i < ioc->reply_depth; i++) {
4599                 /*  Write each address to the IOC!  */
4600                 CHIPREG_WRITE32(&ioc->chip->ReplyFifo, alloc_dma);
4601                 alloc_dma += ioc->reply_sz;
4602         }
4603 
4604         if (dma_mask == DMA_BIT_MASK(35) && !pci_set_dma_mask(ioc->pcidev,
4605             ioc->dma_mask) && !pci_set_consistent_dma_mask(ioc->pcidev,
4606             ioc->dma_mask))
4607                 d36memprintk(ioc, printk(MYIOC_s_DEBUG_FMT
4608                     "restoring 64 bit addressing\n", ioc->name));
4609 
4610         return 0;
4611 
4612 out_fail:
4613 
4614         if (ioc->alloc != NULL) {
4615                 sz = ioc->alloc_sz;
4616                 pci_free_consistent(ioc->pcidev,
4617                                 sz,
4618                                 ioc->alloc, ioc->alloc_dma);
4619                 ioc->reply_frames = NULL;
4620                 ioc->req_frames = NULL;
4621                 ioc->alloc_total -= sz;
4622         }
4623         if (ioc->sense_buf_pool != NULL) {
4624                 sz = (ioc->req_depth * MPT_SENSE_BUFFER_ALLOC);
4625                 pci_free_consistent(ioc->pcidev,
4626                                 sz,
4627                                 ioc->sense_buf_pool, ioc->sense_buf_pool_dma);
4628                 ioc->sense_buf_pool = NULL;
4629         }
4630 
4631         if (dma_mask == DMA_BIT_MASK(35) && !pci_set_dma_mask(ioc->pcidev,
4632             DMA_BIT_MASK(64)) && !pci_set_consistent_dma_mask(ioc->pcidev,
4633             DMA_BIT_MASK(64)))
4634                 d36memprintk(ioc, printk(MYIOC_s_DEBUG_FMT
4635                     "restoring 64 bit addressing\n", ioc->name));
4636 
4637         return -1;
4638 }
4639 
4640 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
4641 /**
4642  *      mpt_handshake_req_reply_wait - Send MPT request to and receive reply
4643  *      from IOC via doorbell handshake method.
4644  *      @ioc: Pointer to MPT_ADAPTER structure
4645  *      @reqBytes: Size of the request in bytes
4646  *      @req: Pointer to MPT request frame
4647  *      @replyBytes: Expected size of the reply in bytes
4648  *      @u16reply: Pointer to area where reply should be written
4649  *      @maxwait: Max wait time for a reply (in seconds)
4650  *      @sleepFlag: Specifies whether the process can sleep
4651  *
4652  *      NOTES: It is the callers responsibility to byte-swap fields in the
4653  *      request which are greater than 1 byte in size.  It is also the
4654  *      callers responsibility to byte-swap response fields which are
4655  *      greater than 1 byte in size.
4656  *
4657  *      Returns 0 for success, non-zero for failure.
4658  */
4659 static int
4660 mpt_handshake_req_reply_wait(MPT_ADAPTER *ioc, int reqBytes, u32 *req,
4661                 int replyBytes, u16 *u16reply, int maxwait, int sleepFlag)
4662 {
4663         MPIDefaultReply_t *mptReply;
4664         int failcnt = 0;
4665         int t;
4666 
4667         /*
4668          * Get ready to cache a handshake reply
4669          */
4670         ioc->hs_reply_idx = 0;
4671         mptReply = (MPIDefaultReply_t *) ioc->hs_reply;
4672         mptReply->MsgLength = 0;
4673 
4674         /*
4675          * Make sure there are no doorbells (WRITE 0 to IntStatus reg),
4676          * then tell IOC that we want to handshake a request of N words.
4677          * (WRITE u32val to Doorbell reg).
4678          */
4679         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
4680         CHIPREG_WRITE32(&ioc->chip->Doorbell,
4681                         ((MPI_FUNCTION_HANDSHAKE<<MPI_DOORBELL_FUNCTION_SHIFT) |
4682                          ((reqBytes/4)<<MPI_DOORBELL_ADD_DWORDS_SHIFT)));
4683 
4684         /*
4685          * Wait for IOC's doorbell handshake int
4686          */
4687         if ((t = WaitForDoorbellInt(ioc, 5, sleepFlag)) < 0)
4688                 failcnt++;
4689 
4690         dhsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "HandShake request start reqBytes=%d, WaitCnt=%d%s\n",
4691                         ioc->name, reqBytes, t, failcnt ? " - MISSING DOORBELL HANDSHAKE!" : ""));
4692 
4693         /* Read doorbell and check for active bit */
4694         if (!(CHIPREG_READ32(&ioc->chip->Doorbell) & MPI_DOORBELL_ACTIVE))
4695                         return -1;
4696 
4697         /*
4698          * Clear doorbell int (WRITE 0 to IntStatus reg),
4699          * then wait for IOC to ACKnowledge that it's ready for
4700          * our handshake request.
4701          */
4702         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
4703         if (!failcnt && (t = WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0)
4704                 failcnt++;
4705 
4706         if (!failcnt) {
4707                 int      ii;
4708                 u8      *req_as_bytes = (u8 *) req;
4709 
4710                 /*
4711                  * Stuff request words via doorbell handshake,
4712                  * with ACK from IOC for each.
4713                  */
4714                 for (ii = 0; !failcnt && ii < reqBytes/4; ii++) {
4715                         u32 word = ((req_as_bytes[(ii*4) + 0] <<  0) |
4716                                     (req_as_bytes[(ii*4) + 1] <<  8) |
4717                                     (req_as_bytes[(ii*4) + 2] << 16) |
4718                                     (req_as_bytes[(ii*4) + 3] << 24));
4719 
4720                         CHIPREG_WRITE32(&ioc->chip->Doorbell, word);
4721                         if ((t = WaitForDoorbellAck(ioc, 5, sleepFlag)) < 0)
4722                                 failcnt++;
4723                 }
4724 
4725                 dhsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Handshake request frame (@%p) header\n", ioc->name, req));
4726                 DBG_DUMP_REQUEST_FRAME_HDR(ioc, (u32 *)req);
4727 
4728                 dhsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "HandShake request post done, WaitCnt=%d%s\n",
4729                                 ioc->name, t, failcnt ? " - MISSING DOORBELL ACK!" : ""));
4730 
4731                 /*
4732                  * Wait for completion of doorbell handshake reply from the IOC
4733                  */
4734                 if (!failcnt && (t = WaitForDoorbellReply(ioc, maxwait, sleepFlag)) < 0)
4735                         failcnt++;
4736 
4737                 dhsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "HandShake reply count=%d%s\n",
4738                                 ioc->name, t, failcnt ? " - MISSING DOORBELL REPLY!" : ""));
4739 
4740                 /*
4741                  * Copy out the cached reply...
4742                  */
4743                 for (ii=0; ii < min(replyBytes/2,mptReply->MsgLength*2); ii++)
4744                         u16reply[ii] = ioc->hs_reply[ii];
4745         } else {
4746                 return -99;
4747         }
4748 
4749         return -failcnt;
4750 }
4751 
4752 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
4753 /**
4754  *      WaitForDoorbellAck - Wait for IOC doorbell handshake acknowledge
4755  *      @ioc: Pointer to MPT_ADAPTER structure
4756  *      @howlong: How long to wait (in seconds)
4757  *      @sleepFlag: Specifies whether the process can sleep
4758  *
4759  *      This routine waits (up to ~2 seconds max) for IOC doorbell
4760  *      handshake ACKnowledge, indicated by the IOP_DOORBELL_STATUS
4761  *      bit in its IntStatus register being clear.
4762  *
4763  *      Returns a negative value on failure, else wait loop count.
4764  */
4765 static int
4766 WaitForDoorbellAck(MPT_ADAPTER *ioc, int howlong, int sleepFlag)
4767 {
4768         int cntdn;
4769         int count = 0;
4770         u32 intstat=0;
4771 
4772         cntdn = 1000 * howlong;
4773 
4774         if (sleepFlag == CAN_SLEEP) {
4775                 while (--cntdn) {
4776                         msleep (1);
4777                         intstat = CHIPREG_READ32(&ioc->chip->IntStatus);
4778                         if (! (intstat & MPI_HIS_IOP_DOORBELL_STATUS))
4779                                 break;
4780                         count++;
4781                 }
4782         } else {
4783                 while (--cntdn) {
4784                         udelay (1000);
4785                         intstat = CHIPREG_READ32(&ioc->chip->IntStatus);
4786                         if (! (intstat & MPI_HIS_IOP_DOORBELL_STATUS))
4787                                 break;
4788                         count++;
4789                 }
4790         }
4791 
4792         if (cntdn) {
4793                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "WaitForDoorbell ACK (count=%d)\n",
4794                                 ioc->name, count));
4795                 return count;
4796         }
4797 
4798         printk(MYIOC_s_ERR_FMT "Doorbell ACK timeout (count=%d), IntStatus=%x!\n",
4799                         ioc->name, count, intstat);
4800         return -1;
4801 }
4802 
4803 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
4804 /**
4805  *      WaitForDoorbellInt - Wait for IOC to set its doorbell interrupt bit
4806  *      @ioc: Pointer to MPT_ADAPTER structure
4807  *      @howlong: How long to wait (in seconds)
4808  *      @sleepFlag: Specifies whether the process can sleep
4809  *
4810  *      This routine waits (up to ~2 seconds max) for IOC doorbell interrupt
4811  *      (MPI_HIS_DOORBELL_INTERRUPT) to be set in the IntStatus register.
4812  *
4813  *      Returns a negative value on failure, else wait loop count.
4814  */
4815 static int
4816 WaitForDoorbellInt(MPT_ADAPTER *ioc, int howlong, int sleepFlag)
4817 {
4818         int cntdn;
4819         int count = 0;
4820         u32 intstat=0;
4821 
4822         cntdn = 1000 * howlong;
4823         if (sleepFlag == CAN_SLEEP) {
4824                 while (--cntdn) {
4825                         intstat = CHIPREG_READ32(&ioc->chip->IntStatus);
4826                         if (intstat & MPI_HIS_DOORBELL_INTERRUPT)
4827                                 break;
4828                         msleep(1);
4829                         count++;
4830                 }
4831         } else {
4832                 while (--cntdn) {
4833                         intstat = CHIPREG_READ32(&ioc->chip->IntStatus);
4834                         if (intstat & MPI_HIS_DOORBELL_INTERRUPT)
4835                                 break;
4836                         udelay (1000);
4837                         count++;
4838                 }
4839         }
4840 
4841         if (cntdn) {
4842                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "WaitForDoorbell INT (cnt=%d) howlong=%d\n",
4843                                 ioc->name, count, howlong));
4844                 return count;
4845         }
4846 
4847         printk(MYIOC_s_ERR_FMT "Doorbell INT timeout (count=%d), IntStatus=%x!\n",
4848                         ioc->name, count, intstat);
4849         return -1;
4850 }
4851 
4852 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
4853 /**
4854  *      WaitForDoorbellReply - Wait for and capture an IOC handshake reply.
4855  *      @ioc: Pointer to MPT_ADAPTER structure
4856  *      @howlong: How long to wait (in seconds)
4857  *      @sleepFlag: Specifies whether the process can sleep
4858  *
4859  *      This routine polls the IOC for a handshake reply, 16 bits at a time.
4860  *      Reply is cached to IOC private area large enough to hold a maximum
4861  *      of 128 bytes of reply data.
4862  *
4863  *      Returns a negative value on failure, else size of reply in WORDS.
4864  */
4865 static int
4866 WaitForDoorbellReply(MPT_ADAPTER *ioc, int howlong, int sleepFlag)
4867 {
4868         int u16cnt = 0;
4869         int failcnt = 0;
4870         int t;
4871         u16 *hs_reply = ioc->hs_reply;
4872         volatile MPIDefaultReply_t *mptReply = (MPIDefaultReply_t *) ioc->hs_reply;
4873         u16 hword;
4874 
4875         hs_reply[0] = hs_reply[1] = hs_reply[7] = 0;
4876 
4877         /*
4878          * Get first two u16's so we can look at IOC's intended reply MsgLength
4879          */
4880         u16cnt=0;
4881         if ((t = WaitForDoorbellInt(ioc, howlong, sleepFlag)) < 0) {
4882                 failcnt++;
4883         } else {
4884                 hs_reply[u16cnt++] = le16_to_cpu(CHIPREG_READ32(&ioc->chip->Doorbell) & 0x0000FFFF);
4885                 CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
4886                 if ((t = WaitForDoorbellInt(ioc, 5, sleepFlag)) < 0)
4887                         failcnt++;
4888                 else {
4889                         hs_reply[u16cnt++] = le16_to_cpu(CHIPREG_READ32(&ioc->chip->Doorbell) & 0x0000FFFF);
4890                         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
4891                 }
4892         }
4893 
4894         dhsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "WaitCnt=%d First handshake reply word=%08x%s\n",
4895                         ioc->name, t, le32_to_cpu(*(u32 *)hs_reply),
4896                         failcnt ? " - MISSING DOORBELL HANDSHAKE!" : ""));
4897 
4898         /*
4899          * If no error (and IOC said MsgLength is > 0), piece together
4900          * reply 16 bits at a time.
4901          */
4902         for (u16cnt=2; !failcnt && u16cnt < (2 * mptReply->MsgLength); u16cnt++) {
4903                 if ((t = WaitForDoorbellInt(ioc, 5, sleepFlag)) < 0)
4904                         failcnt++;
4905                 hword = le16_to_cpu(CHIPREG_READ32(&ioc->chip->Doorbell) & 0x0000FFFF);
4906                 /* don't overflow our IOC hs_reply[] buffer! */
4907                 if (u16cnt < ARRAY_SIZE(ioc->hs_reply))
4908                         hs_reply[u16cnt] = hword;
4909                 CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
4910         }
4911 
4912         if (!failcnt && (t = WaitForDoorbellInt(ioc, 5, sleepFlag)) < 0)
4913                 failcnt++;
4914         CHIPREG_WRITE32(&ioc->chip->IntStatus, 0);
4915 
4916         if (failcnt) {
4917                 printk(MYIOC_s_ERR_FMT "Handshake reply failure!\n",
4918                                 ioc->name);
4919                 return -failcnt;
4920         }
4921 #if 0
4922         else if (u16cnt != (2 * mptReply->MsgLength)) {
4923                 return -101;
4924         }
4925         else if ((mptReply->IOCStatus & MPI_IOCSTATUS_MASK) != MPI_IOCSTATUS_SUCCESS) {
4926                 return -102;
4927         }
4928 #endif
4929 
4930         dhsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Got Handshake reply:\n", ioc->name));
4931         DBG_DUMP_REPLY_FRAME(ioc, (u32 *)mptReply);
4932 
4933         dhsprintk(ioc, printk(MYIOC_s_DEBUG_FMT "WaitForDoorbell REPLY WaitCnt=%d (sz=%d)\n",
4934                         ioc->name, t, u16cnt/2));
4935         return u16cnt/2;
4936 }
4937 
4938 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
4939 /**
4940  *      GetLanConfigPages - Fetch LANConfig pages.
4941  *      @ioc: Pointer to MPT_ADAPTER structure
4942  *
4943  *      Return: 0 for success
4944  *      -ENOMEM if no memory available
4945  *              -EPERM if not allowed due to ISR context
4946  *              -EAGAIN if no msg frames currently available
4947  *              -EFAULT for non-successful reply or no reply (timeout)
4948  */
4949 static int
4950 GetLanConfigPages(MPT_ADAPTER *ioc)
4951 {
4952         ConfigPageHeader_t       hdr;
4953         CONFIGPARMS              cfg;
4954         LANPage0_t              *ppage0_alloc;
4955         dma_addr_t               page0_dma;
4956         LANPage1_t              *ppage1_alloc;
4957         dma_addr_t               page1_dma;
4958         int                      rc = 0;
4959         int                      data_sz;
4960         int                      copy_sz;
4961 
4962         /* Get LAN Page 0 header */
4963         hdr.PageVersion = 0;
4964         hdr.PageLength = 0;
4965         hdr.PageNumber = 0;
4966         hdr.PageType = MPI_CONFIG_PAGETYPE_LAN;
4967         cfg.cfghdr.hdr = &hdr;
4968         cfg.physAddr = -1;
4969         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
4970         cfg.dir = 0;
4971         cfg.pageAddr = 0;
4972         cfg.timeout = 0;
4973 
4974         if ((rc = mpt_config(ioc, &cfg)) != 0)
4975                 return rc;
4976 
4977         if (hdr.PageLength > 0) {
4978                 data_sz = hdr.PageLength * 4;
4979                 ppage0_alloc = (LANPage0_t *) pci_alloc_consistent(ioc->pcidev, data_sz, &page0_dma);
4980                 rc = -ENOMEM;
4981                 if (ppage0_alloc) {
4982                         memset((u8 *)ppage0_alloc, 0, data_sz);
4983                         cfg.physAddr = page0_dma;
4984                         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
4985 
4986                         if ((rc = mpt_config(ioc, &cfg)) == 0) {
4987                                 /* save the data */
4988                                 copy_sz = min_t(int, sizeof(LANPage0_t), data_sz);
4989                                 memcpy(&ioc->lan_cnfg_page0, ppage0_alloc, copy_sz);
4990 
4991                         }
4992 
4993                         pci_free_consistent(ioc->pcidev, data_sz, (u8 *) ppage0_alloc, page0_dma);
4994 
4995                         /* FIXME!
4996                          *      Normalize endianness of structure data,
4997                          *      by byte-swapping all > 1 byte fields!
4998                          */
4999 
5000                 }
5001 
5002                 if (rc)
5003                         return rc;
5004         }
5005 
5006         /* Get LAN Page 1 header */
5007         hdr.PageVersion = 0;
5008         hdr.PageLength = 0;
5009         hdr.PageNumber = 1;
5010         hdr.PageType = MPI_CONFIG_PAGETYPE_LAN;
5011         cfg.cfghdr.hdr = &hdr;
5012         cfg.physAddr = -1;
5013         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5014         cfg.dir = 0;
5015         cfg.pageAddr = 0;
5016 
5017         if ((rc = mpt_config(ioc, &cfg)) != 0)
5018                 return rc;
5019 
5020         if (hdr.PageLength == 0)
5021                 return 0;
5022 
5023         data_sz = hdr.PageLength * 4;
5024         rc = -ENOMEM;
5025         ppage1_alloc = (LANPage1_t *) pci_alloc_consistent(ioc->pcidev, data_sz, &page1_dma);
5026         if (ppage1_alloc) {
5027                 memset((u8 *)ppage1_alloc, 0, data_sz);
5028                 cfg.physAddr = page1_dma;
5029                 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5030 
5031                 if ((rc = mpt_config(ioc, &cfg)) == 0) {
5032                         /* save the data */
5033                         copy_sz = min_t(int, sizeof(LANPage1_t), data_sz);
5034                         memcpy(&ioc->lan_cnfg_page1, ppage1_alloc, copy_sz);
5035                 }
5036 
5037                 pci_free_consistent(ioc->pcidev, data_sz, (u8 *) ppage1_alloc, page1_dma);
5038 
5039                 /* FIXME!
5040                  *      Normalize endianness of structure data,
5041                  *      by byte-swapping all > 1 byte fields!
5042                  */
5043 
5044         }
5045 
5046         return rc;
5047 }
5048 
5049 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
5050 /**
5051  *      mptbase_sas_persist_operation - Perform operation on SAS Persistent Table
5052  *      @ioc: Pointer to MPT_ADAPTER structure
5053  *      @persist_opcode: see below
5054  *
5055  *      MPI_SAS_OP_CLEAR_NOT_PRESENT - Free all persist TargetID mappings for
5056  *              devices not currently present.
5057  *      MPI_SAS_OP_CLEAR_ALL_PERSISTENT - Clear al persist TargetID mappings
5058  *
5059  *      NOTE: Don't use not this function during interrupt time.
5060  *
5061  *      Returns 0 for success, non-zero error
5062  */
5063 
5064 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
5065 int
5066 mptbase_sas_persist_operation(MPT_ADAPTER *ioc, u8 persist_opcode)
5067 {
5068         SasIoUnitControlRequest_t       *sasIoUnitCntrReq;
5069         SasIoUnitControlReply_t         *sasIoUnitCntrReply;
5070         MPT_FRAME_HDR                   *mf = NULL;
5071         MPIHeader_t                     *mpi_hdr;
5072         int                             ret = 0;
5073         unsigned long                   timeleft;
5074 
5075         mutex_lock(&ioc->mptbase_cmds.mutex);
5076 
5077         /* init the internal cmd struct */
5078         memset(ioc->mptbase_cmds.reply, 0 , MPT_DEFAULT_FRAME_SIZE);
5079         INITIALIZE_MGMT_STATUS(ioc->mptbase_cmds.status)
5080 
5081         /* insure garbage is not sent to fw */
5082         switch(persist_opcode) {
5083 
5084         case MPI_SAS_OP_CLEAR_NOT_PRESENT:
5085         case MPI_SAS_OP_CLEAR_ALL_PERSISTENT:
5086                 break;
5087 
5088         default:
5089                 ret = -1;
5090                 goto out;
5091         }
5092 
5093         printk(KERN_DEBUG  "%s: persist_opcode=%x\n",
5094                 __func__, persist_opcode);
5095 
5096         /* Get a MF for this command.
5097          */
5098         if ((mf = mpt_get_msg_frame(mpt_base_index, ioc)) == NULL) {
5099                 printk(KERN_DEBUG "%s: no msg frames!\n", __func__);
5100                 ret = -1;
5101                 goto out;
5102         }
5103 
5104         mpi_hdr = (MPIHeader_t *) mf;
5105         sasIoUnitCntrReq = (SasIoUnitControlRequest_t *)mf;
5106         memset(sasIoUnitCntrReq,0,sizeof(SasIoUnitControlRequest_t));
5107         sasIoUnitCntrReq->Function = MPI_FUNCTION_SAS_IO_UNIT_CONTROL;
5108         sasIoUnitCntrReq->MsgContext = mpi_hdr->MsgContext;
5109         sasIoUnitCntrReq->Operation = persist_opcode;
5110 
5111         mpt_put_msg_frame(mpt_base_index, ioc, mf);
5112         timeleft = wait_for_completion_timeout(&ioc->mptbase_cmds.done, 10*HZ);
5113         if (!(ioc->mptbase_cmds.status & MPT_MGMT_STATUS_COMMAND_GOOD)) {
5114                 ret = -ETIME;
5115                 printk(KERN_DEBUG "%s: failed\n", __func__);
5116                 if (ioc->mptbase_cmds.status & MPT_MGMT_STATUS_DID_IOCRESET)
5117                         goto out;
5118                 if (!timeleft) {
5119                         printk(MYIOC_s_WARN_FMT
5120                                "Issuing Reset from %s!!, doorbell=0x%08x\n",
5121                                ioc->name, __func__, mpt_GetIocState(ioc, 0));
5122                         mpt_Soft_Hard_ResetHandler(ioc, CAN_SLEEP);
5123                         mpt_free_msg_frame(ioc, mf);
5124                 }
5125                 goto out;
5126         }
5127 
5128         if (!(ioc->mptbase_cmds.status & MPT_MGMT_STATUS_RF_VALID)) {
5129                 ret = -1;
5130                 goto out;
5131         }
5132 
5133         sasIoUnitCntrReply =
5134             (SasIoUnitControlReply_t *)ioc->mptbase_cmds.reply;
5135         if (le16_to_cpu(sasIoUnitCntrReply->IOCStatus) != MPI_IOCSTATUS_SUCCESS) {
5136                 printk(KERN_DEBUG "%s: IOCStatus=0x%X IOCLogInfo=0x%X\n",
5137                     __func__, sasIoUnitCntrReply->IOCStatus,
5138                     sasIoUnitCntrReply->IOCLogInfo);
5139                 printk(KERN_DEBUG "%s: failed\n", __func__);
5140                 ret = -1;
5141         } else
5142                 printk(KERN_DEBUG "%s: success\n", __func__);
5143  out:
5144 
5145         CLEAR_MGMT_STATUS(ioc->mptbase_cmds.status)
5146         mutex_unlock(&ioc->mptbase_cmds.mutex);
5147         return ret;
5148 }
5149 
5150 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
5151 
5152 static void
5153 mptbase_raid_process_event_data(MPT_ADAPTER *ioc,
5154     MpiEventDataRaid_t * pRaidEventData)
5155 {
5156         int     volume;
5157         int     reason;
5158         int     disk;
5159         int     status;
5160         int     flags;
5161         int     state;
5162 
5163         volume  = pRaidEventData->VolumeID;
5164         reason  = pRaidEventData->ReasonCode;
5165         disk    = pRaidEventData->PhysDiskNum;
5166         status  = le32_to_cpu(pRaidEventData->SettingsStatus);
5167         flags   = (status >> 0) & 0xff;
5168         state   = (status >> 8) & 0xff;
5169 
5170         if (reason == MPI_EVENT_RAID_RC_DOMAIN_VAL_NEEDED) {
5171                 return;
5172         }
5173 
5174         if ((reason >= MPI_EVENT_RAID_RC_PHYSDISK_CREATED &&
5175              reason <= MPI_EVENT_RAID_RC_PHYSDISK_STATUS_CHANGED) ||
5176             (reason == MPI_EVENT_RAID_RC_SMART_DATA)) {
5177                 printk(MYIOC_s_INFO_FMT "RAID STATUS CHANGE for PhysDisk %d id=%d\n",
5178                         ioc->name, disk, volume);
5179         } else {
5180                 printk(MYIOC_s_INFO_FMT "RAID STATUS CHANGE for VolumeID %d\n",
5181                         ioc->name, volume);
5182         }
5183 
5184         switch(reason) {
5185         case MPI_EVENT_RAID_RC_VOLUME_CREATED:
5186                 printk(MYIOC_s_INFO_FMT "  volume has been created\n",
5187                         ioc->name);
5188                 break;
5189 
5190         case MPI_EVENT_RAID_RC_VOLUME_DELETED:
5191 
5192                 printk(MYIOC_s_INFO_FMT "  volume has been deleted\n",
5193                         ioc->name);
5194                 break;
5195 
5196         case MPI_EVENT_RAID_RC_VOLUME_SETTINGS_CHANGED:
5197                 printk(MYIOC_s_INFO_FMT "  volume settings have been changed\n",
5198                         ioc->name);
5199                 break;
5200 
5201         case MPI_EVENT_RAID_RC_VOLUME_STATUS_CHANGED:
5202                 printk(MYIOC_s_INFO_FMT "  volume is now %s%s%s%s\n",
5203                         ioc->name,
5204                         state == MPI_RAIDVOL0_STATUS_STATE_OPTIMAL
5205                          ? "optimal"
5206                          : state == MPI_RAIDVOL0_STATUS_STATE_DEGRADED
5207                           ? "degraded"
5208                           : state == MPI_RAIDVOL0_STATUS_STATE_FAILED
5209                            ? "failed"
5210                            : "state unknown",
5211                         flags & MPI_RAIDVOL0_STATUS_FLAG_ENABLED
5212                          ? ", enabled" : "",
5213                         flags & MPI_RAIDVOL0_STATUS_FLAG_QUIESCED
5214                          ? ", quiesced" : "",
5215                         flags & MPI_RAIDVOL0_STATUS_FLAG_RESYNC_IN_PROGRESS
5216                          ? ", resync in progress" : "" );
5217                 break;
5218 
5219         case MPI_EVENT_RAID_RC_VOLUME_PHYSDISK_CHANGED:
5220                 printk(MYIOC_s_INFO_FMT "  volume membership of PhysDisk %d has changed\n",
5221                         ioc->name, disk);
5222                 break;
5223 
5224         case MPI_EVENT_RAID_RC_PHYSDISK_CREATED:
5225                 printk(MYIOC_s_INFO_FMT "  PhysDisk has been created\n",
5226                         ioc->name);
5227                 break;
5228 
5229         case MPI_EVENT_RAID_RC_PHYSDISK_DELETED:
5230                 printk(MYIOC_s_INFO_FMT "  PhysDisk has been deleted\n",
5231                         ioc->name);
5232                 break;
5233 
5234         case MPI_EVENT_RAID_RC_PHYSDISK_SETTINGS_CHANGED:
5235                 printk(MYIOC_s_INFO_FMT "  PhysDisk settings have been changed\n",
5236                         ioc->name);
5237                 break;
5238 
5239         case MPI_EVENT_RAID_RC_PHYSDISK_STATUS_CHANGED:
5240                 printk(MYIOC_s_INFO_FMT "  PhysDisk is now %s%s%s\n",
5241                         ioc->name,
5242                         state == MPI_PHYSDISK0_STATUS_ONLINE
5243                          ? "online"
5244                          : state == MPI_PHYSDISK0_STATUS_MISSING
5245                           ? "missing"
5246                           : state == MPI_PHYSDISK0_STATUS_NOT_COMPATIBLE
5247                            ? "not compatible"
5248                            : state == MPI_PHYSDISK0_STATUS_FAILED
5249                             ? "failed"
5250                             : state == MPI_PHYSDISK0_STATUS_INITIALIZING
5251                              ? "initializing"
5252                              : state == MPI_PHYSDISK0_STATUS_OFFLINE_REQUESTED
5253                               ? "offline requested"
5254                               : state == MPI_PHYSDISK0_STATUS_FAILED_REQUESTED
5255                                ? "failed requested"
5256                                : state == MPI_PHYSDISK0_STATUS_OTHER_OFFLINE
5257                                 ? "offline"
5258                                 : "state unknown",
5259                         flags & MPI_PHYSDISK0_STATUS_FLAG_OUT_OF_SYNC
5260                          ? ", out of sync" : "",
5261                         flags & MPI_PHYSDISK0_STATUS_FLAG_QUIESCED
5262                          ? ", quiesced" : "" );
5263                 break;
5264 
5265         case MPI_EVENT_RAID_RC_DOMAIN_VAL_NEEDED:
5266                 printk(MYIOC_s_INFO_FMT "  Domain Validation needed for PhysDisk %d\n",
5267                         ioc->name, disk);
5268                 break;
5269 
5270         case MPI_EVENT_RAID_RC_SMART_DATA:
5271                 printk(MYIOC_s_INFO_FMT "  SMART data received, ASC/ASCQ = %02xh/%02xh\n",
5272                         ioc->name, pRaidEventData->ASC, pRaidEventData->ASCQ);
5273                 break;
5274 
5275         case MPI_EVENT_RAID_RC_REPLACE_ACTION_STARTED:
5276                 printk(MYIOC_s_INFO_FMT "  replacement of PhysDisk %d has started\n",
5277                         ioc->name, disk);
5278                 break;
5279         }
5280 }
5281 
5282 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
5283 /**
5284  *      GetIoUnitPage2 - Retrieve BIOS version and boot order information.
5285  *      @ioc: Pointer to MPT_ADAPTER structure
5286  *
5287  *      Returns: 0 for success
5288  *      -ENOMEM if no memory available
5289  *              -EPERM if not allowed due to ISR context
5290  *              -EAGAIN if no msg frames currently available
5291  *              -EFAULT for non-successful reply or no reply (timeout)
5292  */
5293 static int
5294 GetIoUnitPage2(MPT_ADAPTER *ioc)
5295 {
5296         ConfigPageHeader_t       hdr;
5297         CONFIGPARMS              cfg;
5298         IOUnitPage2_t           *ppage_alloc;
5299         dma_addr_t               page_dma;
5300         int                      data_sz;
5301         int                      rc;
5302 
5303         /* Get the page header */
5304         hdr.PageVersion = 0;
5305         hdr.PageLength = 0;
5306         hdr.PageNumber = 2;
5307         hdr.PageType = MPI_CONFIG_PAGETYPE_IO_UNIT;
5308         cfg.cfghdr.hdr = &hdr;
5309         cfg.physAddr = -1;
5310         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5311         cfg.dir = 0;
5312         cfg.pageAddr = 0;
5313         cfg.timeout = 0;
5314 
5315         if ((rc = mpt_config(ioc, &cfg)) != 0)
5316                 return rc;
5317 
5318         if (hdr.PageLength == 0)
5319                 return 0;
5320 
5321         /* Read the config page */
5322         data_sz = hdr.PageLength * 4;
5323         rc = -ENOMEM;
5324         ppage_alloc = (IOUnitPage2_t *) pci_alloc_consistent(ioc->pcidev, data_sz, &page_dma);
5325         if (ppage_alloc) {
5326                 memset((u8 *)ppage_alloc, 0, data_sz);
5327                 cfg.physAddr = page_dma;
5328                 cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5329 
5330                 /* If Good, save data */
5331                 if ((rc = mpt_config(ioc, &cfg)) == 0)
5332                         ioc->biosVersion = le32_to_cpu(ppage_alloc->BiosVersion);
5333 
5334                 pci_free_consistent(ioc->pcidev, data_sz, (u8 *) ppage_alloc, page_dma);
5335         }
5336 
5337         return rc;
5338 }
5339 
5340 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
5341 /**
5342  *      mpt_GetScsiPortSettings - read SCSI Port Page 0 and 2
5343  *      @ioc: Pointer to a Adapter Strucutre
5344  *      @portnum: IOC port number
5345  *
5346  *      Return: -EFAULT if read of config page header fails
5347  *                      or if no nvram
5348  *      If read of SCSI Port Page 0 fails,
5349  *              NVRAM = MPT_HOST_NVRAM_INVALID  (0xFFFFFFFF)
5350  *              Adapter settings: async, narrow
5351  *              Return 1
5352  *      If read of SCSI Port Page 2 fails,
5353  *              Adapter settings valid
5354  *              NVRAM = MPT_HOST_NVRAM_INVALID  (0xFFFFFFFF)
5355  *              Return 1
5356  *      Else
5357  *              Both valid
5358  *              Return 0
5359  *      CHECK - what type of locking mechanisms should be used????
5360  */
5361 static int
5362 mpt_GetScsiPortSettings(MPT_ADAPTER *ioc, int portnum)
5363 {
5364         u8                      *pbuf;
5365         dma_addr_t               buf_dma;
5366         CONFIGPARMS              cfg;
5367         ConfigPageHeader_t       header;
5368         int                      ii;
5369         int                      data, rc = 0;
5370 
5371         /* Allocate memory
5372          */
5373         if (!ioc->spi_data.nvram) {
5374                 int      sz;
5375                 u8      *mem;
5376                 sz = MPT_MAX_SCSI_DEVICES * sizeof(int);
5377                 mem = kmalloc(sz, GFP_ATOMIC);
5378                 if (mem == NULL)
5379                         return -EFAULT;
5380 
5381                 ioc->spi_data.nvram = (int *) mem;
5382 
5383                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "SCSI device NVRAM settings @ %p, sz=%d\n",
5384                         ioc->name, ioc->spi_data.nvram, sz));
5385         }
5386 
5387         /* Invalidate NVRAM information
5388          */
5389         for (ii=0; ii < MPT_MAX_SCSI_DEVICES; ii++) {
5390                 ioc->spi_data.nvram[ii] = MPT_HOST_NVRAM_INVALID;
5391         }
5392 
5393         /* Read SPP0 header, allocate memory, then read page.
5394          */
5395         header.PageVersion = 0;
5396         header.PageLength = 0;
5397         header.PageNumber = 0;
5398         header.PageType = MPI_CONFIG_PAGETYPE_SCSI_PORT;
5399         cfg.cfghdr.hdr = &header;
5400         cfg.physAddr = -1;
5401         cfg.pageAddr = portnum;
5402         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5403         cfg.dir = 0;
5404         cfg.timeout = 0;        /* use default */
5405         if (mpt_config(ioc, &cfg) != 0)
5406                  return -EFAULT;
5407 
5408         if (header.PageLength > 0) {
5409                 pbuf = pci_alloc_consistent(ioc->pcidev, header.PageLength * 4, &buf_dma);
5410                 if (pbuf) {
5411                         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5412                         cfg.physAddr = buf_dma;
5413                         if (mpt_config(ioc, &cfg) != 0) {
5414                                 ioc->spi_data.maxBusWidth = MPT_NARROW;
5415                                 ioc->spi_data.maxSyncOffset = 0;
5416                                 ioc->spi_data.minSyncFactor = MPT_ASYNC;
5417                                 ioc->spi_data.busType = MPT_HOST_BUS_UNKNOWN;
5418                                 rc = 1;
5419                                 ddvprintk(ioc, printk(MYIOC_s_DEBUG_FMT
5420                                         "Unable to read PortPage0 minSyncFactor=%x\n",
5421                                         ioc->name, ioc->spi_data.minSyncFactor));
5422                         } else {
5423                                 /* Save the Port Page 0 data
5424                                  */
5425                                 SCSIPortPage0_t  *pPP0 = (SCSIPortPage0_t  *) pbuf;
5426                                 pPP0->Capabilities = le32_to_cpu(pPP0->Capabilities);
5427                                 pPP0->PhysicalInterface = le32_to_cpu(pPP0->PhysicalInterface);
5428 
5429                                 if ( (pPP0->Capabilities & MPI_SCSIPORTPAGE0_CAP_QAS) == 0 ) {
5430                                         ioc->spi_data.noQas |= MPT_TARGET_NO_NEGO_QAS;
5431                                         ddvprintk(ioc, printk(MYIOC_s_DEBUG_FMT
5432                                                 "noQas due to Capabilities=%x\n",
5433                                                 ioc->name, pPP0->Capabilities));
5434                                 }
5435                                 ioc->spi_data.maxBusWidth = pPP0->Capabilities & MPI_SCSIPORTPAGE0_CAP_WIDE ? 1 : 0;
5436                                 data = pPP0->Capabilities & MPI_SCSIPORTPAGE0_CAP_MAX_SYNC_OFFSET_MASK;
5437                                 if (data) {
5438                                         ioc->spi_data.maxSyncOffset = (u8) (data >> 16);
5439                                         data = pPP0->Capabilities & MPI_SCSIPORTPAGE0_CAP_MIN_SYNC_PERIOD_MASK;
5440                                         ioc->spi_data.minSyncFactor = (u8) (data >> 8);
5441                                         ddvprintk(ioc, printk(MYIOC_s_DEBUG_FMT
5442                                                 "PortPage0 minSyncFactor=%x\n",
5443                                                 ioc->name, ioc->spi_data.minSyncFactor));
5444                                 } else {
5445                                         ioc->spi_data.maxSyncOffset = 0;
5446                                         ioc->spi_data.minSyncFactor = MPT_ASYNC;
5447                                 }
5448 
5449                                 ioc->spi_data.busType = pPP0->PhysicalInterface & MPI_SCSIPORTPAGE0_PHY_SIGNAL_TYPE_MASK;
5450 
5451                                 /* Update the minSyncFactor based on bus type.
5452                                  */
5453                                 if ((ioc->spi_data.busType == MPI_SCSIPORTPAGE0_PHY_SIGNAL_HVD) ||
5454                                         (ioc->spi_data.busType == MPI_SCSIPORTPAGE0_PHY_SIGNAL_SE))  {
5455 
5456                                         if (ioc->spi_data.minSyncFactor < MPT_ULTRA) {
5457                                                 ioc->spi_data.minSyncFactor = MPT_ULTRA;
5458                                                 ddvprintk(ioc, printk(MYIOC_s_DEBUG_FMT
5459                                                         "HVD or SE detected, minSyncFactor=%x\n",
5460                                                         ioc->name, ioc->spi_data.minSyncFactor));
5461                                         }
5462                                 }
5463                         }
5464                         if (pbuf) {
5465                                 pci_free_consistent(ioc->pcidev, header.PageLength * 4, pbuf, buf_dma);
5466                         }
5467                 }
5468         }
5469 
5470         /* SCSI Port Page 2 - Read the header then the page.
5471          */
5472         header.PageVersion = 0;
5473         header.PageLength = 0;
5474         header.PageNumber = 2;
5475         header.PageType = MPI_CONFIG_PAGETYPE_SCSI_PORT;
5476         cfg.cfghdr.hdr = &header;
5477         cfg.physAddr = -1;
5478         cfg.pageAddr = portnum;
5479         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5480         cfg.dir = 0;
5481         if (mpt_config(ioc, &cfg) != 0)
5482                 return -EFAULT;
5483 
5484         if (header.PageLength > 0) {
5485                 /* Allocate memory and read SCSI Port Page 2
5486                  */
5487                 pbuf = pci_alloc_consistent(ioc->pcidev, header.PageLength * 4, &buf_dma);
5488                 if (pbuf) {
5489                         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_NVRAM;
5490                         cfg.physAddr = buf_dma;
5491                         if (mpt_config(ioc, &cfg) != 0) {
5492                                 /* Nvram data is left with INVALID mark
5493                                  */
5494                                 rc = 1;
5495                         } else if (ioc->pcidev->vendor == PCI_VENDOR_ID_ATTO) {
5496 
5497                                 /* This is an ATTO adapter, read Page2 accordingly
5498                                 */
5499                                 ATTO_SCSIPortPage2_t *pPP2 = (ATTO_SCSIPortPage2_t  *) pbuf;
5500                                 ATTODeviceInfo_t *pdevice = NULL;
5501                                 u16 ATTOFlags;
5502 
5503                                 /* Save the Port Page 2 data
5504                                  * (reformat into a 32bit quantity)
5505                                  */
5506                                 for (ii=0; ii < MPT_MAX_SCSI_DEVICES; ii++) {
5507                                   pdevice = &pPP2->DeviceSettings[ii];
5508                                   ATTOFlags = le16_to_cpu(pdevice->ATTOFlags);
5509                                   data = 0;
5510 
5511                                   /* Translate ATTO device flags to LSI format
5512                                    */
5513                                   if (ATTOFlags & ATTOFLAG_DISC)
5514                                     data |= (MPI_SCSIPORTPAGE2_DEVICE_DISCONNECT_ENABLE);
5515                                   if (ATTOFlags & ATTOFLAG_ID_ENB)
5516                                     data |= (MPI_SCSIPORTPAGE2_DEVICE_ID_SCAN_ENABLE);
5517                                   if (ATTOFlags & ATTOFLAG_LUN_ENB)
5518                                     data |= (MPI_SCSIPORTPAGE2_DEVICE_LUN_SCAN_ENABLE);
5519                                   if (ATTOFlags & ATTOFLAG_TAGGED)
5520                                     data |= (MPI_SCSIPORTPAGE2_DEVICE_TAG_QUEUE_ENABLE);
5521                                   if (!(ATTOFlags & ATTOFLAG_WIDE_ENB))
5522                                     data |= (MPI_SCSIPORTPAGE2_DEVICE_WIDE_DISABLE);
5523 
5524                                   data = (data << 16) | (pdevice->Period << 8) | 10;
5525                                   ioc->spi_data.nvram[ii] = data;
5526                                 }
5527                         } else {
5528                                 SCSIPortPage2_t *pPP2 = (SCSIPortPage2_t  *) pbuf;
5529                                 MpiDeviceInfo_t *pdevice = NULL;
5530 
5531                                 /*
5532                                  * Save "Set to Avoid SCSI Bus Resets" flag
5533                                  */
5534                                 ioc->spi_data.bus_reset =
5535                                     (le32_to_cpu(pPP2->PortFlags) &
5536                                 MPI_SCSIPORTPAGE2_PORT_FLAGS_AVOID_SCSI_RESET) ?
5537                                     0 : 1 ;
5538 
5539                                 /* Save the Port Page 2 data
5540                                  * (reformat into a 32bit quantity)
5541                                  */
5542                                 data = le32_to_cpu(pPP2->PortFlags) & MPI_SCSIPORTPAGE2_PORT_FLAGS_DV_MASK;
5543                                 ioc->spi_data.PortFlags = data;
5544                                 for (ii=0; ii < MPT_MAX_SCSI_DEVICES; ii++) {
5545                                         pdevice = &pPP2->DeviceSettings[ii];
5546                                         data = (le16_to_cpu(pdevice->DeviceFlags) << 16) |
5547                                                 (pdevice->SyncFactor << 8) | pdevice->Timeout;
5548                                         ioc->spi_data.nvram[ii] = data;
5549                                 }
5550                         }
5551 
5552                         pci_free_consistent(ioc->pcidev, header.PageLength * 4, pbuf, buf_dma);
5553                 }
5554         }
5555 
5556         /* Update Adapter limits with those from NVRAM
5557          * Comment: Don't need to do this. Target performance
5558          * parameters will never exceed the adapters limits.
5559          */
5560 
5561         return rc;
5562 }
5563 
5564 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
5565 /**
5566  *      mpt_readScsiDevicePageHeaders - save version and length of SDP1
5567  *      @ioc: Pointer to a Adapter Strucutre
5568  *      @portnum: IOC port number
5569  *
5570  *      Return: -EFAULT if read of config page header fails
5571  *              or 0 if success.
5572  */
5573 static int
5574 mpt_readScsiDevicePageHeaders(MPT_ADAPTER *ioc, int portnum)
5575 {
5576         CONFIGPARMS              cfg;
5577         ConfigPageHeader_t       header;
5578 
5579         /* Read the SCSI Device Page 1 header
5580          */
5581         header.PageVersion = 0;
5582         header.PageLength = 0;
5583         header.PageNumber = 1;
5584         header.PageType = MPI_CONFIG_PAGETYPE_SCSI_DEVICE;
5585         cfg.cfghdr.hdr = &header;
5586         cfg.physAddr = -1;
5587         cfg.pageAddr = portnum;
5588         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5589         cfg.dir = 0;
5590         cfg.timeout = 0;
5591         if (mpt_config(ioc, &cfg) != 0)
5592                  return -EFAULT;
5593 
5594         ioc->spi_data.sdp1version = cfg.cfghdr.hdr->PageVersion;
5595         ioc->spi_data.sdp1length = cfg.cfghdr.hdr->PageLength;
5596 
5597         header.PageVersion = 0;
5598         header.PageLength = 0;
5599         header.PageNumber = 0;
5600         header.PageType = MPI_CONFIG_PAGETYPE_SCSI_DEVICE;
5601         if (mpt_config(ioc, &cfg) != 0)
5602                  return -EFAULT;
5603 
5604         ioc->spi_data.sdp0version = cfg.cfghdr.hdr->PageVersion;
5605         ioc->spi_data.sdp0length = cfg.cfghdr.hdr->PageLength;
5606 
5607         dcprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Headers: 0: version %d length %d\n",
5608                         ioc->name, ioc->spi_data.sdp0version, ioc->spi_data.sdp0length));
5609 
5610         dcprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Headers: 1: version %d length %d\n",
5611                         ioc->name, ioc->spi_data.sdp1version, ioc->spi_data.sdp1length));
5612         return 0;
5613 }
5614 
5615 /**
5616  * mpt_inactive_raid_list_free - This clears this link list.
5617  * @ioc : pointer to per adapter structure
5618  **/
5619 static void
5620 mpt_inactive_raid_list_free(MPT_ADAPTER *ioc)
5621 {
5622         struct inactive_raid_component_info *component_info, *pNext;
5623 
5624         if (list_empty(&ioc->raid_data.inactive_list))
5625                 return;
5626 
5627         mutex_lock(&ioc->raid_data.inactive_list_mutex);
5628         list_for_each_entry_safe(component_info, pNext,
5629             &ioc->raid_data.inactive_list, list) {
5630                 list_del(&component_info->list);
5631                 kfree(component_info);
5632         }
5633         mutex_unlock(&ioc->raid_data.inactive_list_mutex);
5634 }
5635 
5636 /**
5637  * mpt_inactive_raid_volumes - sets up link list of phy_disk_nums for devices belonging in an inactive volume
5638  *
5639  * @ioc : pointer to per adapter structure
5640  * @channel : volume channel
5641  * @id : volume target id
5642  **/
5643 static void
5644 mpt_inactive_raid_volumes(MPT_ADAPTER *ioc, u8 channel, u8 id)
5645 {
5646         CONFIGPARMS                     cfg;
5647         ConfigPageHeader_t              hdr;
5648         dma_addr_t                      dma_handle;
5649         pRaidVolumePage0_t              buffer = NULL;
5650         int                             i;
5651         RaidPhysDiskPage0_t             phys_disk;
5652         struct inactive_raid_component_info *component_info;
5653         int                             handle_inactive_volumes;
5654 
5655         memset(&cfg, 0 , sizeof(CONFIGPARMS));
5656         memset(&hdr, 0 , sizeof(ConfigPageHeader_t));
5657         hdr.PageType = MPI_CONFIG_PAGETYPE_RAID_VOLUME;
5658         cfg.pageAddr = (channel << 8) + id;
5659         cfg.cfghdr.hdr = &hdr;
5660         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5661 
5662         if (mpt_config(ioc, &cfg) != 0)
5663                 goto out;
5664 
5665         if (!hdr.PageLength)
5666                 goto out;
5667 
5668         buffer = pci_alloc_consistent(ioc->pcidev, hdr.PageLength * 4,
5669             &dma_handle);
5670 
5671         if (!buffer)
5672                 goto out;
5673 
5674         cfg.physAddr = dma_handle;
5675         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5676 
5677         if (mpt_config(ioc, &cfg) != 0)
5678                 goto out;
5679 
5680         if (!buffer->NumPhysDisks)
5681                 goto out;
5682 
5683         handle_inactive_volumes =
5684            (buffer->VolumeStatus.Flags & MPI_RAIDVOL0_STATUS_FLAG_VOLUME_INACTIVE ||
5685            (buffer->VolumeStatus.Flags & MPI_RAIDVOL0_STATUS_FLAG_ENABLED) == 0 ||
5686             buffer->VolumeStatus.State == MPI_RAIDVOL0_STATUS_STATE_FAILED ||
5687             buffer->VolumeStatus.State == MPI_RAIDVOL0_STATUS_STATE_MISSING) ? 1 : 0;
5688 
5689         if (!handle_inactive_volumes)
5690                 goto out;
5691 
5692         mutex_lock(&ioc->raid_data.inactive_list_mutex);
5693         for (i = 0; i < buffer->NumPhysDisks; i++) {
5694                 if(mpt_raid_phys_disk_pg0(ioc,
5695                     buffer->PhysDisk[i].PhysDiskNum, &phys_disk) != 0)
5696                         continue;
5697 
5698                 if ((component_info = kmalloc(sizeof (*component_info),
5699                  GFP_KERNEL)) == NULL)
5700                         continue;
5701 
5702                 component_info->volumeID = id;
5703                 component_info->volumeBus = channel;
5704                 component_info->d.PhysDiskNum = phys_disk.PhysDiskNum;
5705                 component_info->d.PhysDiskBus = phys_disk.PhysDiskBus;
5706                 component_info->d.PhysDiskID = phys_disk.PhysDiskID;
5707                 component_info->d.PhysDiskIOC = phys_disk.PhysDiskIOC;
5708 
5709                 list_add_tail(&component_info->list,
5710                     &ioc->raid_data.inactive_list);
5711         }
5712         mutex_unlock(&ioc->raid_data.inactive_list_mutex);
5713 
5714  out:
5715         if (buffer)
5716                 pci_free_consistent(ioc->pcidev, hdr.PageLength * 4, buffer,
5717                     dma_handle);
5718 }
5719 
5720 /**
5721  *      mpt_raid_phys_disk_pg0 - returns phys disk page zero
5722  *      @ioc: Pointer to a Adapter Structure
5723  *      @phys_disk_num: io unit unique phys disk num generated by the ioc
5724  *      @phys_disk: requested payload data returned
5725  *
5726  *      Return:
5727  *      0 on success
5728  *      -EFAULT if read of config page header fails or data pointer not NULL
5729  *      -ENOMEM if pci_alloc failed
5730  **/
5731 int
5732 mpt_raid_phys_disk_pg0(MPT_ADAPTER *ioc, u8 phys_disk_num,
5733                         RaidPhysDiskPage0_t *phys_disk)
5734 {
5735         CONFIGPARMS                     cfg;
5736         ConfigPageHeader_t              hdr;
5737         dma_addr_t                      dma_handle;
5738         pRaidPhysDiskPage0_t            buffer = NULL;
5739         int                             rc;
5740 
5741         memset(&cfg, 0 , sizeof(CONFIGPARMS));
5742         memset(&hdr, 0 , sizeof(ConfigPageHeader_t));
5743         memset(phys_disk, 0, sizeof(RaidPhysDiskPage0_t));
5744 
5745         hdr.PageVersion = MPI_RAIDPHYSDISKPAGE0_PAGEVERSION;
5746         hdr.PageType = MPI_CONFIG_PAGETYPE_RAID_PHYSDISK;
5747         cfg.cfghdr.hdr = &hdr;
5748         cfg.physAddr = -1;
5749         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5750 
5751         if (mpt_config(ioc, &cfg) != 0) {
5752                 rc = -EFAULT;
5753                 goto out;
5754         }
5755 
5756         if (!hdr.PageLength) {
5757                 rc = -EFAULT;
5758                 goto out;
5759         }
5760 
5761         buffer = pci_alloc_consistent(ioc->pcidev, hdr.PageLength * 4,
5762             &dma_handle);
5763 
5764         if (!buffer) {
5765                 rc = -ENOMEM;
5766                 goto out;
5767         }
5768 
5769         cfg.physAddr = dma_handle;
5770         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5771         cfg.pageAddr = phys_disk_num;
5772 
5773         if (mpt_config(ioc, &cfg) != 0) {
5774                 rc = -EFAULT;
5775                 goto out;
5776         }
5777 
5778         rc = 0;
5779         memcpy(phys_disk, buffer, sizeof(*buffer));
5780         phys_disk->MaxLBA = le32_to_cpu(buffer->MaxLBA);
5781 
5782  out:
5783 
5784         if (buffer)
5785                 pci_free_consistent(ioc->pcidev, hdr.PageLength * 4, buffer,
5786                     dma_handle);
5787 
5788         return rc;
5789 }
5790 
5791 /**
5792  *      mpt_raid_phys_disk_get_num_paths - returns number paths associated to this phys_num
5793  *      @ioc: Pointer to a Adapter Structure
5794  *      @phys_disk_num: io unit unique phys disk num generated by the ioc
5795  *
5796  *      Return:
5797  *      returns number paths
5798  **/
5799 int
5800 mpt_raid_phys_disk_get_num_paths(MPT_ADAPTER *ioc, u8 phys_disk_num)
5801 {
5802         CONFIGPARMS                     cfg;
5803         ConfigPageHeader_t              hdr;
5804         dma_addr_t                      dma_handle;
5805         pRaidPhysDiskPage1_t            buffer = NULL;
5806         int                             rc;
5807 
5808         memset(&cfg, 0 , sizeof(CONFIGPARMS));
5809         memset(&hdr, 0 , sizeof(ConfigPageHeader_t));
5810 
5811         hdr.PageVersion = MPI_RAIDPHYSDISKPAGE1_PAGEVERSION;
5812         hdr.PageType = MPI_CONFIG_PAGETYPE_RAID_PHYSDISK;
5813         hdr.PageNumber = 1;
5814         cfg.cfghdr.hdr = &hdr;
5815         cfg.physAddr = -1;
5816         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5817 
5818         if (mpt_config(ioc, &cfg) != 0) {
5819                 rc = 0;
5820                 goto out;
5821         }
5822 
5823         if (!hdr.PageLength) {
5824                 rc = 0;
5825                 goto out;
5826         }
5827 
5828         buffer = pci_alloc_consistent(ioc->pcidev, hdr.PageLength * 4,
5829             &dma_handle);
5830 
5831         if (!buffer) {
5832                 rc = 0;
5833                 goto out;
5834         }
5835 
5836         cfg.physAddr = dma_handle;
5837         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5838         cfg.pageAddr = phys_disk_num;
5839 
5840         if (mpt_config(ioc, &cfg) != 0) {
5841                 rc = 0;
5842                 goto out;
5843         }
5844 
5845         rc = buffer->NumPhysDiskPaths;
5846  out:
5847 
5848         if (buffer)
5849                 pci_free_consistent(ioc->pcidev, hdr.PageLength * 4, buffer,
5850                     dma_handle);
5851 
5852         return rc;
5853 }
5854 EXPORT_SYMBOL(mpt_raid_phys_disk_get_num_paths);
5855 
5856 /**
5857  *      mpt_raid_phys_disk_pg1 - returns phys disk page 1
5858  *      @ioc: Pointer to a Adapter Structure
5859  *      @phys_disk_num: io unit unique phys disk num generated by the ioc
5860  *      @phys_disk: requested payload data returned
5861  *
5862  *      Return:
5863  *      0 on success
5864  *      -EFAULT if read of config page header fails or data pointer not NULL
5865  *      -ENOMEM if pci_alloc failed
5866  **/
5867 int
5868 mpt_raid_phys_disk_pg1(MPT_ADAPTER *ioc, u8 phys_disk_num,
5869                 RaidPhysDiskPage1_t *phys_disk)
5870 {
5871         CONFIGPARMS                     cfg;
5872         ConfigPageHeader_t              hdr;
5873         dma_addr_t                      dma_handle;
5874         pRaidPhysDiskPage1_t            buffer = NULL;
5875         int                             rc;
5876         int                             i;
5877         __le64                          sas_address;
5878 
5879         memset(&cfg, 0 , sizeof(CONFIGPARMS));
5880         memset(&hdr, 0 , sizeof(ConfigPageHeader_t));
5881         rc = 0;
5882 
5883         hdr.PageVersion = MPI_RAIDPHYSDISKPAGE1_PAGEVERSION;
5884         hdr.PageType = MPI_CONFIG_PAGETYPE_RAID_PHYSDISK;
5885         hdr.PageNumber = 1;
5886         cfg.cfghdr.hdr = &hdr;
5887         cfg.physAddr = -1;
5888         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5889 
5890         if (mpt_config(ioc, &cfg) != 0) {
5891                 rc = -EFAULT;
5892                 goto out;
5893         }
5894 
5895         if (!hdr.PageLength) {
5896                 rc = -EFAULT;
5897                 goto out;
5898         }
5899 
5900         buffer = pci_alloc_consistent(ioc->pcidev, hdr.PageLength * 4,
5901             &dma_handle);
5902 
5903         if (!buffer) {
5904                 rc = -ENOMEM;
5905                 goto out;
5906         }
5907 
5908         cfg.physAddr = dma_handle;
5909         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
5910         cfg.pageAddr = phys_disk_num;
5911 
5912         if (mpt_config(ioc, &cfg) != 0) {
5913                 rc = -EFAULT;
5914                 goto out;
5915         }
5916 
5917         phys_disk->NumPhysDiskPaths = buffer->NumPhysDiskPaths;
5918         phys_disk->PhysDiskNum = phys_disk_num;
5919         for (i = 0; i < phys_disk->NumPhysDiskPaths; i++) {
5920                 phys_disk->Path[i].PhysDiskID = buffer->Path[i].PhysDiskID;
5921                 phys_disk->Path[i].PhysDiskBus = buffer->Path[i].PhysDiskBus;
5922                 phys_disk->Path[i].OwnerIdentifier =
5923                                 buffer->Path[i].OwnerIdentifier;
5924                 phys_disk->Path[i].Flags = le16_to_cpu(buffer->Path[i].Flags);
5925                 memcpy(&sas_address, &buffer->Path[i].WWID, sizeof(__le64));
5926                 sas_address = le64_to_cpu(sas_address);
5927                 memcpy(&phys_disk->Path[i].WWID, &sas_address, sizeof(__le64));
5928                 memcpy(&sas_address,
5929                                 &buffer->Path[i].OwnerWWID, sizeof(__le64));
5930                 sas_address = le64_to_cpu(sas_address);
5931                 memcpy(&phys_disk->Path[i].OwnerWWID,
5932                                 &sas_address, sizeof(__le64));
5933         }
5934 
5935  out:
5936 
5937         if (buffer)
5938                 pci_free_consistent(ioc->pcidev, hdr.PageLength * 4, buffer,
5939                     dma_handle);
5940 
5941         return rc;
5942 }
5943 EXPORT_SYMBOL(mpt_raid_phys_disk_pg1);
5944 
5945 
5946 /**
5947  *      mpt_findImVolumes - Identify IDs of hidden disks and RAID Volumes
5948  *      @ioc: Pointer to a Adapter Strucutre
5949  *
5950  *      Return:
5951  *      0 on success
5952  *      -EFAULT if read of config page header fails or data pointer not NULL
5953  *      -ENOMEM if pci_alloc failed
5954  **/
5955 int
5956 mpt_findImVolumes(MPT_ADAPTER *ioc)
5957 {
5958         IOCPage2_t              *pIoc2;
5959         u8                      *mem;
5960         dma_addr_t               ioc2_dma;
5961         CONFIGPARMS              cfg;
5962         ConfigPageHeader_t       header;
5963         int                      rc = 0;
5964         int                      iocpage2sz;
5965         int                      i;
5966 
5967         if (!ioc->ir_firmware)
5968                 return 0;
5969 
5970         /* Free the old page
5971          */
5972         kfree(ioc->raid_data.pIocPg2);
5973         ioc->raid_data.pIocPg2 = NULL;
5974         mpt_inactive_raid_list_free(ioc);
5975 
5976         /* Read IOCP2 header then the page.
5977          */
5978         header.PageVersion = 0;
5979         header.PageLength = 0;
5980         header.PageNumber = 2;
5981         header.PageType = MPI_CONFIG_PAGETYPE_IOC;
5982         cfg.cfghdr.hdr = &header;
5983         cfg.physAddr = -1;
5984         cfg.pageAddr = 0;
5985         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
5986         cfg.dir = 0;
5987         cfg.timeout = 0;
5988         if (mpt_config(ioc, &cfg) != 0)
5989                  return -EFAULT;
5990 
5991         if (header.PageLength == 0)
5992                 return -EFAULT;
5993 
5994         iocpage2sz = header.PageLength * 4;
5995         pIoc2 = pci_alloc_consistent(ioc->pcidev, iocpage2sz, &ioc2_dma);
5996         if (!pIoc2)
5997                 return -ENOMEM;
5998 
5999         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
6000         cfg.physAddr = ioc2_dma;
6001         if (mpt_config(ioc, &cfg) != 0)
6002                 goto out;
6003 
6004         mem = kmemdup(pIoc2, iocpage2sz, GFP_KERNEL);
6005         if (!mem) {
6006                 rc = -ENOMEM;
6007                 goto out;
6008         }
6009 
6010         ioc->raid_data.pIocPg2 = (IOCPage2_t *) mem;
6011 
6012         mpt_read_ioc_pg_3(ioc);
6013 
6014         for (i = 0; i < pIoc2->NumActiveVolumes ; i++)
6015                 mpt_inactive_raid_volumes(ioc,
6016                     pIoc2->RaidVolume[i].VolumeBus,
6017                     pIoc2->RaidVolume[i].VolumeID);
6018 
6019  out:
6020         pci_free_consistent(ioc->pcidev, iocpage2sz, pIoc2, ioc2_dma);
6021 
6022         return rc;
6023 }
6024 
6025 static int
6026 mpt_read_ioc_pg_3(MPT_ADAPTER *ioc)
6027 {
6028         IOCPage3_t              *pIoc3;
6029         u8                      *mem;
6030         CONFIGPARMS              cfg;
6031         ConfigPageHeader_t       header;
6032         dma_addr_t               ioc3_dma;
6033         int                      iocpage3sz = 0;
6034 
6035         /* Free the old page
6036          */
6037         kfree(ioc->raid_data.pIocPg3);
6038         ioc->raid_data.pIocPg3 = NULL;
6039 
6040         /* There is at least one physical disk.
6041          * Read and save IOC Page 3
6042          */
6043         header.PageVersion = 0;
6044         header.PageLength = 0;
6045         header.PageNumber = 3;
6046         header.PageType = MPI_CONFIG_PAGETYPE_IOC;
6047         cfg.cfghdr.hdr = &header;
6048         cfg.physAddr = -1;
6049         cfg.pageAddr = 0;
6050         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
6051         cfg.dir = 0;
6052         cfg.timeout = 0;
6053         if (mpt_config(ioc, &cfg) != 0)
6054                 return 0;
6055 
6056         if (header.PageLength == 0)
6057                 return 0;
6058 
6059         /* Read Header good, alloc memory
6060          */
6061         iocpage3sz = header.PageLength * 4;
6062         pIoc3 = pci_alloc_consistent(ioc->pcidev, iocpage3sz, &ioc3_dma);
6063         if (!pIoc3)
6064                 return 0;
6065 
6066         /* Read the Page and save the data
6067          * into malloc'd memory.
6068          */
6069         cfg.physAddr = ioc3_dma;
6070         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
6071         if (mpt_config(ioc, &cfg) == 0) {
6072                 mem = kmalloc(iocpage3sz, GFP_KERNEL);
6073                 if (mem) {
6074                         memcpy(mem, (u8 *)pIoc3, iocpage3sz);
6075                         ioc->raid_data.pIocPg3 = (IOCPage3_t *) mem;
6076                 }
6077         }
6078 
6079         pci_free_consistent(ioc->pcidev, iocpage3sz, pIoc3, ioc3_dma);
6080 
6081         return 0;
6082 }
6083 
6084 static void
6085 mpt_read_ioc_pg_4(MPT_ADAPTER *ioc)
6086 {
6087         IOCPage4_t              *pIoc4;
6088         CONFIGPARMS              cfg;
6089         ConfigPageHeader_t       header;
6090         dma_addr_t               ioc4_dma;
6091         int                      iocpage4sz;
6092 
6093         /* Read and save IOC Page 4
6094          */
6095         header.PageVersion = 0;
6096         header.PageLength = 0;
6097         header.PageNumber = 4;
6098         header.PageType = MPI_CONFIG_PAGETYPE_IOC;
6099         cfg.cfghdr.hdr = &header;
6100         cfg.physAddr = -1;
6101         cfg.pageAddr = 0;
6102         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
6103         cfg.dir = 0;
6104         cfg.timeout = 0;
6105         if (mpt_config(ioc, &cfg) != 0)
6106                 return;
6107 
6108         if (header.PageLength == 0)
6109                 return;
6110 
6111         if ( (pIoc4 = ioc->spi_data.pIocPg4) == NULL ) {
6112                 iocpage4sz = (header.PageLength + 4) * 4; /* Allow 4 additional SEP's */
6113                 pIoc4 = pci_alloc_consistent(ioc->pcidev, iocpage4sz, &ioc4_dma);
6114                 if (!pIoc4)
6115                         return;
6116                 ioc->alloc_total += iocpage4sz;
6117         } else {
6118                 ioc4_dma = ioc->spi_data.IocPg4_dma;
6119                 iocpage4sz = ioc->spi_data.IocPg4Sz;
6120         }
6121 
6122         /* Read the Page into dma memory.
6123          */
6124         cfg.physAddr = ioc4_dma;
6125         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
6126         if (mpt_config(ioc, &cfg) == 0) {
6127                 ioc->spi_data.pIocPg4 = (IOCPage4_t *) pIoc4;
6128                 ioc->spi_data.IocPg4_dma = ioc4_dma;
6129                 ioc->spi_data.IocPg4Sz = iocpage4sz;
6130         } else {
6131                 pci_free_consistent(ioc->pcidev, iocpage4sz, pIoc4, ioc4_dma);
6132                 ioc->spi_data.pIocPg4 = NULL;
6133                 ioc->alloc_total -= iocpage4sz;
6134         }
6135 }
6136 
6137 static void
6138 mpt_read_ioc_pg_1(MPT_ADAPTER *ioc)
6139 {
6140         IOCPage1_t              *pIoc1;
6141         CONFIGPARMS              cfg;
6142         ConfigPageHeader_t       header;
6143         dma_addr_t               ioc1_dma;
6144         int                      iocpage1sz = 0;
6145         u32                      tmp;
6146 
6147         /* Check the Coalescing Timeout in IOC Page 1
6148          */
6149         header.PageVersion = 0;
6150         header.PageLength = 0;
6151         header.PageNumber = 1;
6152         header.PageType = MPI_CONFIG_PAGETYPE_IOC;
6153         cfg.cfghdr.hdr = &header;
6154         cfg.physAddr = -1;
6155         cfg.pageAddr = 0;
6156         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
6157         cfg.dir = 0;
6158         cfg.timeout = 0;
6159         if (mpt_config(ioc, &cfg) != 0)
6160                 return;
6161 
6162         if (header.PageLength == 0)
6163                 return;
6164 
6165         /* Read Header good, alloc memory
6166          */
6167         iocpage1sz = header.PageLength * 4;
6168         pIoc1 = pci_alloc_consistent(ioc->pcidev, iocpage1sz, &ioc1_dma);
6169         if (!pIoc1)
6170                 return;
6171 
6172         /* Read the Page and check coalescing timeout
6173          */
6174         cfg.physAddr = ioc1_dma;
6175         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
6176         if (mpt_config(ioc, &cfg) == 0) {
6177 
6178                 tmp = le32_to_cpu(pIoc1->Flags) & MPI_IOCPAGE1_REPLY_COALESCING;
6179                 if (tmp == MPI_IOCPAGE1_REPLY_COALESCING) {
6180                         tmp = le32_to_cpu(pIoc1->CoalescingTimeout);
6181 
6182                         dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Coalescing Enabled Timeout = %d\n",
6183                                         ioc->name, tmp));
6184 
6185                         if (tmp > MPT_COALESCING_TIMEOUT) {
6186                                 pIoc1->CoalescingTimeout = cpu_to_le32(MPT_COALESCING_TIMEOUT);
6187 
6188                                 /* Write NVRAM and current
6189                                  */
6190                                 cfg.dir = 1;
6191                                 cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_CURRENT;
6192                                 if (mpt_config(ioc, &cfg) == 0) {
6193                                         dprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Reset Current Coalescing Timeout to = %d\n",
6194                                                         ioc->name, MPT_COALESCING_TIMEOUT));
6195 
6196                                         cfg.action = MPI_CONFIG_ACTION_PAGE_WRITE_NVRAM;
6197                                         if (mpt_config(ioc, &cfg) == 0) {
6198                                                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6199                                                                 "Reset NVRAM Coalescing Timeout to = %d\n",
6200                                                                 ioc->name, MPT_COALESCING_TIMEOUT));
6201                                         } else {
6202                                                 dprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6203                                                                 "Reset NVRAM Coalescing Timeout Failed\n",
6204                                                                 ioc->name));
6205                                         }
6206 
6207                                 } else {
6208                                         dprintk(ioc, printk(MYIOC_s_WARN_FMT
6209                                                 "Reset of Current Coalescing Timeout Failed!\n",
6210                                                 ioc->name));
6211                                 }
6212                         }
6213 
6214                 } else {
6215                         dprintk(ioc, printk(MYIOC_s_WARN_FMT "Coalescing Disabled\n", ioc->name));
6216                 }
6217         }
6218 
6219         pci_free_consistent(ioc->pcidev, iocpage1sz, pIoc1, ioc1_dma);
6220 
6221         return;
6222 }
6223 
6224 static void
6225 mpt_get_manufacturing_pg_0(MPT_ADAPTER *ioc)
6226 {
6227         CONFIGPARMS             cfg;
6228         ConfigPageHeader_t      hdr;
6229         dma_addr_t              buf_dma;
6230         ManufacturingPage0_t    *pbuf = NULL;
6231 
6232         memset(&cfg, 0 , sizeof(CONFIGPARMS));
6233         memset(&hdr, 0 , sizeof(ConfigPageHeader_t));
6234 
6235         hdr.PageType = MPI_CONFIG_PAGETYPE_MANUFACTURING;
6236         cfg.cfghdr.hdr = &hdr;
6237         cfg.physAddr = -1;
6238         cfg.action = MPI_CONFIG_ACTION_PAGE_HEADER;
6239         cfg.timeout = 10;
6240 
6241         if (mpt_config(ioc, &cfg) != 0)
6242                 goto out;
6243 
6244         if (!cfg.cfghdr.hdr->PageLength)
6245                 goto out;
6246 
6247         cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
6248         pbuf = pci_alloc_consistent(ioc->pcidev, hdr.PageLength * 4, &buf_dma);
6249         if (!pbuf)
6250                 goto out;
6251 
6252         cfg.physAddr = buf_dma;
6253 
6254         if (mpt_config(ioc, &cfg) != 0)
6255                 goto out;
6256 
6257         memcpy(ioc->board_name, pbuf->BoardName, sizeof(ioc->board_name));
6258         memcpy(ioc->board_assembly, pbuf->BoardAssembly, sizeof(ioc->board_assembly));
6259         memcpy(ioc->board_tracer, pbuf->BoardTracerNumber, sizeof(ioc->board_tracer));
6260 
6261 out:
6262 
6263         if (pbuf)
6264                 pci_free_consistent(ioc->pcidev, hdr.PageLength * 4, pbuf, buf_dma);
6265 }
6266 
6267 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
6268 /**
6269  *      SendEventNotification - Send EventNotification (on or off) request to adapter
6270  *      @ioc: Pointer to MPT_ADAPTER structure
6271  *      @EvSwitch: Event switch flags
6272  *      @sleepFlag: Specifies whether the process can sleep
6273  */
6274 static int
6275 SendEventNotification(MPT_ADAPTER *ioc, u8 EvSwitch, int sleepFlag)
6276 {
6277         EventNotification_t     evn;
6278         MPIDefaultReply_t       reply_buf;
6279 
6280         memset(&evn, 0, sizeof(EventNotification_t));
6281         memset(&reply_buf, 0, sizeof(MPIDefaultReply_t));
6282 
6283         evn.Function = MPI_FUNCTION_EVENT_NOTIFICATION;
6284         evn.Switch = EvSwitch;
6285         evn.MsgContext = cpu_to_le32(mpt_base_index << 16);
6286 
6287         devtverboseprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6288             "Sending EventNotification (%d) request %p\n",
6289             ioc->name, EvSwitch, &evn));
6290 
6291         return mpt_handshake_req_reply_wait(ioc, sizeof(EventNotification_t),
6292             (u32 *)&evn, sizeof(MPIDefaultReply_t), (u16 *)&reply_buf, 30,
6293             sleepFlag);
6294 }
6295 
6296 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
6297 /**
6298  *      SendEventAck - Send EventAck request to MPT adapter.
6299  *      @ioc: Pointer to MPT_ADAPTER structure
6300  *      @evnp: Pointer to original EventNotification request
6301  */
6302 static int
6303 SendEventAck(MPT_ADAPTER *ioc, EventNotificationReply_t *evnp)
6304 {
6305         EventAck_t      *pAck;
6306 
6307         if ((pAck = (EventAck_t *) mpt_get_msg_frame(mpt_base_index, ioc)) == NULL) {
6308                 dfailprintk(ioc, printk(MYIOC_s_WARN_FMT "%s, no msg frames!!\n",
6309                     ioc->name, __func__));
6310                 return -1;
6311         }
6312 
6313         devtverboseprintk(ioc, printk(MYIOC_s_DEBUG_FMT "Sending EventAck\n", ioc->name));
6314 
6315         pAck->Function     = MPI_FUNCTION_EVENT_ACK;
6316         pAck->ChainOffset  = 0;
6317         pAck->Reserved[0]  = pAck->Reserved[1] = 0;
6318         pAck->MsgFlags     = 0;
6319         pAck->Reserved1[0] = pAck->Reserved1[1] = pAck->Reserved1[2] = 0;
6320         pAck->Event        = evnp->Event;
6321         pAck->EventContext = evnp->EventContext;
6322 
6323         mpt_put_msg_frame(mpt_base_index, ioc, (MPT_FRAME_HDR *)pAck);
6324 
6325         return 0;
6326 }
6327 
6328 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
6329 /**
6330  *      mpt_config - Generic function to issue config message
6331  *      @ioc:   Pointer to an adapter structure
6332  *      @pCfg:  Pointer to a configuration structure. Struct contains
6333  *              action, page address, direction, physical address
6334  *              and pointer to a configuration page header
6335  *              Page header is updated.
6336  *
6337  *      Returns 0 for success
6338  *      -EPERM if not allowed due to ISR context
6339  *      -EAGAIN if no msg frames currently available
6340  *      -EFAULT for non-successful reply or no reply (timeout)
6341  */
6342 int
6343 mpt_config(MPT_ADAPTER *ioc, CONFIGPARMS *pCfg)
6344 {
6345         Config_t        *pReq;
6346         ConfigReply_t   *pReply;
6347         ConfigExtendedPageHeader_t  *pExtHdr = NULL;
6348         MPT_FRAME_HDR   *mf;
6349         int              ii;
6350         int              flagsLength;
6351         long             timeout;
6352         int              ret;
6353         u8               page_type = 0, extend_page;
6354         unsigned long    timeleft;
6355         unsigned long    flags;
6356         int              in_isr;
6357         u8               issue_hard_reset = 0;
6358         u8               retry_count = 0;
6359 
6360         /*      Prevent calling wait_event() (below), if caller happens
6361          *      to be in ISR context, because that is fatal!
6362          */
6363         in_isr = in_interrupt();
6364         if (in_isr) {
6365                 dcprintk(ioc, printk(MYIOC_s_WARN_FMT "Config request not allowed in ISR context!\n",
6366                                 ioc->name));
6367                 return -EPERM;
6368     }
6369 
6370         /* don't send a config page during diag reset */
6371         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
6372         if (ioc->ioc_reset_in_progress) {
6373                 dfailprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6374                     "%s: busy with host reset\n", ioc->name, __func__));
6375                 spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
6376                 return -EBUSY;
6377         }
6378         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
6379 
6380         /* don't send if no chance of success */
6381         if (!ioc->active ||
6382             mpt_GetIocState(ioc, 1) != MPI_IOC_STATE_OPERATIONAL) {
6383                 dfailprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6384                     "%s: ioc not operational, %d, %xh\n",
6385                     ioc->name, __func__, ioc->active,
6386                     mpt_GetIocState(ioc, 0)));
6387                 return -EFAULT;
6388         }
6389 
6390  retry_config:
6391         mutex_lock(&ioc->mptbase_cmds.mutex);
6392         /* init the internal cmd struct */
6393         memset(ioc->mptbase_cmds.reply, 0 , MPT_DEFAULT_FRAME_SIZE);
6394         INITIALIZE_MGMT_STATUS(ioc->mptbase_cmds.status)
6395 
6396         /* Get and Populate a free Frame
6397          */
6398         if ((mf = mpt_get_msg_frame(mpt_base_index, ioc)) == NULL) {
6399                 dcprintk(ioc, printk(MYIOC_s_WARN_FMT
6400                 "mpt_config: no msg frames!\n", ioc->name));
6401                 ret = -EAGAIN;
6402                 goto out;
6403         }
6404 
6405         pReq = (Config_t *)mf;
6406         pReq->Action = pCfg->action;
6407         pReq->Reserved = 0;
6408         pReq->ChainOffset = 0;
6409         pReq->Function = MPI_FUNCTION_CONFIG;
6410 
6411         /* Assume page type is not extended and clear "reserved" fields. */
6412         pReq->ExtPageLength = 0;
6413         pReq->ExtPageType = 0;
6414         pReq->MsgFlags = 0;
6415 
6416         for (ii=0; ii < 8; ii++)
6417                 pReq->Reserved2[ii] = 0;
6418 
6419         pReq->Header.PageVersion = pCfg->cfghdr.hdr->PageVersion;
6420         pReq->Header.PageLength = pCfg->cfghdr.hdr->PageLength;
6421         pReq->Header.PageNumber = pCfg->cfghdr.hdr->PageNumber;
6422         pReq->Header.PageType = (pCfg->cfghdr.hdr->PageType & MPI_CONFIG_PAGETYPE_MASK);
6423 
6424         if ((pCfg->cfghdr.hdr->PageType & MPI_CONFIG_PAGETYPE_MASK) == MPI_CONFIG_PAGETYPE_EXTENDED) {
6425                 pExtHdr = (ConfigExtendedPageHeader_t *)pCfg->cfghdr.ehdr;
6426                 pReq->ExtPageLength = cpu_to_le16(pExtHdr->ExtPageLength);
6427                 pReq->ExtPageType = pExtHdr->ExtPageType;
6428                 pReq->Header.PageType = MPI_CONFIG_PAGETYPE_EXTENDED;
6429 
6430                 /* Page Length must be treated as a reserved field for the
6431                  * extended header.
6432                  */
6433                 pReq->Header.PageLength = 0;
6434         }
6435 
6436         pReq->PageAddress = cpu_to_le32(pCfg->pageAddr);
6437 
6438         /* Add a SGE to the config request.
6439          */
6440         if (pCfg->dir)
6441                 flagsLength = MPT_SGE_FLAGS_SSIMPLE_WRITE;
6442         else
6443                 flagsLength = MPT_SGE_FLAGS_SSIMPLE_READ;
6444 
6445         if ((pCfg->cfghdr.hdr->PageType & MPI_CONFIG_PAGETYPE_MASK) ==
6446             MPI_CONFIG_PAGETYPE_EXTENDED) {
6447                 flagsLength |= pExtHdr->ExtPageLength * 4;
6448                 page_type = pReq->ExtPageType;
6449                 extend_page = 1;
6450         } else {
6451                 flagsLength |= pCfg->cfghdr.hdr->PageLength * 4;
6452                 page_type = pReq->Header.PageType;
6453                 extend_page = 0;
6454         }
6455 
6456         dcprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6457             "Sending Config request type 0x%x, page 0x%x and action %d\n",
6458             ioc->name, page_type, pReq->Header.PageNumber, pReq->Action));
6459 
6460         ioc->add_sge((char *)&pReq->PageBufferSGE, flagsLength, pCfg->physAddr);
6461         timeout = (pCfg->timeout < 15) ? HZ*15 : HZ*pCfg->timeout;
6462         mpt_put_msg_frame(mpt_base_index, ioc, mf);
6463         timeleft = wait_for_completion_timeout(&ioc->mptbase_cmds.done,
6464                 timeout);
6465         if (!(ioc->mptbase_cmds.status & MPT_MGMT_STATUS_COMMAND_GOOD)) {
6466                 ret = -ETIME;
6467                 dfailprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6468                     "Failed Sending Config request type 0x%x, page 0x%x,"
6469                     " action %d, status %xh, time left %ld\n\n",
6470                         ioc->name, page_type, pReq->Header.PageNumber,
6471                         pReq->Action, ioc->mptbase_cmds.status, timeleft));
6472                 if (ioc->mptbase_cmds.status & MPT_MGMT_STATUS_DID_IOCRESET)
6473                         goto out;
6474                 if (!timeleft) {
6475                         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
6476                         if (ioc->ioc_reset_in_progress) {
6477                                 spin_unlock_irqrestore(&ioc->taskmgmt_lock,
6478                                         flags);
6479                                 printk(MYIOC_s_INFO_FMT "%s: host reset in"
6480                                         " progress mpt_config timed out.!!\n",
6481                                         __func__, ioc->name);
6482                                 mutex_unlock(&ioc->mptbase_cmds.mutex);
6483                                 return -EFAULT;
6484                         }
6485                         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
6486                         issue_hard_reset = 1;
6487                 }
6488                 goto out;
6489         }
6490 
6491         if (!(ioc->mptbase_cmds.status & MPT_MGMT_STATUS_RF_VALID)) {
6492                 ret = -1;
6493                 goto out;
6494         }
6495         pReply = (ConfigReply_t *)ioc->mptbase_cmds.reply;
6496         ret = le16_to_cpu(pReply->IOCStatus) & MPI_IOCSTATUS_MASK;
6497         if (ret == MPI_IOCSTATUS_SUCCESS) {
6498                 if (extend_page) {
6499                         pCfg->cfghdr.ehdr->ExtPageLength =
6500                             le16_to_cpu(pReply->ExtPageLength);
6501                         pCfg->cfghdr.ehdr->ExtPageType =
6502                             pReply->ExtPageType;
6503                 }
6504                 pCfg->cfghdr.hdr->PageVersion = pReply->Header.PageVersion;
6505                 pCfg->cfghdr.hdr->PageLength = pReply->Header.PageLength;
6506                 pCfg->cfghdr.hdr->PageNumber = pReply->Header.PageNumber;
6507                 pCfg->cfghdr.hdr->PageType = pReply->Header.PageType;
6508 
6509         }
6510 
6511         if (retry_count)
6512                 printk(MYIOC_s_INFO_FMT "Retry completed "
6513                     "ret=0x%x timeleft=%ld\n",
6514                     ioc->name, ret, timeleft);
6515 
6516         dcprintk(ioc, printk(KERN_DEBUG "IOCStatus=%04xh, IOCLogInfo=%08xh\n",
6517              ret, le32_to_cpu(pReply->IOCLogInfo)));
6518 
6519 out:
6520 
6521         CLEAR_MGMT_STATUS(ioc->mptbase_cmds.status)
6522         mutex_unlock(&ioc->mptbase_cmds.mutex);
6523         if (issue_hard_reset) {
6524                 issue_hard_reset = 0;
6525                 printk(MYIOC_s_WARN_FMT
6526                        "Issuing Reset from %s!!, doorbell=0x%08x\n",
6527                        ioc->name, __func__, mpt_GetIocState(ioc, 0));
6528                 if (retry_count == 0) {
6529                         if (mpt_Soft_Hard_ResetHandler(ioc, CAN_SLEEP) != 0)
6530                                 retry_count++;
6531                 } else
6532                         mpt_HardResetHandler(ioc, CAN_SLEEP);
6533 
6534                 mpt_free_msg_frame(ioc, mf);
6535                 /* attempt one retry for a timed out command */
6536                 if (retry_count < 2) {
6537                         printk(MYIOC_s_INFO_FMT
6538                             "Attempting Retry Config request"
6539                             " type 0x%x, page 0x%x,"
6540                             " action %d\n", ioc->name, page_type,
6541                             pCfg->cfghdr.hdr->PageNumber, pCfg->action);
6542                         retry_count++;
6543                         goto retry_config;
6544                 }
6545         }
6546         return ret;
6547 
6548 }
6549 
6550 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
6551 /**
6552  *      mpt_ioc_reset - Base cleanup for hard reset
6553  *      @ioc: Pointer to the adapter structure
6554  *      @reset_phase: Indicates pre- or post-reset functionality
6555  *
6556  *      Remark: Frees resources with internally generated commands.
6557  */
6558 static int
6559 mpt_ioc_reset(MPT_ADAPTER *ioc, int reset_phase)
6560 {
6561         switch (reset_phase) {
6562         case MPT_IOC_SETUP_RESET:
6563                 ioc->taskmgmt_quiesce_io = 1;
6564                 dtmprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6565                     "%s: MPT_IOC_SETUP_RESET\n", ioc->name, __func__));
6566                 break;
6567         case MPT_IOC_PRE_RESET:
6568                 dtmprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6569                     "%s: MPT_IOC_PRE_RESET\n", ioc->name, __func__));
6570                 break;
6571         case MPT_IOC_POST_RESET:
6572                 dtmprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6573                     "%s: MPT_IOC_POST_RESET\n",  ioc->name, __func__));
6574 /* wake up mptbase_cmds */
6575                 if (ioc->mptbase_cmds.status & MPT_MGMT_STATUS_PENDING) {
6576                         ioc->mptbase_cmds.status |=
6577                             MPT_MGMT_STATUS_DID_IOCRESET;
6578                         complete(&ioc->mptbase_cmds.done);
6579                 }
6580 /* wake up taskmgmt_cmds */
6581                 if (ioc->taskmgmt_cmds.status & MPT_MGMT_STATUS_PENDING) {
6582                         ioc->taskmgmt_cmds.status |=
6583                                 MPT_MGMT_STATUS_DID_IOCRESET;
6584                         complete(&ioc->taskmgmt_cmds.done);
6585                 }
6586                 break;
6587         default:
6588                 break;
6589         }
6590 
6591         return 1;               /* currently means nothing really */
6592 }
6593 
6594 
6595 #ifdef CONFIG_PROC_FS           /* { */
6596 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
6597 /*
6598  *      procfs (%MPT_PROCFS_MPTBASEDIR/...) support stuff...
6599  */
6600 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
6601 /**
6602  *      procmpt_create - Create %MPT_PROCFS_MPTBASEDIR entries.
6603  *
6604  *      Returns 0 for success, non-zero for failure.
6605  */
6606 static int
6607 procmpt_create(void)
6608 {
6609         mpt_proc_root_dir = proc_mkdir(MPT_PROCFS_MPTBASEDIR, NULL);
6610         if (mpt_proc_root_dir == NULL)
6611                 return -ENOTDIR;
6612 
6613         proc_create_single("summary", S_IRUGO, mpt_proc_root_dir,
6614                         mpt_summary_proc_show);
6615         proc_create_single("version", S_IRUGO, mpt_proc_root_dir,
6616                         mpt_version_proc_show);
6617         return 0;
6618 }
6619 
6620 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
6621 /**
6622  *      procmpt_destroy - Tear down %MPT_PROCFS_MPTBASEDIR entries.
6623  *
6624  *      Returns 0 for success, non-zero for failure.
6625  */
6626 static void
6627 procmpt_destroy(void)
6628 {
6629         remove_proc_entry("version", mpt_proc_root_dir);
6630         remove_proc_entry("summary", mpt_proc_root_dir);
6631         remove_proc_entry(MPT_PROCFS_MPTBASEDIR, NULL);
6632 }
6633 
6634 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
6635 /*
6636  *      Handles read request from /proc/mpt/summary or /proc/mpt/iocN/summary.
6637  */
6638 static void seq_mpt_print_ioc_summary(MPT_ADAPTER *ioc, struct seq_file *m, int showlan);
6639 
6640 static int mpt_summary_proc_show(struct seq_file *m, void *v)
6641 {
6642         MPT_ADAPTER *ioc = m->private;
6643 
6644         if (ioc) {
6645                 seq_mpt_print_ioc_summary(ioc, m, 1);
6646         } else {
6647                 list_for_each_entry(ioc, &ioc_list, list) {
6648                         seq_mpt_print_ioc_summary(ioc, m, 1);
6649                 }
6650         }
6651 
6652         return 0;
6653 }
6654 
6655 static int mpt_version_proc_show(struct seq_file *m, void *v)
6656 {
6657         u8       cb_idx;
6658         int      scsi, fc, sas, lan, ctl, targ, dmp;
6659         char    *drvname;
6660 
6661         seq_printf(m, "%s-%s\n", "mptlinux", MPT_LINUX_VERSION_COMMON);
6662         seq_printf(m, "  Fusion MPT base driver\n");
6663 
6664         scsi = fc = sas = lan = ctl = targ = dmp = 0;
6665         for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--) {
6666                 drvname = NULL;
6667                 if (MptCallbacks[cb_idx]) {
6668                         switch (MptDriverClass[cb_idx]) {
6669                         case MPTSPI_DRIVER:
6670                                 if (!scsi++) drvname = "SPI host";
6671                                 break;
6672                         case MPTFC_DRIVER:
6673                                 if (!fc++) drvname = "FC host";
6674                                 break;
6675                         case MPTSAS_DRIVER:
6676                                 if (!sas++) drvname = "SAS host";
6677                                 break;
6678                         case MPTLAN_DRIVER:
6679                                 if (!lan++) drvname = "LAN";
6680                                 break;
6681                         case MPTSTM_DRIVER:
6682                                 if (!targ++) drvname = "SCSI target";
6683                                 break;
6684                         case MPTCTL_DRIVER:
6685                                 if (!ctl++) drvname = "ioctl";
6686                                 break;
6687                         }
6688 
6689                         if (drvname)
6690                                 seq_printf(m, "  Fusion MPT %s driver\n", drvname);
6691                 }
6692         }
6693 
6694         return 0;
6695 }
6696 
6697 static int mpt_iocinfo_proc_show(struct seq_file *m, void *v)
6698 {
6699         MPT_ADAPTER     *ioc = m->private;
6700         char             expVer[32];
6701         int              sz;
6702         int              p;
6703 
6704         mpt_get_fw_exp_ver(expVer, ioc);
6705 
6706         seq_printf(m, "%s:", ioc->name);
6707         if (ioc->facts.Flags & MPI_IOCFACTS_FLAGS_FW_DOWNLOAD_BOOT)
6708                 seq_printf(m, "  (f/w download boot flag set)");
6709 //      if (ioc->facts.IOCExceptions & MPI_IOCFACTS_EXCEPT_CONFIG_CHECKSUM_FAIL)
6710 //              seq_printf(m, "  CONFIG_CHECKSUM_FAIL!");
6711 
6712         seq_printf(m, "\n  ProductID = 0x%04x (%s)\n",
6713                         ioc->facts.ProductID,
6714                         ioc->prod_name);
6715         seq_printf(m, "  FWVersion = 0x%08x%s", ioc->facts.FWVersion.Word, expVer);
6716         if (ioc->facts.FWImageSize)
6717                 seq_printf(m, " (fw_size=%d)", ioc->facts.FWImageSize);
6718         seq_printf(m, "\n  MsgVersion = 0x%04x\n", ioc->facts.MsgVersion);
6719         seq_printf(m, "  FirstWhoInit = 0x%02x\n", ioc->FirstWhoInit);
6720         seq_printf(m, "  EventState = 0x%02x\n", ioc->facts.EventState);
6721 
6722         seq_printf(m, "  CurrentHostMfaHighAddr = 0x%08x\n",
6723                         ioc->facts.CurrentHostMfaHighAddr);
6724         seq_printf(m, "  CurrentSenseBufferHighAddr = 0x%08x\n",
6725                         ioc->facts.CurrentSenseBufferHighAddr);
6726 
6727         seq_printf(m, "  MaxChainDepth = 0x%02x frames\n", ioc->facts.MaxChainDepth);
6728         seq_printf(m, "  MinBlockSize = 0x%02x bytes\n", 4*ioc->facts.BlockSize);
6729 
6730         seq_printf(m, "  RequestFrames @ 0x%p (Dma @ 0x%p)\n",
6731                                         (void *)ioc->req_frames, (void *)(ulong)ioc->req_frames_dma);
6732         /*
6733          *  Rounding UP to nearest 4-kB boundary here...
6734          */
6735         sz = (ioc->req_sz * ioc->req_depth) + 128;
6736         sz = ((sz + 0x1000UL - 1UL) / 0x1000) * 0x1000;
6737         seq_printf(m, "    {CurReqSz=%d} x {CurReqDepth=%d} = %d bytes ^= 0x%x\n",
6738                                         ioc->req_sz, ioc->req_depth, ioc->req_sz*ioc->req_depth, sz);
6739         seq_printf(m, "    {MaxReqSz=%d}   {MaxReqDepth=%d}\n",
6740                                         4*ioc->facts.RequestFrameSize,
6741                                         ioc->facts.GlobalCredits);
6742 
6743         seq_printf(m, "  Frames   @ 0x%p (Dma @ 0x%p)\n",
6744                                         (void *)ioc->alloc, (void *)(ulong)ioc->alloc_dma);
6745         sz = (ioc->reply_sz * ioc->reply_depth) + 128;
6746         seq_printf(m, "    {CurRepSz=%d} x {CurRepDepth=%d} = %d bytes ^= 0x%x\n",
6747                                         ioc->reply_sz, ioc->reply_depth, ioc->reply_sz*ioc->reply_depth, sz);
6748         seq_printf(m, "    {MaxRepSz=%d}   {MaxRepDepth=%d}\n",
6749                                         ioc->facts.CurReplyFrameSize,
6750                                         ioc->facts.ReplyQueueDepth);
6751 
6752         seq_printf(m, "  MaxDevices = %d\n",
6753                         (ioc->facts.MaxDevices==0) ? 255 : ioc->facts.MaxDevices);
6754         seq_printf(m, "  MaxBuses = %d\n", ioc->facts.MaxBuses);
6755 
6756         /* per-port info */
6757         for (p=0; p < ioc->facts.NumberOfPorts; p++) {
6758                 seq_printf(m, "  PortNumber = %d (of %d)\n",
6759                                 p+1,
6760                                 ioc->facts.NumberOfPorts);
6761                 if (ioc->bus_type == FC) {
6762                         if (ioc->pfacts[p].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN) {
6763                                 u8 *a = (u8*)&ioc->lan_cnfg_page1.HardwareAddressLow;
6764                                 seq_printf(m, "    LanAddr = %pMR\n", a);
6765                         }
6766                         seq_printf(m, "    WWN = %08X%08X:%08X%08X\n",
6767                                         ioc->fc_port_page0[p].WWNN.High,
6768                                         ioc->fc_port_page0[p].WWNN.Low,
6769                                         ioc->fc_port_page0[p].WWPN.High,
6770                                         ioc->fc_port_page0[p].WWPN.Low);
6771                 }
6772         }
6773 
6774         return 0;
6775 }
6776 #endif          /* CONFIG_PROC_FS } */
6777 
6778 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
6779 static void
6780 mpt_get_fw_exp_ver(char *buf, MPT_ADAPTER *ioc)
6781 {
6782         buf[0] ='\0';
6783         if ((ioc->facts.FWVersion.Word >> 24) == 0x0E) {
6784                 sprintf(buf, " (Exp %02d%02d)",
6785                         (ioc->facts.FWVersion.Word >> 16) & 0x00FF,     /* Month */
6786                         (ioc->facts.FWVersion.Word >> 8) & 0x1F);       /* Day */
6787 
6788                 /* insider hack! */
6789                 if ((ioc->facts.FWVersion.Word >> 8) & 0x80)
6790                         strcat(buf, " [MDBG]");
6791         }
6792 }
6793 
6794 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
6795 /**
6796  *      mpt_print_ioc_summary - Write ASCII summary of IOC to a buffer.
6797  *      @ioc: Pointer to MPT_ADAPTER structure
6798  *      @buffer: Pointer to buffer where IOC summary info should be written
6799  *      @size: Pointer to number of bytes we wrote (set by this routine)
6800  *      @len: Offset at which to start writing in buffer
6801  *      @showlan: Display LAN stuff?
6802  *
6803  *      This routine writes (english readable) ASCII text, which represents
6804  *      a summary of IOC information, to a buffer.
6805  */
6806 void
6807 mpt_print_ioc_summary(MPT_ADAPTER *ioc, char *buffer, int *size, int len, int showlan)
6808 {
6809         char expVer[32];
6810         int y;
6811 
6812         mpt_get_fw_exp_ver(expVer, ioc);
6813 
6814         /*
6815          *  Shorter summary of attached ioc's...
6816          */
6817         y = sprintf(buffer+len, "%s: %s, %s%08xh%s, Ports=%d, MaxQ=%d",
6818                         ioc->name,
6819                         ioc->prod_name,
6820                         MPT_FW_REV_MAGIC_ID_STRING,     /* "FwRev=" or somesuch */
6821                         ioc->facts.FWVersion.Word,
6822                         expVer,
6823                         ioc->facts.NumberOfPorts,
6824                         ioc->req_depth);
6825 
6826         if (showlan && (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN)) {
6827                 u8 *a = (u8*)&ioc->lan_cnfg_page1.HardwareAddressLow;
6828                 y += sprintf(buffer+len+y, ", LanAddr=%pMR", a);
6829         }
6830 
6831         y += sprintf(buffer+len+y, ", IRQ=%d", ioc->pci_irq);
6832 
6833         if (!ioc->active)
6834                 y += sprintf(buffer+len+y, " (disabled)");
6835 
6836         y += sprintf(buffer+len+y, "\n");
6837 
6838         *size = y;
6839 }
6840 
6841 #ifdef CONFIG_PROC_FS
6842 static void seq_mpt_print_ioc_summary(MPT_ADAPTER *ioc, struct seq_file *m, int showlan)
6843 {
6844         char expVer[32];
6845 
6846         mpt_get_fw_exp_ver(expVer, ioc);
6847 
6848         /*
6849          *  Shorter summary of attached ioc's...
6850          */
6851         seq_printf(m, "%s: %s, %s%08xh%s, Ports=%d, MaxQ=%d",
6852                         ioc->name,
6853                         ioc->prod_name,
6854                         MPT_FW_REV_MAGIC_ID_STRING,     /* "FwRev=" or somesuch */
6855                         ioc->facts.FWVersion.Word,
6856                         expVer,
6857                         ioc->facts.NumberOfPorts,
6858                         ioc->req_depth);
6859 
6860         if (showlan && (ioc->pfacts[0].ProtocolFlags & MPI_PORTFACTS_PROTOCOL_LAN)) {
6861                 u8 *a = (u8*)&ioc->lan_cnfg_page1.HardwareAddressLow;
6862                 seq_printf(m, ", LanAddr=%pMR", a);
6863         }
6864 
6865         seq_printf(m, ", IRQ=%d", ioc->pci_irq);
6866 
6867         if (!ioc->active)
6868                 seq_printf(m, " (disabled)");
6869 
6870         seq_putc(m, '\n');
6871 }
6872 #endif
6873 
6874 /**
6875  *      mpt_set_taskmgmt_in_progress_flag - set flags associated with task management
6876  *      @ioc: Pointer to MPT_ADAPTER structure
6877  *
6878  *      Returns 0 for SUCCESS or -1 if FAILED.
6879  *
6880  *      If -1 is return, then it was not possible to set the flags
6881  **/
6882 int
6883 mpt_set_taskmgmt_in_progress_flag(MPT_ADAPTER *ioc)
6884 {
6885         unsigned long    flags;
6886         int              retval;
6887 
6888         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
6889         if (ioc->ioc_reset_in_progress || ioc->taskmgmt_in_progress ||
6890             (ioc->alt_ioc && ioc->alt_ioc->taskmgmt_in_progress)) {
6891                 retval = -1;
6892                 goto out;
6893         }
6894         retval = 0;
6895         ioc->taskmgmt_in_progress = 1;
6896         ioc->taskmgmt_quiesce_io = 1;
6897         if (ioc->alt_ioc) {
6898                 ioc->alt_ioc->taskmgmt_in_progress = 1;
6899                 ioc->alt_ioc->taskmgmt_quiesce_io = 1;
6900         }
6901  out:
6902         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
6903         return retval;
6904 }
6905 EXPORT_SYMBOL(mpt_set_taskmgmt_in_progress_flag);
6906 
6907 /**
6908  *      mpt_clear_taskmgmt_in_progress_flag - clear flags associated with task management
6909  *      @ioc: Pointer to MPT_ADAPTER structure
6910  *
6911  **/
6912 void
6913 mpt_clear_taskmgmt_in_progress_flag(MPT_ADAPTER *ioc)
6914 {
6915         unsigned long    flags;
6916 
6917         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
6918         ioc->taskmgmt_in_progress = 0;
6919         ioc->taskmgmt_quiesce_io = 0;
6920         if (ioc->alt_ioc) {
6921                 ioc->alt_ioc->taskmgmt_in_progress = 0;
6922                 ioc->alt_ioc->taskmgmt_quiesce_io = 0;
6923         }
6924         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
6925 }
6926 EXPORT_SYMBOL(mpt_clear_taskmgmt_in_progress_flag);
6927 
6928 
6929 /**
6930  *      mpt_halt_firmware - Halts the firmware if it is operational and panic
6931  *      the kernel
6932  *      @ioc: Pointer to MPT_ADAPTER structure
6933  *
6934  **/
6935 void
6936 mpt_halt_firmware(MPT_ADAPTER *ioc)
6937 {
6938         u32      ioc_raw_state;
6939 
6940         ioc_raw_state = mpt_GetIocState(ioc, 0);
6941 
6942         if ((ioc_raw_state & MPI_IOC_STATE_MASK) == MPI_IOC_STATE_FAULT) {
6943                 printk(MYIOC_s_ERR_FMT "IOC is in FAULT state (%04xh)!!!\n",
6944                         ioc->name, ioc_raw_state & MPI_DOORBELL_DATA_MASK);
6945                 panic("%s: IOC Fault (%04xh)!!!\n", ioc->name,
6946                         ioc_raw_state & MPI_DOORBELL_DATA_MASK);
6947         } else {
6948                 CHIPREG_WRITE32(&ioc->chip->Doorbell, 0xC0FFEE00);
6949                 panic("%s: Firmware is halted due to command timeout\n",
6950                         ioc->name);
6951         }
6952 }
6953 EXPORT_SYMBOL(mpt_halt_firmware);
6954 
6955 /**
6956  *      mpt_SoftResetHandler - Issues a less expensive reset
6957  *      @ioc: Pointer to MPT_ADAPTER structure
6958  *      @sleepFlag: Indicates if sleep or schedule must be called.
6959  *
6960  *      Returns 0 for SUCCESS or -1 if FAILED.
6961  *
6962  *      Message Unit Reset - instructs the IOC to reset the Reply Post and
6963  *      Free FIFO's. All the Message Frames on Reply Free FIFO are discarded.
6964  *      All posted buffers are freed, and event notification is turned off.
6965  *      IOC doesn't reply to any outstanding request. This will transfer IOC
6966  *      to READY state.
6967  **/
6968 static int
6969 mpt_SoftResetHandler(MPT_ADAPTER *ioc, int sleepFlag)
6970 {
6971         int              rc;
6972         int              ii;
6973         u8               cb_idx;
6974         unsigned long    flags;
6975         u32              ioc_state;
6976         unsigned long    time_count;
6977 
6978         dtmprintk(ioc, printk(MYIOC_s_DEBUG_FMT "SoftResetHandler Entered!\n",
6979                 ioc->name));
6980 
6981         ioc_state = mpt_GetIocState(ioc, 0) & MPI_IOC_STATE_MASK;
6982 
6983         if (mpt_fwfault_debug)
6984                 mpt_halt_firmware(ioc);
6985 
6986         if (ioc_state == MPI_IOC_STATE_FAULT ||
6987             ioc_state == MPI_IOC_STATE_RESET) {
6988                 dtmprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6989                     "skipping, either in FAULT or RESET state!\n", ioc->name));
6990                 return -1;
6991         }
6992 
6993         if (ioc->bus_type == FC) {
6994                 dtmprintk(ioc, printk(MYIOC_s_DEBUG_FMT
6995                     "skipping, because the bus type is FC!\n", ioc->name));
6996                 return -1;
6997         }
6998 
6999         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
7000         if (ioc->ioc_reset_in_progress) {
7001                 spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
7002                 return -1;
7003         }
7004         ioc->ioc_reset_in_progress = 1;
7005         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
7006 
7007         rc = -1;
7008 
7009         for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--) {
7010                 if (MptResetHandlers[cb_idx])
7011                         mpt_signal_reset(cb_idx, ioc, MPT_IOC_SETUP_RESET);
7012         }
7013 
7014         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
7015         if (ioc->taskmgmt_in_progress) {
7016                 ioc->ioc_reset_in_progress = 0;
7017                 spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
7018                 return -1;
7019         }
7020         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
7021         /* Disable reply interrupts (also blocks FreeQ) */
7022         CHIPREG_WRITE32(&ioc->chip->IntMask, 0xFFFFFFFF);
7023         ioc->active = 0;
7024         time_count = jiffies;
7025 
7026         rc = SendIocReset(ioc, MPI_FUNCTION_IOC_MESSAGE_UNIT_RESET, sleepFlag);
7027 
7028         for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--) {
7029                 if (MptResetHandlers[cb_idx])
7030                         mpt_signal_reset(cb_idx, ioc, MPT_IOC_PRE_RESET);
7031         }
7032 
7033         if (rc)
7034                 goto out;
7035 
7036         ioc_state = mpt_GetIocState(ioc, 0) & MPI_IOC_STATE_MASK;
7037         if (ioc_state != MPI_IOC_STATE_READY)
7038                 goto out;
7039 
7040         for (ii = 0; ii < 5; ii++) {
7041                 /* Get IOC facts! Allow 5 retries */
7042                 rc = GetIocFacts(ioc, sleepFlag,
7043                         MPT_HOSTEVENT_IOC_RECOVER);
7044                 if (rc == 0)
7045                         break;
7046                 if (sleepFlag == CAN_SLEEP)
7047                         msleep(100);
7048                 else
7049                         mdelay(100);
7050         }
7051         if (ii == 5)
7052                 goto out;
7053 
7054         rc = PrimeIocFifos(ioc);
7055         if (rc != 0)
7056                 goto out;
7057 
7058         rc = SendIocInit(ioc, sleepFlag);
7059         if (rc != 0)
7060                 goto out;
7061 
7062         rc = SendEventNotification(ioc, 1, sleepFlag);
7063         if (rc != 0)
7064                 goto out;
7065 
7066         if (ioc->hard_resets < -1)
7067                 ioc->hard_resets++;
7068 
7069         /*
7070          * At this point, we know soft reset succeeded.
7071          */
7072 
7073         ioc->active = 1;
7074         CHIPREG_WRITE32(&ioc->chip->IntMask, MPI_HIM_DIM);
7075 
7076  out:
7077         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
7078         ioc->ioc_reset_in_progress = 0;
7079         ioc->taskmgmt_quiesce_io = 0;
7080         ioc->taskmgmt_in_progress = 0;
7081         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
7082 
7083         if (ioc->active) {      /* otherwise, hard reset coming */
7084                 for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--) {
7085                         if (MptResetHandlers[cb_idx])
7086                                 mpt_signal_reset(cb_idx, ioc,
7087                                         MPT_IOC_POST_RESET);
7088                 }
7089         }
7090 
7091         dtmprintk(ioc, printk(MYIOC_s_DEBUG_FMT
7092                 "SoftResetHandler: completed (%d seconds): %s\n",
7093                 ioc->name, jiffies_to_msecs(jiffies - time_count)/1000,
7094                 ((rc == 0) ? "SUCCESS" : "FAILED")));
7095 
7096         return rc;
7097 }
7098 
7099 /**
7100  *      mpt_Soft_Hard_ResetHandler - Try less expensive reset
7101  *      @ioc: Pointer to MPT_ADAPTER structure
7102  *      @sleepFlag: Indicates if sleep or schedule must be called.
7103  *
7104  *      Returns 0 for SUCCESS or -1 if FAILED.
7105  *      Try for softreset first, only if it fails go for expensive
7106  *      HardReset.
7107  **/
7108 int
7109 mpt_Soft_Hard_ResetHandler(MPT_ADAPTER *ioc, int sleepFlag) {
7110         int ret = -1;
7111 
7112         ret = mpt_SoftResetHandler(ioc, sleepFlag);
7113         if (ret == 0)
7114                 return ret;
7115         ret = mpt_HardResetHandler(ioc, sleepFlag);
7116         return ret;
7117 }
7118 EXPORT_SYMBOL(mpt_Soft_Hard_ResetHandler);
7119 
7120 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
7121 /*
7122  *      Reset Handling
7123  */
7124 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
7125 /**
7126  *      mpt_HardResetHandler - Generic reset handler
7127  *      @ioc: Pointer to MPT_ADAPTER structure
7128  *      @sleepFlag: Indicates if sleep or schedule must be called.
7129  *
7130  *      Issues SCSI Task Management call based on input arg values.
7131  *      If TaskMgmt fails, returns associated SCSI request.
7132  *
7133  *      Remark: _HardResetHandler can be invoked from an interrupt thread (timer)
7134  *      or a non-interrupt thread.  In the former, must not call schedule().
7135  *
7136  *      Note: A return of -1 is a FATAL error case, as it means a
7137  *      FW reload/initialization failed.
7138  *
7139  *      Returns 0 for SUCCESS or -1 if FAILED.
7140  */
7141 int
7142 mpt_HardResetHandler(MPT_ADAPTER *ioc, int sleepFlag)
7143 {
7144         int      rc;
7145         u8       cb_idx;
7146         unsigned long    flags;
7147         unsigned long    time_count;
7148 
7149         dtmprintk(ioc, printk(MYIOC_s_DEBUG_FMT "HardResetHandler Entered!\n", ioc->name));
7150 #ifdef MFCNT
7151         printk(MYIOC_s_INFO_FMT "HardResetHandler Entered!\n", ioc->name);
7152         printk("MF count 0x%x !\n", ioc->mfcnt);
7153 #endif
7154         if (mpt_fwfault_debug)
7155                 mpt_halt_firmware(ioc);
7156 
7157         /* Reset the adapter. Prevent more than 1 call to
7158          * mpt_do_ioc_recovery at any instant in time.
7159          */
7160         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
7161         if (ioc->ioc_reset_in_progress) {
7162                 spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
7163                 ioc->wait_on_reset_completion = 1;
7164                 do {
7165                         ssleep(1);
7166                 } while (ioc->ioc_reset_in_progress == 1);
7167                 ioc->wait_on_reset_completion = 0;
7168                 return ioc->reset_status;
7169         }
7170         if (ioc->wait_on_reset_completion) {
7171                 spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
7172                 rc = 0;
7173                 time_count = jiffies;
7174                 goto exit;
7175         }
7176         ioc->ioc_reset_in_progress = 1;
7177         if (ioc->alt_ioc)
7178                 ioc->alt_ioc->ioc_reset_in_progress = 1;
7179         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
7180 
7181 
7182         /* The SCSI driver needs to adjust timeouts on all current
7183          * commands prior to the diagnostic reset being issued.
7184          * Prevents timeouts occurring during a diagnostic reset...very bad.
7185          * For all other protocol drivers, this is a no-op.
7186          */
7187         for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--) {
7188                 if (MptResetHandlers[cb_idx]) {
7189                         mpt_signal_reset(cb_idx, ioc, MPT_IOC_SETUP_RESET);
7190                         if (ioc->alt_ioc)
7191                                 mpt_signal_reset(cb_idx, ioc->alt_ioc,
7192                                         MPT_IOC_SETUP_RESET);
7193                 }
7194         }
7195 
7196         time_count = jiffies;
7197         rc = mpt_do_ioc_recovery(ioc, MPT_HOSTEVENT_IOC_RECOVER, sleepFlag);
7198         if (rc != 0) {
7199                 printk(KERN_WARNING MYNAM
7200                        ": WARNING - (%d) Cannot recover %s, doorbell=0x%08x\n",
7201                        rc, ioc->name, mpt_GetIocState(ioc, 0));
7202         } else {
7203                 if (ioc->hard_resets < -1)
7204                         ioc->hard_resets++;
7205         }
7206 
7207         spin_lock_irqsave(&ioc->taskmgmt_lock, flags);
7208         ioc->ioc_reset_in_progress = 0;
7209         ioc->taskmgmt_quiesce_io = 0;
7210         ioc->taskmgmt_in_progress = 0;
7211         ioc->reset_status = rc;
7212         if (ioc->alt_ioc) {
7213                 ioc->alt_ioc->ioc_reset_in_progress = 0;
7214                 ioc->alt_ioc->taskmgmt_quiesce_io = 0;
7215                 ioc->alt_ioc->taskmgmt_in_progress = 0;
7216         }
7217         spin_unlock_irqrestore(&ioc->taskmgmt_lock, flags);
7218 
7219         for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--) {
7220                 if (MptResetHandlers[cb_idx]) {
7221                         mpt_signal_reset(cb_idx, ioc, MPT_IOC_POST_RESET);
7222                         if (ioc->alt_ioc)
7223                                 mpt_signal_reset(cb_idx,
7224                                         ioc->alt_ioc, MPT_IOC_POST_RESET);
7225                 }
7226         }
7227 exit:
7228         dtmprintk(ioc,
7229             printk(MYIOC_s_DEBUG_FMT
7230                 "HardResetHandler: completed (%d seconds): %s\n", ioc->name,
7231                 jiffies_to_msecs(jiffies - time_count)/1000, ((rc == 0) ?
7232                 "SUCCESS" : "FAILED")));
7233 
7234         return rc;
7235 }
7236 
7237 #ifdef CONFIG_FUSION_LOGGING
7238 static void
7239 mpt_display_event_info(MPT_ADAPTER *ioc, EventNotificationReply_t *pEventReply)
7240 {
7241         char *ds = NULL;
7242         u32 evData0;
7243         int ii;
7244         u8 event;
7245         char *evStr = ioc->evStr;
7246 
7247         event = le32_to_cpu(pEventReply->Event) & 0xFF;
7248         evData0 = le32_to_cpu(pEventReply->Data[0]);
7249 
7250         switch(event) {
7251         case MPI_EVENT_NONE:
7252                 ds = "None";
7253                 break;
7254         case MPI_EVENT_LOG_DATA:
7255                 ds = "Log Data";
7256                 break;
7257         case MPI_EVENT_STATE_CHANGE:
7258                 ds = "State Change";
7259                 break;
7260         case MPI_EVENT_UNIT_ATTENTION:
7261                 ds = "Unit Attention";
7262                 break;
7263         case MPI_EVENT_IOC_BUS_RESET:
7264                 ds = "IOC Bus Reset";
7265                 break;
7266         case MPI_EVENT_EXT_BUS_RESET:
7267                 ds = "External Bus Reset";
7268                 break;
7269         case MPI_EVENT_RESCAN:
7270                 ds = "Bus Rescan Event";
7271                 break;
7272         case MPI_EVENT_LINK_STATUS_CHANGE:
7273                 if (evData0 == MPI_EVENT_LINK_STATUS_FAILURE)
7274                         ds = "Link Status(FAILURE) Change";
7275                 else
7276                         ds = "Link Status(ACTIVE) Change";
7277                 break;
7278         case MPI_EVENT_LOOP_STATE_CHANGE:
7279                 if (evData0 == MPI_EVENT_LOOP_STATE_CHANGE_LIP)
7280                         ds = "Loop State(LIP) Change";
7281                 else if (evData0 == MPI_EVENT_LOOP_STATE_CHANGE_LPE)
7282                         ds = "Loop State(LPE) Change";
7283                 else
7284                         ds = "Loop State(LPB) Change";
7285                 break;
7286         case MPI_EVENT_LOGOUT:
7287                 ds = "Logout";
7288                 break;
7289         case MPI_EVENT_EVENT_CHANGE:
7290                 if (evData0)
7291                         ds = "Events ON";
7292                 else
7293                         ds = "Events OFF";
7294                 break;
7295         case MPI_EVENT_INTEGRATED_RAID:
7296         {
7297                 u8 ReasonCode = (u8)(evData0 >> 16);
7298                 switch (ReasonCode) {
7299                 case MPI_EVENT_RAID_RC_VOLUME_CREATED :
7300                         ds = "Integrated Raid: Volume Created";
7301                         break;
7302                 case MPI_EVENT_RAID_RC_VOLUME_DELETED :
7303                         ds = "Integrated Raid: Volume Deleted";
7304                         break;
7305                 case MPI_EVENT_RAID_RC_VOLUME_SETTINGS_CHANGED :
7306                         ds = "Integrated Raid: Volume Settings Changed";
7307                         break;
7308                 case MPI_EVENT_RAID_RC_VOLUME_STATUS_CHANGED :
7309                         ds = "Integrated Raid: Volume Status Changed";
7310                         break;
7311                 case MPI_EVENT_RAID_RC_VOLUME_PHYSDISK_CHANGED :
7312                         ds = "Integrated Raid: Volume Physdisk Changed";
7313                         break;
7314                 case MPI_EVENT_RAID_RC_PHYSDISK_CREATED :
7315                         ds = "Integrated Raid: Physdisk Created";
7316                         break;
7317                 case MPI_EVENT_RAID_RC_PHYSDISK_DELETED :
7318                         ds = "Integrated Raid: Physdisk Deleted";
7319                         break;
7320                 case MPI_EVENT_RAID_RC_PHYSDISK_SETTINGS_CHANGED :
7321                         ds = "Integrated Raid: Physdisk Settings Changed";
7322                         break;
7323                 case MPI_EVENT_RAID_RC_PHYSDISK_STATUS_CHANGED :
7324                         ds = "Integrated Raid: Physdisk Status Changed";
7325                         break;
7326                 case MPI_EVENT_RAID_RC_DOMAIN_VAL_NEEDED :
7327                         ds = "Integrated Raid: Domain Validation Needed";
7328                         break;
7329                 case MPI_EVENT_RAID_RC_SMART_DATA :
7330                         ds = "Integrated Raid; Smart Data";
7331                         break;
7332                 case MPI_EVENT_RAID_RC_REPLACE_ACTION_STARTED :
7333                         ds = "Integrated Raid: Replace Action Started";
7334                         break;
7335                 default:
7336                         ds = "Integrated Raid";
7337                 break;
7338                 }
7339                 break;
7340         }
7341         case MPI_EVENT_SCSI_DEVICE_STATUS_CHANGE:
7342                 ds = "SCSI Device Status Change";
7343                 break;
7344         case MPI_EVENT_SAS_DEVICE_STATUS_CHANGE:
7345         {
7346                 u8 id = (u8)(evData0);
7347                 u8 channel = (u8)(evData0 >> 8);
7348                 u8 ReasonCode = (u8)(evData0 >> 16);
7349                 switch (ReasonCode) {
7350                 case MPI_EVENT_SAS_DEV_STAT_RC_ADDED:
7351                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7352                             "SAS Device Status Change: Added: "
7353                             "id=%d channel=%d", id, channel);
7354                         break;
7355                 case MPI_EVENT_SAS_DEV_STAT_RC_NOT_RESPONDING:
7356                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7357                             "SAS Device Status Change: Deleted: "
7358                             "id=%d channel=%d", id, channel);
7359                         break;
7360                 case MPI_EVENT_SAS_DEV_STAT_RC_SMART_DATA:
7361                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7362                             "SAS Device Status Change: SMART Data: "
7363                             "id=%d channel=%d", id, channel);
7364                         break;
7365                 case MPI_EVENT_SAS_DEV_STAT_RC_NO_PERSIST_ADDED:
7366                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7367                             "SAS Device Status Change: No Persistency: "
7368                             "id=%d channel=%d", id, channel);
7369                         break;
7370                 case MPI_EVENT_SAS_DEV_STAT_RC_UNSUPPORTED:
7371                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7372                             "SAS Device Status Change: Unsupported Device "
7373                             "Discovered : id=%d channel=%d", id, channel);
7374                         break;
7375                 case MPI_EVENT_SAS_DEV_STAT_RC_INTERNAL_DEVICE_RESET:
7376                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7377                             "SAS Device Status Change: Internal Device "
7378                             "Reset : id=%d channel=%d", id, channel);
7379                         break;
7380                 case MPI_EVENT_SAS_DEV_STAT_RC_TASK_ABORT_INTERNAL:
7381                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7382                             "SAS Device Status Change: Internal Task "
7383                             "Abort : id=%d channel=%d", id, channel);
7384                         break;
7385                 case MPI_EVENT_SAS_DEV_STAT_RC_ABORT_TASK_SET_INTERNAL:
7386                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7387                             "SAS Device Status Change: Internal Abort "
7388                             "Task Set : id=%d channel=%d", id, channel);
7389                         break;
7390                 case MPI_EVENT_SAS_DEV_STAT_RC_CLEAR_TASK_SET_INTERNAL:
7391                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7392                             "SAS Device Status Change: Internal Clear "
7393                             "Task Set : id=%d channel=%d", id, channel);
7394                         break;
7395                 case MPI_EVENT_SAS_DEV_STAT_RC_QUERY_TASK_INTERNAL:
7396                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7397                             "SAS Device Status Change: Internal Query "
7398                             "Task : id=%d channel=%d", id, channel);
7399                         break;
7400                 default:
7401                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7402                             "SAS Device Status Change: Unknown: "
7403                             "id=%d channel=%d", id, channel);
7404                         break;
7405                 }
7406                 break;
7407         }
7408         case MPI_EVENT_ON_BUS_TIMER_EXPIRED:
7409                 ds = "Bus Timer Expired";
7410                 break;
7411         case MPI_EVENT_QUEUE_FULL:
7412         {
7413                 u16 curr_depth = (u16)(evData0 >> 16);
7414                 u8 channel = (u8)(evData0 >> 8);
7415                 u8 id = (u8)(evData0);
7416 
7417                 snprintf(evStr, EVENT_DESCR_STR_SZ,
7418                    "Queue Full: channel=%d id=%d depth=%d",
7419                    channel, id, curr_depth);
7420                 break;
7421         }
7422         case MPI_EVENT_SAS_SES:
7423                 ds = "SAS SES Event";
7424                 break;
7425         case MPI_EVENT_PERSISTENT_TABLE_FULL:
7426                 ds = "Persistent Table Full";
7427                 break;
7428         case MPI_EVENT_SAS_PHY_LINK_STATUS:
7429         {
7430                 u8 LinkRates = (u8)(evData0 >> 8);
7431                 u8 PhyNumber = (u8)(evData0);
7432                 LinkRates = (LinkRates & MPI_EVENT_SAS_PLS_LR_CURRENT_MASK) >>
7433                         MPI_EVENT_SAS_PLS_LR_CURRENT_SHIFT;
7434                 switch (LinkRates) {
7435                 case MPI_EVENT_SAS_PLS_LR_RATE_UNKNOWN:
7436                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7437                            "SAS PHY Link Status: Phy=%d:"
7438                            " Rate Unknown",PhyNumber);
7439                         break;
7440                 case MPI_EVENT_SAS_PLS_LR_RATE_PHY_DISABLED:
7441                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7442                            "SAS PHY Link Status: Phy=%d:"
7443                            " Phy Disabled",PhyNumber);
7444                         break;
7445                 case MPI_EVENT_SAS_PLS_LR_RATE_FAILED_SPEED_NEGOTIATION:
7446                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7447                            "SAS PHY Link Status: Phy=%d:"
7448                            " Failed Speed Nego",PhyNumber);
7449                         break;
7450                 case MPI_EVENT_SAS_PLS_LR_RATE_SATA_OOB_COMPLETE:
7451                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7452                            "SAS PHY Link Status: Phy=%d:"
7453                            " Sata OOB Completed",PhyNumber);
7454                         break;
7455                 case MPI_EVENT_SAS_PLS_LR_RATE_1_5:
7456                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7457                            "SAS PHY Link Status: Phy=%d:"
7458                            " Rate 1.5 Gbps",PhyNumber);
7459                         break;
7460                 case MPI_EVENT_SAS_PLS_LR_RATE_3_0:
7461                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7462                            "SAS PHY Link Status: Phy=%d:"
7463                            " Rate 3.0 Gbps", PhyNumber);
7464                         break;
7465                 case MPI_EVENT_SAS_PLS_LR_RATE_6_0:
7466                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7467                            "SAS PHY Link Status: Phy=%d:"
7468                            " Rate 6.0 Gbps", PhyNumber);
7469                         break;
7470                 default:
7471                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7472                            "SAS PHY Link Status: Phy=%d", PhyNumber);
7473                         break;
7474                 }
7475                 break;
7476         }
7477         case MPI_EVENT_SAS_DISCOVERY_ERROR:
7478                 ds = "SAS Discovery Error";
7479                 break;
7480         case MPI_EVENT_IR_RESYNC_UPDATE:
7481         {
7482                 u8 resync_complete = (u8)(evData0 >> 16);
7483                 snprintf(evStr, EVENT_DESCR_STR_SZ,
7484                     "IR Resync Update: Complete = %d:",resync_complete);
7485                 break;
7486         }
7487         case MPI_EVENT_IR2:
7488         {
7489                 u8 id = (u8)(evData0);
7490                 u8 channel = (u8)(evData0 >> 8);
7491                 u8 phys_num = (u8)(evData0 >> 24);
7492                 u8 ReasonCode = (u8)(evData0 >> 16);
7493 
7494                 switch (ReasonCode) {
7495                 case MPI_EVENT_IR2_RC_LD_STATE_CHANGED:
7496                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7497                             "IR2: LD State Changed: "
7498                             "id=%d channel=%d phys_num=%d",
7499                             id, channel, phys_num);
7500                         break;
7501                 case MPI_EVENT_IR2_RC_PD_STATE_CHANGED:
7502                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7503                             "IR2: PD State Changed "
7504                             "id=%d channel=%d phys_num=%d",
7505                             id, channel, phys_num);
7506                         break;
7507                 case MPI_EVENT_IR2_RC_BAD_BLOCK_TABLE_FULL:
7508                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7509                             "IR2: Bad Block Table Full: "
7510                             "id=%d channel=%d phys_num=%d",
7511                             id, channel, phys_num);
7512                         break;
7513                 case MPI_EVENT_IR2_RC_PD_INSERTED:
7514                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7515                             "IR2: PD Inserted: "
7516                             "id=%d channel=%d phys_num=%d",
7517                             id, channel, phys_num);
7518                         break;
7519                 case MPI_EVENT_IR2_RC_PD_REMOVED:
7520                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7521                             "IR2: PD Removed: "
7522                             "id=%d channel=%d phys_num=%d",
7523                             id, channel, phys_num);
7524                         break;
7525                 case MPI_EVENT_IR2_RC_FOREIGN_CFG_DETECTED:
7526                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7527                             "IR2: Foreign CFG Detected: "
7528                             "id=%d channel=%d phys_num=%d",
7529                             id, channel, phys_num);
7530                         break;
7531                 case MPI_EVENT_IR2_RC_REBUILD_MEDIUM_ERROR:
7532                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7533                             "IR2: Rebuild Medium Error: "
7534                             "id=%d channel=%d phys_num=%d",
7535                             id, channel, phys_num);
7536                         break;
7537                 case MPI_EVENT_IR2_RC_DUAL_PORT_ADDED:
7538                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7539                             "IR2: Dual Port Added: "
7540                             "id=%d channel=%d phys_num=%d",
7541                             id, channel, phys_num);
7542                         break;
7543                 case MPI_EVENT_IR2_RC_DUAL_PORT_REMOVED:
7544                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7545                             "IR2: Dual Port Removed: "
7546                             "id=%d channel=%d phys_num=%d",
7547                             id, channel, phys_num);
7548                         break;
7549                 default:
7550                         ds = "IR2";
7551                 break;
7552                 }
7553                 break;
7554         }
7555         case MPI_EVENT_SAS_DISCOVERY:
7556         {
7557                 if (evData0)
7558                         ds = "SAS Discovery: Start";
7559                 else
7560                         ds = "SAS Discovery: Stop";
7561                 break;
7562         }
7563         case MPI_EVENT_LOG_ENTRY_ADDED:
7564                 ds = "SAS Log Entry Added";
7565                 break;
7566 
7567         case MPI_EVENT_SAS_BROADCAST_PRIMITIVE:
7568         {
7569                 u8 phy_num = (u8)(evData0);
7570                 u8 port_num = (u8)(evData0 >> 8);
7571                 u8 port_width = (u8)(evData0 >> 16);
7572                 u8 primitive = (u8)(evData0 >> 24);
7573                 snprintf(evStr, EVENT_DESCR_STR_SZ,
7574                     "SAS Broadcast Primitive: phy=%d port=%d "
7575                     "width=%d primitive=0x%02x",
7576                     phy_num, port_num, port_width, primitive);
7577                 break;
7578         }
7579 
7580         case MPI_EVENT_SAS_INIT_DEVICE_STATUS_CHANGE:
7581         {
7582                 u8 reason = (u8)(evData0);
7583 
7584                 switch (reason) {
7585                 case MPI_EVENT_SAS_INIT_RC_ADDED:
7586                         ds = "SAS Initiator Status Change: Added";
7587                         break;
7588                 case MPI_EVENT_SAS_INIT_RC_REMOVED:
7589                         ds = "SAS Initiator Status Change: Deleted";
7590                         break;
7591                 default:
7592                         ds = "SAS Initiator Status Change";
7593                         break;
7594                 }
7595                 break;
7596         }
7597 
7598         case MPI_EVENT_SAS_INIT_TABLE_OVERFLOW:
7599         {
7600                 u8 max_init = (u8)(evData0);
7601                 u8 current_init = (u8)(evData0 >> 8);
7602 
7603                 snprintf(evStr, EVENT_DESCR_STR_SZ,
7604                     "SAS Initiator Device Table Overflow: max initiators=%02d "
7605                     "current initiators=%02d",
7606                     max_init, current_init);
7607                 break;
7608         }
7609         case MPI_EVENT_SAS_SMP_ERROR:
7610         {
7611                 u8 status = (u8)(evData0);
7612                 u8 port_num = (u8)(evData0 >> 8);
7613                 u8 result = (u8)(evData0 >> 16);
7614 
7615                 if (status == MPI_EVENT_SAS_SMP_FUNCTION_RESULT_VALID)
7616                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7617                             "SAS SMP Error: port=%d result=0x%02x",
7618                             port_num, result);
7619                 else if (status == MPI_EVENT_SAS_SMP_CRC_ERROR)
7620                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7621                             "SAS SMP Error: port=%d : CRC Error",
7622                             port_num);
7623                 else if (status == MPI_EVENT_SAS_SMP_TIMEOUT)
7624                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7625                             "SAS SMP Error: port=%d : Timeout",
7626                             port_num);
7627                 else if (status == MPI_EVENT_SAS_SMP_NO_DESTINATION)
7628                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7629                             "SAS SMP Error: port=%d : No Destination",
7630                             port_num);
7631                 else if (status == MPI_EVENT_SAS_SMP_BAD_DESTINATION)
7632                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7633                             "SAS SMP Error: port=%d : Bad Destination",
7634                             port_num);
7635                 else
7636                         snprintf(evStr, EVENT_DESCR_STR_SZ,
7637                             "SAS SMP Error: port=%d : status=0x%02x",
7638                             port_num, status);
7639                 break;
7640         }
7641 
7642         case MPI_EVENT_SAS_EXPANDER_STATUS_CHANGE:
7643         {
7644                 u8 reason = (u8)(evData0);
7645 
7646                 switch (reason) {
7647                 case MPI_EVENT_SAS_EXP_RC_ADDED:
7648                         ds = "Expander Status Change: Added";
7649                         break;
7650                 case MPI_EVENT_SAS_EXP_RC_NOT_RESPONDING:
7651                         ds = "Expander Status Change: Deleted";
7652                         break;
7653                 default:
7654                         ds = "Expander Status Change";
7655                         break;
7656                 }
7657                 break;
7658         }
7659 
7660         /*
7661          *  MPT base "custom" events may be added here...
7662          */
7663         default:
7664                 ds = "Unknown";
7665                 break;
7666         }
7667         if (ds)
7668                 strlcpy(evStr, ds, EVENT_DESCR_STR_SZ);
7669 
7670 
7671         devtprintk(ioc, printk(MYIOC_s_DEBUG_FMT
7672             "MPT event:(%02Xh) : %s\n",
7673             ioc->name, event, evStr));
7674 
7675         devtverboseprintk(ioc, printk(KERN_DEBUG MYNAM
7676             ": Event data:\n"));
7677         for (ii = 0; ii < le16_to_cpu(pEventReply->EventDataLength); ii++)
7678                 devtverboseprintk(ioc, printk(" %08x",
7679                     le32_to_cpu(pEventReply->Data[ii])));
7680         devtverboseprintk(ioc, printk(KERN_DEBUG "\n"));
7681 }
7682 #endif
7683 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
7684 /**
7685  *      ProcessEventNotification - Route EventNotificationReply to all event handlers
7686  *      @ioc: Pointer to MPT_ADAPTER structure
7687  *      @pEventReply: Pointer to EventNotification reply frame
7688  *      @evHandlers: Pointer to integer, number of event handlers
7689  *
7690  *      Routes a received EventNotificationReply to all currently registered
7691  *      event handlers.
7692  *      Returns sum of event handlers return values.
7693  */
7694 static int
7695 ProcessEventNotification(MPT_ADAPTER *ioc, EventNotificationReply_t *pEventReply, int *evHandlers)
7696 {
7697         u16 evDataLen;
7698         u32 evData0 = 0;
7699         int ii;
7700         u8 cb_idx;
7701         int r = 0;
7702         int handlers = 0;
7703         u8 event;
7704 
7705         /*
7706          *  Do platform normalization of values
7707          */
7708         event = le32_to_cpu(pEventReply->Event) & 0xFF;
7709         evDataLen = le16_to_cpu(pEventReply->EventDataLength);
7710         if (evDataLen) {
7711                 evData0 = le32_to_cpu(pEventReply->Data[0]);
7712         }
7713 
7714 #ifdef CONFIG_FUSION_LOGGING
7715         if (evDataLen)
7716                 mpt_display_event_info(ioc, pEventReply);
7717 #endif
7718 
7719         /*
7720          *  Do general / base driver event processing
7721          */
7722         switch(event) {
7723         case MPI_EVENT_EVENT_CHANGE:            /* 0A */
7724                 if (evDataLen) {
7725                         u8 evState = evData0 & 0xFF;
7726 
7727                         /* CHECKME! What if evState unexpectedly says OFF (0)? */
7728 
7729                         /* Update EventState field in cached IocFacts */
7730                         if (ioc->facts.Function) {
7731                                 ioc->facts.EventState = evState;
7732                         }
7733                 }
7734                 break;
7735         case MPI_EVENT_INTEGRATED_RAID:
7736                 mptbase_raid_process_event_data(ioc,
7737                     (MpiEventDataRaid_t *)pEventReply->Data);
7738                 break;
7739         default:
7740                 break;
7741         }
7742 
7743         /*
7744          * Should this event be logged? Events are written sequentially.
7745          * When buffer is full, start again at the top.
7746          */
7747         if (ioc->events && (ioc->eventTypes & ( 1 << event))) {
7748                 int idx;
7749 
7750                 idx = ioc->eventContext % MPTCTL_EVENT_LOG_SIZE;
7751 
7752                 ioc->events[idx].event = event;
7753                 ioc->events[idx].eventContext = ioc->eventContext;
7754 
7755                 for (ii = 0; ii < 2; ii++) {
7756                         if (ii < evDataLen)
7757                                 ioc->events[idx].data[ii] = le32_to_cpu(pEventReply->Data[ii]);
7758                         else
7759                                 ioc->events[idx].data[ii] =  0;
7760                 }
7761 
7762                 ioc->eventContext++;
7763         }
7764 
7765 
7766         /*
7767          *  Call each currently registered protocol event handler.
7768          */
7769         for (cb_idx = MPT_MAX_PROTOCOL_DRIVERS-1; cb_idx; cb_idx--) {
7770                 if (MptEvHandlers[cb_idx]) {
7771                         devtverboseprintk(ioc, printk(MYIOC_s_DEBUG_FMT
7772                             "Routing Event to event handler #%d\n",
7773                             ioc->name, cb_idx));
7774                         r += (*(MptEvHandlers[cb_idx]))(ioc, pEventReply);
7775                         handlers++;
7776                 }
7777         }
7778         /* FIXME?  Examine results here? */
7779 
7780         /*
7781          *  If needed, send (a single) EventAck.
7782          */
7783         if (pEventReply->AckRequired == MPI_EVENT_NOTIFICATION_ACK_REQUIRED) {
7784                 devtverboseprintk(ioc, printk(MYIOC_s_DEBUG_FMT
7785                         "EventAck required\n",ioc->name));
7786                 if ((ii = SendEventAck(ioc, pEventReply)) != 0) {
7787                         devtverboseprintk(ioc, printk(MYIOC_s_DEBUG_FMT "SendEventAck returned %d\n",
7788                                         ioc->name, ii));
7789                 }
7790         }
7791 
7792         *evHandlers = handlers;
7793         return r;
7794 }
7795 
7796 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
7797 /**
7798  *      mpt_fc_log_info - Log information returned from Fibre Channel IOC.
7799  *      @ioc: Pointer to MPT_ADAPTER structure
7800  *      @log_info: U32 LogInfo reply word from the IOC
7801  *
7802  *      Refer to lsi/mpi_log_fc.h.
7803  */
7804 static void
7805 mpt_fc_log_info(MPT_ADAPTER *ioc, u32 log_info)
7806 {
7807         char *desc = "unknown";
7808 
7809         switch (log_info & 0xFF000000) {
7810         case MPI_IOCLOGINFO_FC_INIT_BASE:
7811                 desc = "FCP Initiator";
7812                 break;
7813         case MPI_IOCLOGINFO_FC_TARGET_BASE:
7814                 desc = "FCP Target";
7815                 break;
7816         case MPI_IOCLOGINFO_FC_LAN_BASE:
7817                 desc = "LAN";
7818                 break;
7819         case MPI_IOCLOGINFO_FC_MSG_BASE:
7820                 desc = "MPI Message Layer";
7821                 break;
7822         case MPI_IOCLOGINFO_FC_LINK_BASE:
7823                 desc = "FC Link";
7824                 break;
7825         case MPI_IOCLOGINFO_FC_CTX_BASE:
7826                 desc = "Context Manager";
7827                 break;
7828         case MPI_IOCLOGINFO_FC_INVALID_FIELD_BYTE_OFFSET:
7829                 desc = "Invalid Field Offset";
7830                 break;
7831         case MPI_IOCLOGINFO_FC_STATE_CHANGE:
7832                 desc = "State Change Info";
7833                 break;
7834         }
7835 
7836         printk(MYIOC_s_INFO_FMT "LogInfo(0x%08x): SubClass={%s}, Value=(0x%06x)\n",
7837                         ioc->name, log_info, desc, (log_info & 0xFFFFFF));
7838 }
7839 
7840 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
7841 /**
7842  *      mpt_spi_log_info - Log information returned from SCSI Parallel IOC.
7843  *      @ioc: Pointer to MPT_ADAPTER structure
7844  *      @log_info: U32 LogInfo word from the IOC
7845  *
7846  *      Refer to lsi/sp_log.h.
7847  */
7848 static void
7849 mpt_spi_log_info(MPT_ADAPTER *ioc, u32 log_info)
7850 {
7851         u32 info = log_info & 0x00FF0000;
7852         char *desc = "unknown";
7853 
7854         switch (info) {
7855         case 0x00010000:
7856                 desc = "bug! MID not found";
7857                 break;
7858 
7859         case 0x00020000:
7860                 desc = "Parity Error";
7861                 break;
7862 
7863         case 0x00030000:
7864                 desc = "ASYNC Outbound Overrun";
7865                 break;
7866 
7867         case 0x00040000:
7868                 desc = "SYNC Offset Error";
7869                 break;
7870 
7871         case 0x00050000:
7872                 desc = "BM Change";
7873                 break;
7874 
7875         case 0x00060000:
7876                 desc = "Msg In Overflow";
7877                 break;
7878 
7879         case 0x00070000:
7880                 desc = "DMA Error";
7881                 break;
7882 
7883         case 0x00080000:
7884                 desc = "Outbound DMA Overrun";
7885                 break;
7886 
7887         case 0x00090000:
7888                 desc = "Task Management";
7889                 break;
7890 
7891         case 0x000A0000:
7892                 desc = "Device Problem";
7893                 break;
7894 
7895         case 0x000B0000:
7896                 desc = "Invalid Phase Change";
7897                 break;
7898 
7899         case 0x000C0000:
7900                 desc = "Untagged Table Size";
7901                 break;
7902 
7903         }
7904 
7905         printk(MYIOC_s_INFO_FMT "LogInfo(0x%08x): F/W: %s\n", ioc->name, log_info, desc);
7906 }
7907 
7908 /* strings for sas loginfo */
7909         static char *originator_str[] = {
7910                 "IOP",                                          /* 00h */
7911                 "PL",                                           /* 01h */
7912                 "IR"                                            /* 02h */
7913         };
7914         static char *iop_code_str[] = {
7915                 NULL,                                           /* 00h */
7916                 "Invalid SAS Address",                          /* 01h */
7917                 NULL,                                           /* 02h */
7918                 "Invalid Page",                                 /* 03h */
7919                 "Diag Message Error",                           /* 04h */
7920                 "Task Terminated",                              /* 05h */
7921                 "Enclosure Management",                         /* 06h */
7922                 "Target Mode"                                   /* 07h */
7923         };
7924         static char *pl_code_str[] = {
7925                 NULL,                                           /* 00h */
7926                 "Open Failure",                                 /* 01h */
7927                 "Invalid Scatter Gather List",                  /* 02h */
7928                 "Wrong Relative Offset or Frame Length",        /* 03h */
7929                 "Frame Transfer Error",                         /* 04h */
7930                 "Transmit Frame Connected Low",                 /* 05h */
7931                 "SATA Non-NCQ RW Error Bit Set",                /* 06h */
7932                 "SATA Read Log Receive Data Error",             /* 07h */
7933                 "SATA NCQ Fail All Commands After Error",       /* 08h */
7934                 "SATA Error in Receive Set Device Bit FIS",     /* 09h */
7935                 "Receive Frame Invalid Message",                /* 0Ah */
7936                 "Receive Context Message Valid Error",          /* 0Bh */
7937                 "Receive Frame Current Frame Error",            /* 0Ch */
7938                 "SATA Link Down",                               /* 0Dh */
7939                 "Discovery SATA Init W IOS",                    /* 0Eh */
7940                 "Config Invalid Page",                          /* 0Fh */
7941                 "Discovery SATA Init Timeout",                  /* 10h */
7942                 "Reset",                                        /* 11h */
7943                 "Abort",                                        /* 12h */
7944                 "IO Not Yet Executed",                          /* 13h */
7945                 "IO Executed",                                  /* 14h */
7946                 "Persistent Reservation Out Not Affiliation "
7947                     "Owner",                                    /* 15h */
7948                 "Open Transmit DMA Abort",                      /* 16h */
7949                 "IO Device Missing Delay Retry",                /* 17h */
7950                 "IO Cancelled Due to Receive Error",            /* 18h */
7951                 NULL,                                           /* 19h */
7952                 NULL,                                           /* 1Ah */
7953                 NULL,                                           /* 1Bh */
7954                 NULL,                                           /* 1Ch */
7955                 NULL,                                           /* 1Dh */
7956                 NULL,                                           /* 1Eh */
7957                 NULL,                                           /* 1Fh */
7958                 "Enclosure Management"                          /* 20h */
7959         };
7960         static char *ir_code_str[] = {
7961                 "Raid Action Error",                            /* 00h */
7962                 NULL,                                           /* 00h */
7963                 NULL,                                           /* 01h */
7964                 NULL,                                           /* 02h */
7965                 NULL,                                           /* 03h */
7966                 NULL,                                           /* 04h */
7967                 NULL,                                           /* 05h */
7968                 NULL,                                           /* 06h */
7969                 NULL                                            /* 07h */
7970         };
7971         static char *raid_sub_code_str[] = {
7972                 NULL,                                           /* 00h */
7973                 "Volume Creation Failed: Data Passed too "
7974                     "Large",                                    /* 01h */
7975                 "Volume Creation Failed: Duplicate Volumes "
7976                     "Attempted",                                /* 02h */
7977                 "Volume Creation Failed: Max Number "
7978                     "Supported Volumes Exceeded",               /* 03h */
7979                 "Volume Creation Failed: DMA Error",            /* 04h */
7980                 "Volume Creation Failed: Invalid Volume Type",  /* 05h */
7981                 "Volume Creation Failed: Error Reading "
7982                     "MFG Page 4",                               /* 06h */
7983                 "Volume Creation Failed: Creating Internal "
7984                     "Structures",                               /* 07h */
7985                 NULL,                                           /* 08h */
7986                 NULL,                                           /* 09h */
7987                 NULL,                                           /* 0Ah */
7988                 NULL,                                           /* 0Bh */
7989                 NULL,                                           /* 0Ch */
7990                 NULL,                                           /* 0Dh */
7991                 NULL,                                           /* 0Eh */
7992                 NULL,                                           /* 0Fh */
7993                 "Activation failed: Already Active Volume",     /* 10h */
7994                 "Activation failed: Unsupported Volume Type",   /* 11h */
7995                 "Activation failed: Too Many Active Volumes",   /* 12h */
7996                 "Activation failed: Volume ID in Use",          /* 13h */
7997                 "Activation failed: Reported Failure",          /* 14h */
7998                 "Activation failed: Importing a Volume",        /* 15h */
7999                 NULL,                                           /* 16h */
8000                 NULL,                                           /* 17h */
8001                 NULL,                                           /* 18h */
8002                 NULL,                                           /* 19h */
8003                 NULL,                                           /* 1Ah */
8004                 NULL,                                           /* 1Bh */
8005                 NULL,                                           /* 1Ch */
8006                 NULL,                                           /* 1Dh */
8007                 NULL,                                           /* 1Eh */
8008                 NULL,                                           /* 1Fh */
8009                 "Phys Disk failed: Too Many Phys Disks",        /* 20h */
8010                 "Phys Disk failed: Data Passed too Large",      /* 21h */
8011                 "Phys Disk failed: DMA Error",                  /* 22h */
8012                 "Phys Disk failed: Invalid <channel:id>",       /* 23h */
8013                 "Phys Disk failed: Creating Phys Disk Config "
8014                     "Page",                                     /* 24h */
8015                 NULL,                                           /* 25h */
8016                 NULL,                                           /* 26h */
8017                 NULL,                                           /* 27h */
8018                 NULL,                                           /* 28h */
8019                 NULL,                                           /* 29h */
8020                 NULL,                                           /* 2Ah */
8021                 NULL,                                           /* 2Bh */
8022                 NULL,                                           /* 2Ch */
8023                 NULL,                                           /* 2Dh */
8024                 NULL,                                           /* 2Eh */
8025                 NULL,                                           /* 2Fh */
8026                 "Compatibility Error: IR Disabled",             /* 30h */
8027                 "Compatibility Error: Inquiry Command Failed",  /* 31h */
8028                 "Compatibility Error: Device not Direct Access "
8029                     "Device ",                                  /* 32h */
8030                 "Compatibility Error: Removable Device Found",  /* 33h */
8031                 "Compatibility Error: Device SCSI Version not "
8032                     "2 or Higher",                              /* 34h */
8033                 "Compatibility Error: SATA Device, 48 BIT LBA "
8034                     "not Supported",                            /* 35h */
8035                 "Compatibility Error: Device doesn't have "
8036                     "512 Byte Block Sizes",                     /* 36h */
8037                 "Compatibility Error: Volume Type Check Failed", /* 37h */
8038                 "Compatibility Error: Volume Type is "
8039                     "Unsupported by FW",                        /* 38h */
8040                 "Compatibility Error: Disk Drive too Small for "
8041                     "use in Volume",                            /* 39h */
8042                 "Compatibility Error: Phys Disk for Create "
8043                     "Volume not Found",                         /* 3Ah */
8044                 "Compatibility Error: Too Many or too Few "
8045                     "Disks for Volume Type",                    /* 3Bh */
8046                 "Compatibility Error: Disk stripe Sizes "
8047                     "Must be 64KB",                             /* 3Ch */
8048                 "Compatibility Error: IME Size Limited to < 2TB", /* 3Dh */
8049         };
8050 
8051 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
8052 /**
8053  *      mpt_sas_log_info - Log information returned from SAS IOC.
8054  *      @ioc: Pointer to MPT_ADAPTER structure
8055  *      @log_info: U32 LogInfo reply word from the IOC
8056  *      @cb_idx: callback function's handle
8057  *
8058  *      Refer to lsi/mpi_log_sas.h.
8059  **/
8060 static void
8061 mpt_sas_log_info(MPT_ADAPTER *ioc, u32 log_info, u8 cb_idx)
8062 {
8063         union loginfo_type {
8064                 u32     loginfo;
8065                 struct {
8066                         u32     subcode:16;
8067                         u32     code:8;
8068                         u32     originator:4;
8069                         u32     bus_type:4;
8070                 } dw;
8071         };
8072         union loginfo_type sas_loginfo;
8073         char *originator_desc = NULL;
8074         char *code_desc = NULL;
8075         char *sub_code_desc = NULL;
8076 
8077         sas_loginfo.loginfo = log_info;
8078         if ((sas_loginfo.dw.bus_type != 3 /*SAS*/) &&
8079             (sas_loginfo.dw.originator < ARRAY_SIZE(originator_str)))
8080                 return;
8081 
8082         originator_desc = originator_str[sas_loginfo.dw.originator];
8083 
8084         switch (sas_loginfo.dw.originator) {
8085 
8086                 case 0:  /* IOP */
8087                         if (sas_loginfo.dw.code <
8088                             ARRAY_SIZE(iop_code_str))
8089                                 code_desc = iop_code_str[sas_loginfo.dw.code];
8090                         break;
8091                 case 1:  /* PL */
8092                         if (sas_loginfo.dw.code <
8093                             ARRAY_SIZE(pl_code_str))
8094                                 code_desc = pl_code_str[sas_loginfo.dw.code];
8095                         break;
8096                 case 2:  /* IR */
8097                         if (sas_loginfo.dw.code >=
8098                             ARRAY_SIZE(ir_code_str))
8099                                 break;
8100                         code_desc = ir_code_str[sas_loginfo.dw.code];
8101                         if (sas_loginfo.dw.subcode >=
8102                             ARRAY_SIZE(raid_sub_code_str))
8103                                 break;
8104                         if (sas_loginfo.dw.code == 0)
8105                                 sub_code_desc =
8106                                     raid_sub_code_str[sas_loginfo.dw.subcode];
8107                         break;
8108                 default:
8109                         return;
8110         }
8111 
8112         if (sub_code_desc != NULL)
8113                 printk(MYIOC_s_INFO_FMT
8114                         "LogInfo(0x%08x): Originator={%s}, Code={%s},"
8115                         " SubCode={%s} cb_idx %s\n",
8116                         ioc->name, log_info, originator_desc, code_desc,
8117                         sub_code_desc, MptCallbacksName[cb_idx]);
8118         else if (code_desc != NULL)
8119                 printk(MYIOC_s_INFO_FMT
8120                         "LogInfo(0x%08x): Originator={%s}, Code={%s},"
8121                         " SubCode(0x%04x) cb_idx %s\n",
8122                         ioc->name, log_info, originator_desc, code_desc,
8123                         sas_loginfo.dw.subcode, MptCallbacksName[cb_idx]);
8124         else
8125                 printk(MYIOC_s_INFO_FMT
8126                         "LogInfo(0x%08x): Originator={%s}, Code=(0x%02x),"
8127                         " SubCode(0x%04x) cb_idx %s\n",
8128                         ioc->name, log_info, originator_desc,
8129                         sas_loginfo.dw.code, sas_loginfo.dw.subcode,
8130                         MptCallbacksName[cb_idx]);
8131 }
8132 
8133 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
8134 /**
8135  *      mpt_iocstatus_info_config - IOCSTATUS information for config pages
8136  *      @ioc: Pointer to MPT_ADAPTER structure
8137  *      @ioc_status: U32 IOCStatus word from IOC
8138  *      @mf: Pointer to MPT request frame
8139  *
8140  *      Refer to lsi/mpi.h.
8141  **/
8142 static void
8143 mpt_iocstatus_info_config(MPT_ADAPTER *ioc, u32 ioc_status, MPT_FRAME_HDR *mf)
8144 {
8145         Config_t *pReq = (Config_t *)mf;
8146         char extend_desc[EVENT_DESCR_STR_SZ];
8147         char *desc = NULL;
8148         u32 form;
8149         u8 page_type;
8150 
8151         if (pReq->Header.PageType == MPI_CONFIG_PAGETYPE_EXTENDED)
8152                 page_type = pReq->ExtPageType;
8153         else
8154                 page_type = pReq->Header.PageType;
8155 
8156         /*
8157          * ignore invalid page messages for GET_NEXT_HANDLE
8158          */
8159         form = le32_to_cpu(pReq->PageAddress);
8160         if (ioc_status == MPI_IOCSTATUS_CONFIG_INVALID_PAGE) {
8161                 if (page_type == MPI_CONFIG_EXTPAGETYPE_SAS_DEVICE ||
8162                     page_type == MPI_CONFIG_EXTPAGETYPE_SAS_EXPANDER ||
8163                     page_type == MPI_CONFIG_EXTPAGETYPE_ENCLOSURE) {
8164                         if ((form >> MPI_SAS_DEVICE_PGAD_FORM_SHIFT) ==
8165                                 MPI_SAS_DEVICE_PGAD_FORM_GET_NEXT_HANDLE)
8166                                 return;
8167                 }
8168                 if (page_type == MPI_CONFIG_PAGETYPE_FC_DEVICE)
8169                         if ((form & MPI_FC_DEVICE_PGAD_FORM_MASK) ==
8170                                 MPI_FC_DEVICE_PGAD_FORM_NEXT_DID)
8171                                 return;
8172         }
8173 
8174         snprintf(extend_desc, EVENT_DESCR_STR_SZ,
8175             "type=%02Xh, page=%02Xh, action=%02Xh, form=%08Xh",
8176             page_type, pReq->Header.PageNumber, pReq->Action, form);
8177 
8178         switch (ioc_status) {
8179 
8180         case MPI_IOCSTATUS_CONFIG_INVALID_ACTION: /* 0x0020 */
8181                 desc = "Config Page Invalid Action";
8182                 break;
8183 
8184         case MPI_IOCSTATUS_CONFIG_INVALID_TYPE:   /* 0x0021 */
8185                 desc = "Config Page Invalid Type";
8186                 break;
8187 
8188         case MPI_IOCSTATUS_CONFIG_INVALID_PAGE:   /* 0x0022 */
8189                 desc = "Config Page Invalid Page";
8190                 break;
8191 
8192         case MPI_IOCSTATUS_CONFIG_INVALID_DATA:   /* 0x0023 */
8193                 desc = "Config Page Invalid Data";
8194                 break;
8195 
8196         case MPI_IOCSTATUS_CONFIG_NO_DEFAULTS:    /* 0x0024 */
8197                 desc = "Config Page No Defaults";
8198                 break;
8199 
8200         case MPI_IOCSTATUS_CONFIG_CANT_COMMIT:    /* 0x0025 */
8201                 desc = "Config Page Can't Commit";
8202                 break;
8203         }
8204 
8205         if (!desc)
8206                 return;
8207 
8208         dreplyprintk(ioc, printk(MYIOC_s_DEBUG_FMT "IOCStatus(0x%04X): %s: %s\n",
8209             ioc->name, ioc_status, desc, extend_desc));
8210 }
8211 
8212 /**
8213  *      mpt_iocstatus_info - IOCSTATUS information returned from IOC.
8214  *      @ioc: Pointer to MPT_ADAPTER structure
8215  *      @ioc_status: U32 IOCStatus word from IOC
8216  *      @mf: Pointer to MPT request frame
8217  *
8218  *      Refer to lsi/mpi.h.
8219  **/
8220 static void
8221 mpt_iocstatus_info(MPT_ADAPTER *ioc, u32 ioc_status, MPT_FRAME_HDR *mf)
8222 {
8223         u32 status = ioc_status & MPI_IOCSTATUS_MASK;
8224         char *desc = NULL;
8225 
8226         switch (status) {
8227 
8228 /****************************************************************************/
8229 /*  Common IOCStatus values for all replies                                 */
8230 /****************************************************************************/
8231 
8232         case MPI_IOCSTATUS_INVALID_FUNCTION: /* 0x0001 */
8233                 desc = "Invalid Function";
8234                 break;
8235 
8236         case MPI_IOCSTATUS_BUSY: /* 0x0002 */
8237                 desc = "Busy";
8238                 break;
8239 
8240         case MPI_IOCSTATUS_INVALID_SGL: /* 0x0003 */
8241                 desc = "Invalid SGL";
8242                 break;
8243 
8244         case MPI_IOCSTATUS_INTERNAL_ERROR: /* 0x0004 */
8245                 desc = "Internal Error";
8246                 break;
8247 
8248         case MPI_IOCSTATUS_RESERVED: /* 0x0005 */
8249                 desc = "Reserved";
8250                 break;
8251 
8252         case MPI_IOCSTATUS_INSUFFICIENT_RESOURCES: /* 0x0006 */
8253                 desc = "Insufficient Resources";
8254                 break;
8255 
8256         case MPI_IOCSTATUS_INVALID_FIELD: /* 0x0007 */
8257                 desc = "Invalid Field";
8258                 break;
8259 
8260         case MPI_IOCSTATUS_INVALID_STATE: /* 0x0008 */
8261                 desc = "Invalid State";
8262                 break;
8263 
8264 /****************************************************************************/
8265 /*  Config IOCStatus values                                                 */
8266 /****************************************************************************/
8267 
8268         case MPI_IOCSTATUS_CONFIG_INVALID_ACTION: /* 0x0020 */
8269         case MPI_IOCSTATUS_CONFIG_INVALID_TYPE:   /* 0x0021 */
8270         case MPI_IOCSTATUS_CONFIG_INVALID_PAGE:   /* 0x0022 */
8271         case MPI_IOCSTATUS_CONFIG_INVALID_DATA:   /* 0x0023 */
8272         case MPI_IOCSTATUS_CONFIG_NO_DEFAULTS:    /* 0x0024 */
8273         case MPI_IOCSTATUS_CONFIG_CANT_COMMIT:    /* 0x0025 */
8274                 mpt_iocstatus_info_config(ioc, status, mf);
8275                 break;
8276 
8277 /****************************************************************************/
8278 /*  SCSIIO Reply (SPI, FCP, SAS) initiator values                           */
8279 /*                                                                          */
8280 /*  Look at mptscsih_iocstatus_info_scsiio in mptscsih.c */
8281 /*                                                                          */
8282 /****************************************************************************/
8283 
8284         case MPI_IOCSTATUS_SCSI_RECOVERED_ERROR: /* 0x0040 */
8285         case MPI_IOCSTATUS_SCSI_DATA_UNDERRUN: /* 0x0045 */
8286         case MPI_IOCSTATUS_SCSI_INVALID_BUS: /* 0x0041 */
8287         case MPI_IOCSTATUS_SCSI_INVALID_TARGETID: /* 0x0042 */
8288         case MPI_IOCSTATUS_SCSI_DEVICE_NOT_THERE: /* 0x0043 */
8289         case MPI_IOCSTATUS_SCSI_DATA_OVERRUN: /* 0x0044 */
8290         case MPI_IOCSTATUS_SCSI_IO_DATA_ERROR: /* 0x0046 */
8291         case MPI_IOCSTATUS_SCSI_PROTOCOL_ERROR: /* 0x0047 */
8292         case MPI_IOCSTATUS_SCSI_TASK_TERMINATED: /* 0x0048 */
8293         case MPI_IOCSTATUS_SCSI_RESIDUAL_MISMATCH: /* 0x0049 */
8294         case MPI_IOCSTATUS_SCSI_TASK_MGMT_FAILED: /* 0x004A */
8295         case MPI_IOCSTATUS_SCSI_IOC_TERMINATED: /* 0x004B */
8296         case MPI_IOCSTATUS_SCSI_EXT_TERMINATED: /* 0x004C */
8297                 break;
8298 
8299 /****************************************************************************/
8300 /*  SCSI Target values                                                      */
8301 /****************************************************************************/
8302 
8303         case MPI_IOCSTATUS_TARGET_PRIORITY_IO: /* 0x0060 */
8304                 desc = "Target: Priority IO";
8305                 break;
8306 
8307         case MPI_IOCSTATUS_TARGET_INVALID_PORT: /* 0x0061 */
8308                 desc = "Target: Invalid Port";
8309                 break;
8310 
8311         case MPI_IOCSTATUS_TARGET_INVALID_IO_INDEX: /* 0x0062 */
8312                 desc = "Target Invalid IO Index:";
8313                 break;
8314 
8315         case MPI_IOCSTATUS_TARGET_ABORTED: /* 0x0063 */
8316                 desc = "Target: Aborted";
8317                 break;
8318 
8319         case MPI_IOCSTATUS_TARGET_NO_CONN_RETRYABLE: /* 0x0064 */
8320                 desc = "Target: No Conn Retryable";
8321                 break;
8322 
8323         case MPI_IOCSTATUS_TARGET_NO_CONNECTION: /* 0x0065 */
8324                 desc = "Target: No Connection";
8325                 break;
8326 
8327         case MPI_IOCSTATUS_TARGET_XFER_COUNT_MISMATCH: /* 0x006A */
8328                 desc = "Target: Transfer Count Mismatch";
8329                 break;
8330 
8331         case MPI_IOCSTATUS_TARGET_STS_DATA_NOT_SENT: /* 0x006B */
8332                 desc = "Target: STS Data not Sent";
8333                 break;
8334 
8335         case MPI_IOCSTATUS_TARGET_DATA_OFFSET_ERROR: /* 0x006D */
8336                 desc = "Target: Data Offset Error";
8337                 break;
8338 
8339         case MPI_IOCSTATUS_TARGET_TOO_MUCH_WRITE_DATA: /* 0x006E */
8340                 desc = "Target: Too Much Write Data";
8341                 break;
8342 
8343         case MPI_IOCSTATUS_TARGET_IU_TOO_SHORT: /* 0x006F */
8344                 desc = "Target: IU Too Short";
8345                 break;
8346 
8347         case MPI_IOCSTATUS_TARGET_ACK_NAK_TIMEOUT: /* 0x0070 */
8348                 desc = "Target: ACK NAK Timeout";
8349                 break;
8350 
8351         case MPI_IOCSTATUS_TARGET_NAK_RECEIVED: /* 0x0071 */
8352                 desc = "Target: Nak Received";
8353                 break;
8354 
8355 /****************************************************************************/
8356 /*  Fibre Channel Direct Access values                                      */
8357 /****************************************************************************/
8358 
8359         case MPI_IOCSTATUS_FC_ABORTED: /* 0x0066 */
8360                 desc = "FC: Aborted";
8361                 break;
8362 
8363         case MPI_IOCSTATUS_FC_RX_ID_INVALID: /* 0x0067 */
8364                 desc = "FC: RX ID Invalid";
8365                 break;
8366 
8367         case MPI_IOCSTATUS_FC_DID_INVALID: /* 0x0068 */
8368                 desc = "FC: DID Invalid";
8369                 break;
8370 
8371         case MPI_IOCSTATUS_FC_NODE_LOGGED_OUT: /* 0x0069 */
8372                 desc = "FC: Node Logged Out";
8373                 break;
8374 
8375         case MPI_IOCSTATUS_FC_EXCHANGE_CANCELED: /* 0x006C */
8376                 desc = "FC: Exchange Canceled";
8377                 break;
8378 
8379 /****************************************************************************/
8380 /*  LAN values                                                              */
8381 /****************************************************************************/
8382 
8383         case MPI_IOCSTATUS_LAN_DEVICE_NOT_FOUND: /* 0x0080 */
8384                 desc = "LAN: Device not Found";
8385                 break;
8386 
8387         case MPI_IOCSTATUS_LAN_DEVICE_FAILURE: /* 0x0081 */
8388                 desc = "LAN: Device Failure";
8389                 break;
8390 
8391         case MPI_IOCSTATUS_LAN_TRANSMIT_ERROR: /* 0x0082 */
8392                 desc = "LAN: Transmit Error";
8393                 break;
8394 
8395         case MPI_IOCSTATUS_LAN_TRANSMIT_ABORTED: /* 0x0083 */
8396                 desc = "LAN: Transmit Aborted";
8397                 break;
8398 
8399         case MPI_IOCSTATUS_LAN_RECEIVE_ERROR: /* 0x0084 */
8400                 desc = "LAN: Receive Error";
8401                 break;
8402 
8403         case MPI_IOCSTATUS_LAN_RECEIVE_ABORTED: /* 0x0085 */
8404                 desc = "LAN: Receive Aborted";
8405                 break;
8406 
8407         case MPI_IOCSTATUS_LAN_PARTIAL_PACKET: /* 0x0086 */
8408                 desc = "LAN: Partial Packet";
8409                 break;
8410 
8411         case MPI_IOCSTATUS_LAN_CANCELED: /* 0x0087 */
8412                 desc = "LAN: Canceled";
8413                 break;
8414 
8415 /****************************************************************************/
8416 /*  Serial Attached SCSI values                                             */
8417 /****************************************************************************/
8418 
8419         case MPI_IOCSTATUS_SAS_SMP_REQUEST_FAILED: /* 0x0090 */
8420                 desc = "SAS: SMP Request Failed";
8421                 break;
8422 
8423         case MPI_IOCSTATUS_SAS_SMP_DATA_OVERRUN: /* 0x0090 */
8424                 desc = "SAS: SMP Data Overrun";
8425                 break;
8426 
8427         default:
8428                 desc = "Others";
8429                 break;
8430         }
8431 
8432         if (!desc)
8433                 return;
8434 
8435         dreplyprintk(ioc, printk(MYIOC_s_DEBUG_FMT "IOCStatus(0x%04X): %s\n",
8436             ioc->name, status, desc));
8437 }
8438 
8439 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
8440 EXPORT_SYMBOL(mpt_attach);
8441 EXPORT_SYMBOL(mpt_detach);
8442 #ifdef CONFIG_PM
8443 EXPORT_SYMBOL(mpt_resume);
8444 EXPORT_SYMBOL(mpt_suspend);
8445 #endif
8446 EXPORT_SYMBOL(ioc_list);
8447 EXPORT_SYMBOL(mpt_register);
8448 EXPORT_SYMBOL(mpt_deregister);
8449 EXPORT_SYMBOL(mpt_event_register);
8450 EXPORT_SYMBOL(mpt_event_deregister);
8451 EXPORT_SYMBOL(mpt_reset_register);
8452 EXPORT_SYMBOL(mpt_reset_deregister);
8453 EXPORT_SYMBOL(mpt_device_driver_register);
8454 EXPORT_SYMBOL(mpt_device_driver_deregister);
8455 EXPORT_SYMBOL(mpt_get_msg_frame);
8456 EXPORT_SYMBOL(mpt_put_msg_frame);
8457 EXPORT_SYMBOL(mpt_put_msg_frame_hi_pri);
8458 EXPORT_SYMBOL(mpt_free_msg_frame);
8459 EXPORT_SYMBOL(mpt_send_handshake_request);
8460 EXPORT_SYMBOL(mpt_verify_adapter);
8461 EXPORT_SYMBOL(mpt_GetIocState);
8462 EXPORT_SYMBOL(mpt_print_ioc_summary);
8463 EXPORT_SYMBOL(mpt_HardResetHandler);
8464 EXPORT_SYMBOL(mpt_config);
8465 EXPORT_SYMBOL(mpt_findImVolumes);
8466 EXPORT_SYMBOL(mpt_alloc_fw_memory);
8467 EXPORT_SYMBOL(mpt_free_fw_memory);
8468 EXPORT_SYMBOL(mptbase_sas_persist_operation);
8469 EXPORT_SYMBOL(mpt_raid_phys_disk_pg0);
8470 
8471 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
8472 /**
8473  *      fusion_init - Fusion MPT base driver initialization routine.
8474  *
8475  *      Returns 0 for success, non-zero for failure.
8476  */
8477 static int __init
8478 fusion_init(void)
8479 {
8480         u8 cb_idx;
8481 
8482         show_mptmod_ver(my_NAME, my_VERSION);
8483         printk(KERN_INFO COPYRIGHT "\n");
8484 
8485         for (cb_idx = 0; cb_idx < MPT_MAX_PROTOCOL_DRIVERS; cb_idx++) {
8486                 MptCallbacks[cb_idx] = NULL;
8487                 MptDriverClass[cb_idx] = MPTUNKNOWN_DRIVER;
8488                 MptEvHandlers[cb_idx] = NULL;
8489                 MptResetHandlers[cb_idx] = NULL;
8490         }
8491 
8492         /*  Register ourselves (mptbase) in order to facilitate
8493          *  EventNotification handling.
8494          */
8495         mpt_base_index = mpt_register(mptbase_reply, MPTBASE_DRIVER,
8496             "mptbase_reply");
8497 
8498         /* Register for hard reset handling callbacks.
8499          */
8500         mpt_reset_register(mpt_base_index, mpt_ioc_reset);
8501 
8502 #ifdef CONFIG_PROC_FS
8503         (void) procmpt_create();
8504 #endif
8505         return 0;
8506 }
8507 
8508 /*=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=*/
8509 /**
8510  *      fusion_exit - Perform driver unload cleanup.
8511  *
8512  *      This routine frees all resources associated with each MPT adapter
8513  *      and removes all %MPT_PROCFS_MPTBASEDIR entries.
8514  */
8515 static void __exit
8516 fusion_exit(void)
8517 {
8518 
8519         mpt_reset_deregister(mpt_base_index);
8520 
8521 #ifdef CONFIG_PROC_FS
8522         procmpt_destroy();
8523 #endif
8524 }
8525 
8526 module_init(fusion_init);
8527 module_exit(fusion_exit);

/* [<][>][^][v][top][bottom][index][help] */