]> git.karo-electronics.de Git - karo-tx-linux.git/blobdiff - drivers/scsi/ipr.c
Merge branch 'for-linus' of git://git.infradead.org/users/vkoul/slave-dma
[karo-tx-linux.git] / drivers / scsi / ipr.c
index 25dc6e594f71c350f035d4cdcd8e2dc902a2f6e1..924b0ba74dfea7aceadbf19673fa72ba6c82b10a 100644 (file)
@@ -2367,6 +2367,42 @@ static void ipr_log_generic_error(struct ipr_ioa_cfg *ioa_cfg,
                         be32_to_cpu(hostrcb->hcam.length));
 }
 
+/**
+ * ipr_log_sis64_device_error - Log a cache error.
+ * @ioa_cfg:   ioa config struct
+ * @hostrcb:   hostrcb struct
+ *
+ * Return value:
+ *     none
+ **/
+static void ipr_log_sis64_device_error(struct ipr_ioa_cfg *ioa_cfg,
+                                        struct ipr_hostrcb *hostrcb)
+{
+       struct ipr_hostrcb_type_21_error *error;
+       char buffer[IPR_MAX_RES_PATH_LENGTH];
+
+       error = &hostrcb->hcam.u.error64.u.type_21_error;
+
+       ipr_err("-----Failing Device Information-----\n");
+       ipr_err("World Wide Unique ID: %08X%08X%08X%08X\n",
+               be32_to_cpu(error->wwn[0]), be32_to_cpu(error->wwn[1]),
+                be32_to_cpu(error->wwn[2]), be32_to_cpu(error->wwn[3]));
+       ipr_err("Device Resource Path: %s\n",
+               __ipr_format_res_path(error->res_path,
+                                     buffer, sizeof(buffer)));
+       error->primary_problem_desc[sizeof(error->primary_problem_desc) - 1] = '\0';
+       error->second_problem_desc[sizeof(error->second_problem_desc) - 1] = '\0';
+       ipr_err("Primary Problem Description: %s\n", error->primary_problem_desc);
+       ipr_err("Secondary Problem Description:  %s\n", error->second_problem_desc);
+       ipr_err("SCSI Sense Data:\n");
+       ipr_log_hex_data(ioa_cfg, error->sense_data, sizeof(error->sense_data));
+       ipr_err("SCSI Command Descriptor Block: \n");
+       ipr_log_hex_data(ioa_cfg, error->cdb, sizeof(error->cdb));
+
+       ipr_err("Additional IOA Data:\n");
+       ipr_log_hex_data(ioa_cfg, error->ioa_data, be32_to_cpu(error->length_of_error));
+}
+
 /**
  * ipr_get_error - Find the specfied IOASC in the ipr_error_table.
  * @ioasc:     IOASC
@@ -2468,6 +2504,9 @@ static void ipr_handle_log_data(struct ipr_ioa_cfg *ioa_cfg,
        case IPR_HOST_RCB_OVERLAY_ID_20:
                ipr_log_fabric_error(ioa_cfg, hostrcb);
                break;
+       case IPR_HOST_RCB_OVERLAY_ID_21:
+               ipr_log_sis64_device_error(ioa_cfg, hostrcb);
+               break;
        case IPR_HOST_RCB_OVERLAY_ID_23:
                ipr_log_sis64_config_error(ioa_cfg, hostrcb);
                break;
@@ -3631,16 +3670,14 @@ static ssize_t ipr_store_iopoll_weight(struct device *dev,
                return strlen(buf);
        }
 
-       if (blk_iopoll_enabled && ioa_cfg->iopoll_weight &&
-                       ioa_cfg->sis64 && ioa_cfg->nvectors > 1) {
+       if (ioa_cfg->iopoll_weight && ioa_cfg->sis64 && ioa_cfg->nvectors > 1) {
                for (i = 1; i < ioa_cfg->hrrq_num; i++)
                        blk_iopoll_disable(&ioa_cfg->hrrq[i].iopoll);
        }
 
        spin_lock_irqsave(shost->host_lock, lock_flags);
        ioa_cfg->iopoll_weight = user_iopoll_weight;
-       if (blk_iopoll_enabled && ioa_cfg->iopoll_weight &&
-                       ioa_cfg->sis64 && ioa_cfg->nvectors > 1) {
+       if (ioa_cfg->iopoll_weight && ioa_cfg->sis64 && ioa_cfg->nvectors > 1) {
                for (i = 1; i < ioa_cfg->hrrq_num; i++) {
                        blk_iopoll_init(&ioa_cfg->hrrq[i].iopoll,
                                        ioa_cfg->iopoll_weight, ipr_iopoll);
@@ -5486,8 +5523,7 @@ static irqreturn_t ipr_isr_mhrrq(int irq, void *devp)
                return IRQ_NONE;
        }
 
-       if (blk_iopoll_enabled && ioa_cfg->iopoll_weight &&
-                       ioa_cfg->sis64 && ioa_cfg->nvectors > 1) {
+       if (ioa_cfg->iopoll_weight && ioa_cfg->sis64 && ioa_cfg->nvectors > 1) {
                if ((be32_to_cpu(*hrrq->hrrq_curr) & IPR_HRRQ_TOGGLE_BIT) ==
                       hrrq->toggle_bit) {
                        if (!blk_iopoll_sched_prep(&hrrq->iopoll))
@@ -9317,53 +9353,40 @@ static void ipr_wait_for_pci_err_recovery(struct ipr_ioa_cfg *ioa_cfg)
 static int ipr_enable_msix(struct ipr_ioa_cfg *ioa_cfg)
 {
        struct msix_entry entries[IPR_MAX_MSIX_VECTORS];
-       int i, err, vectors;
+       int i, vectors;
 
        for (i = 0; i < ARRAY_SIZE(entries); ++i)
                entries[i].entry = i;
 
-       vectors = ipr_number_of_msix;
-
-       while ((err = pci_enable_msix(ioa_cfg->pdev, entries, vectors)) > 0)
-                       vectors = err;
-
-       if (err < 0) {
+       vectors = pci_enable_msix_range(ioa_cfg->pdev,
+                                       entries, 1, ipr_number_of_msix);
+       if (vectors < 0) {
                ipr_wait_for_pci_err_recovery(ioa_cfg);
-               pci_disable_msix(ioa_cfg->pdev);
-               return err;
+               return vectors;
        }
 
-       if (!err) {
-               for (i = 0; i < vectors; i++)
-                       ioa_cfg->vectors_info[i].vec = entries[i].vector;
-               ioa_cfg->nvectors = vectors;
-       }
+       for (i = 0; i < vectors; i++)
+               ioa_cfg->vectors_info[i].vec = entries[i].vector;
+       ioa_cfg->nvectors = vectors;
 
-       return err;
+       return 0;
 }
 
 static int ipr_enable_msi(struct ipr_ioa_cfg *ioa_cfg)
 {
-       int i, err, vectors;
-
-       vectors = ipr_number_of_msix;
+       int i, vectors;
 
-       while ((err = pci_enable_msi_block(ioa_cfg->pdev, vectors)) > 0)
-                       vectors = err;
-
-       if (err < 0) {
+       vectors = pci_enable_msi_range(ioa_cfg->pdev, 1, ipr_number_of_msix);
+       if (vectors < 0) {
                ipr_wait_for_pci_err_recovery(ioa_cfg);
-               pci_disable_msi(ioa_cfg->pdev);
-               return err;
+               return vectors;
        }
 
-       if (!err) {
-               for (i = 0; i < vectors; i++)
-                       ioa_cfg->vectors_info[i].vec = ioa_cfg->pdev->irq + i;
-               ioa_cfg->nvectors = vectors;
-       }
+       for (i = 0; i < vectors; i++)
+               ioa_cfg->vectors_info[i].vec = ioa_cfg->pdev->irq + i;
+       ioa_cfg->nvectors = vectors;
 
-       return err;
+       return 0;
 }
 
 static void name_msi_vectors(struct ipr_ioa_cfg *ioa_cfg)
@@ -9428,7 +9451,7 @@ static irqreturn_t ipr_test_intr(int irq, void *devp)
  * ipr_test_msi - Test for Message Signaled Interrupt (MSI) support.
  * @pdev:              PCI device struct
  *
- * Description: The return value from pci_enable_msi() can not always be
+ * Description: The return value from pci_enable_msi_range() can not always be
  * trusted.  This routine sets up and initiates a test interrupt to determine
  * if the interrupt is received via the ipr_test_intr() service routine.
  * If the tests fails, the driver will fall back to LSI.
@@ -9949,8 +9972,7 @@ static int ipr_probe(struct pci_dev *pdev, const struct pci_device_id *dev_id)
        ioa_cfg->host->max_channel = IPR_VSET_BUS;
        ioa_cfg->iopoll_weight = ioa_cfg->chip_cfg->iopoll_weight;
 
-       if (blk_iopoll_enabled && ioa_cfg->iopoll_weight &&
-                       ioa_cfg->sis64 && ioa_cfg->nvectors > 1) {
+       if (ioa_cfg->iopoll_weight && ioa_cfg->sis64 && ioa_cfg->nvectors > 1) {
                for (i = 1; i < ioa_cfg->hrrq_num; i++) {
                        blk_iopoll_init(&ioa_cfg->hrrq[i].iopoll,
                                        ioa_cfg->iopoll_weight, ipr_iopoll);
@@ -9979,8 +10001,7 @@ static void ipr_shutdown(struct pci_dev *pdev)
        int i;
 
        spin_lock_irqsave(ioa_cfg->host->host_lock, lock_flags);
-       if (blk_iopoll_enabled && ioa_cfg->iopoll_weight &&
-                       ioa_cfg->sis64 && ioa_cfg->nvectors > 1) {
+       if (ioa_cfg->iopoll_weight && ioa_cfg->sis64 && ioa_cfg->nvectors > 1) {
                ioa_cfg->iopoll_weight = 0;
                for (i = 1; i < ioa_cfg->hrrq_num; i++)
                        blk_iopoll_disable(&ioa_cfg->hrrq[i].iopoll);
@@ -10097,6 +10118,12 @@ static struct pci_device_id ipr_pci_table[] = {
                PCI_VENDOR_ID_IBM, IPR_SUBS_DEV_ID_57EF, 0, 0, 0 },
        { PCI_VENDOR_ID_IBM, PCI_DEVICE_ID_IBM_CROCODILE,
                PCI_VENDOR_ID_IBM, IPR_SUBS_DEV_ID_57F0, 0, 0, 0 },
+       { PCI_VENDOR_ID_IBM, PCI_DEVICE_ID_IBM_CROCODILE,
+               PCI_VENDOR_ID_IBM, IPR_SUBS_DEV_ID_2CCA, 0, 0, 0 },
+       { PCI_VENDOR_ID_IBM, PCI_DEVICE_ID_IBM_CROCODILE,
+               PCI_VENDOR_ID_IBM, IPR_SUBS_DEV_ID_2CD2, 0, 0, 0 },
+       { PCI_VENDOR_ID_IBM, PCI_DEVICE_ID_IBM_CROCODILE,
+               PCI_VENDOR_ID_IBM, IPR_SUBS_DEV_ID_2CCD, 0, 0, 0 },
        { }
 };
 MODULE_DEVICE_TABLE(pci, ipr_pci_table);