mpt2sas: Fix unsafe using smp_processor_id() in preemptible
[pandora-kernel.git] / drivers / scsi / mvsas / mv_sas.c
index 4958fef..a4884a5 100644 (file)
@@ -214,7 +214,7 @@ int mvs_phy_control(struct asd_sas_phy *sas_phy, enum phy_func func,
                break;
        case PHY_FUNC_RELEASE_SPINUP_HOLD:
        default:
-               rc = -EOPNOTSUPP;
+               rc = -ENOSYS;
        }
        msleep(200);
        return rc;
@@ -265,6 +265,12 @@ static void mvs_bytes_dmaed(struct mvs_info *mvi, int i)
                id->dev_type = phy->identify.device_type;
                id->initiator_bits = SAS_PROTOCOL_ALL;
                id->target_bits = phy->identify.target_port_protocols;
+
+               /* direct attached SAS device */
+               if (phy->att_dev_info & PORT_SSP_TRGT_MASK) {
+                       MVS_CHIP_DISP->write_port_cfg_addr(mvi, i, PHYR_PHY_STAT);
+                       MVS_CHIP_DISP->write_port_cfg_data(mvi, i, 0x00);
+               }
        } else if (phy->phy_type & PORT_TYPE_SATA) {
                /*Nothing*/
        }
@@ -276,36 +282,6 @@ static void mvs_bytes_dmaed(struct mvs_info *mvi, int i)
                                   PORTE_BYTES_DMAED);
 }
 
-int mvs_slave_alloc(struct scsi_device *scsi_dev)
-{
-       struct domain_device *dev = sdev_to_domain_dev(scsi_dev);
-       if (dev_is_sata(dev)) {
-               /* We don't need to rescan targets
-                * if REPORT_LUNS request is failed
-                */
-               if (scsi_dev->lun > 0)
-                       return -ENXIO;
-               scsi_dev->tagged_supported = 1;
-       }
-
-       return sas_slave_alloc(scsi_dev);
-}
-
-int mvs_slave_configure(struct scsi_device *sdev)
-{
-       struct domain_device *dev = sdev_to_domain_dev(sdev);
-       int ret = sas_slave_configure(sdev);
-
-       if (ret)
-               return ret;
-       if (!dev_is_sata(dev)) {
-               sas_change_queue_depth(sdev,
-                       MVS_QUEUE_SIZE,
-                       SCSI_QDEPTH_DEFAULT);
-       }
-       return 0;
-}
-
 void mvs_scan_start(struct Scsi_Host *shost)
 {
        int i, j;
@@ -426,7 +402,7 @@ static int mvs_task_prep_smp(struct mvs_info *mvi,
        /* generate open address frame hdr (first 12 bytes) */
        /* initiator, SMP, ftype 1h */
        buf_oaf[0] = (1 << 7) | (PROTOCOL_SMP << 4) | 0x01;
-       buf_oaf[1] = dev->linkrate & 0xf;
+       buf_oaf[1] = min(sas_port->linkrate, dev->linkrate) & 0xf;
        *(u16 *)(buf_oaf + 2) = 0xFFFF;         /* SAS SPEC */
        memcpy(buf_oaf + 4, dev->sas_addr, SAS_ADDR_SIZE);
 
@@ -571,7 +547,7 @@ static int mvs_task_prep_ata(struct mvs_info *mvi,
        /* generate open address frame hdr (first 12 bytes) */
        /* initiator, STP, ftype 1h */
        buf_oaf[0] = (1 << 7) | (PROTOCOL_STP << 4) | 0x1;
-       buf_oaf[1] = dev->linkrate & 0xf;
+       buf_oaf[1] = min(sas_port->linkrate, dev->linkrate) & 0xf;
        *(u16 *)(buf_oaf + 2) = cpu_to_be16(mvi_dev->device_id + 1);
        memcpy(buf_oaf + 4, dev->sas_addr, SAS_ADDR_SIZE);
 
@@ -679,7 +655,7 @@ static int mvs_task_prep_ssp(struct mvs_info *mvi,
        /* generate open address frame hdr (first 12 bytes) */
        /* initiator, SSP, ftype 1h */
        buf_oaf[0] = (1 << 7) | (PROTOCOL_SSP << 4) | 0x1;
-       buf_oaf[1] = dev->linkrate & 0xf;
+       buf_oaf[1] = min(sas_port->linkrate, dev->linkrate) & 0xf;
        *(u16 *)(buf_oaf + 2) = cpu_to_be16(mvi_dev->device_id + 1);
        memcpy(buf_oaf + 4, dev->sas_addr, SAS_ADDR_SIZE);
 
@@ -1241,6 +1217,12 @@ static void mvs_port_notify_formed(struct asd_sas_phy *sas_phy, int lock)
                port->wide_port_phymap = sas_port->phy_mask;
                mv_printk("set wide port phy map %x\n", sas_port->phy_mask);
                mvs_update_wideport(mvi, sas_phy->id);
+
+               /* direct attached SAS device */
+               if (phy->att_dev_info & PORT_SSP_TRGT_MASK) {
+                       MVS_CHIP_DISP->write_port_cfg_addr(mvi, i, PHYR_PHY_STAT);
+                       MVS_CHIP_DISP->write_port_cfg_data(mvi, i, 0x04);
+               }
        }
        if (lock)
                spin_unlock_irqrestore(&mvi->lock, flags);
@@ -1387,28 +1369,6 @@ void mvs_dev_gone(struct domain_device *dev)
        mvs_dev_gone_notify(dev);
 }
 
-static  struct sas_task *mvs_alloc_task(void)
-{
-       struct sas_task *task = kzalloc(sizeof(struct sas_task), GFP_KERNEL);
-
-       if (task) {
-               INIT_LIST_HEAD(&task->list);
-               spin_lock_init(&task->task_state_lock);
-               task->task_state_flags = SAS_TASK_STATE_PENDING;
-               init_timer(&task->timer);
-               init_completion(&task->completion);
-       }
-       return task;
-}
-
-static  void mvs_free_task(struct sas_task *task)
-{
-       if (task) {
-               BUG_ON(!list_empty(&task->list));
-               kfree(task);
-       }
-}
-
 static void mvs_task_done(struct sas_task *task)
 {
        if (!del_timer(&task->timer))
@@ -1432,7 +1392,7 @@ static int mvs_exec_internal_tmf_task(struct domain_device *dev,
        struct sas_task *task = NULL;
 
        for (retry = 0; retry < 3; retry++) {
-               task = mvs_alloc_task();
+               task = sas_alloc_task(GFP_KERNEL);
                if (!task)
                        return -ENOMEM;
 
@@ -1490,15 +1450,14 @@ static int mvs_exec_internal_tmf_task(struct domain_device *dev,
                                    SAS_ADDR(dev->sas_addr),
                                    task->task_status.resp,
                                    task->task_status.stat);
-                       mvs_free_task(task);
+                       sas_free_task(task);
                        task = NULL;
 
                }
        }
 ex_err:
        BUG_ON(retry == 3 && task != NULL);
-       if (task != NULL)
-               mvs_free_task(task);
+       sas_free_task(task);
        return res;
 }