aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/libsas/sas_ata.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/libsas/sas_ata.c')
-rw-r--r--drivers/scsi/libsas/sas_ata.c36
1 files changed, 23 insertions, 13 deletions
diff --git a/drivers/scsi/libsas/sas_ata.c b/drivers/scsi/libsas/sas_ata.c
index 83118d0b6d0c..81ce39d166d1 100644
--- a/drivers/scsi/libsas/sas_ata.c
+++ b/drivers/scsi/libsas/sas_ata.c
@@ -166,23 +166,30 @@ qc_already_gone:
166 166
167static unsigned int sas_ata_qc_issue(struct ata_queued_cmd *qc) 167static unsigned int sas_ata_qc_issue(struct ata_queued_cmd *qc)
168{ 168{
169 int res; 169 unsigned long flags;
170 struct sas_task *task; 170 struct sas_task *task;
171 struct domain_device *dev = qc->ap->private_data; 171 struct scatterlist *sg;
172 int ret = AC_ERR_SYSTEM;
173 unsigned int si, xfer = 0;
174 struct ata_port *ap = qc->ap;
175 struct domain_device *dev = ap->private_data;
172 struct sas_ha_struct *sas_ha = dev->port->ha; 176 struct sas_ha_struct *sas_ha = dev->port->ha;
173 struct Scsi_Host *host = sas_ha->core.shost; 177 struct Scsi_Host *host = sas_ha->core.shost;
174 struct sas_internal *i = to_sas_internal(host->transportt); 178 struct sas_internal *i = to_sas_internal(host->transportt);
175 struct scatterlist *sg; 179
176 unsigned int xfer = 0; 180 /* TODO: audit callers to ensure they are ready for qc_issue to
177 unsigned int si; 181 * unconditionally re-enable interrupts
182 */
183 local_irq_save(flags);
184 spin_unlock(ap->lock);
178 185
179 /* If the device fell off, no sense in issuing commands */ 186 /* If the device fell off, no sense in issuing commands */
180 if (dev->gone) 187 if (dev->gone)
181 return AC_ERR_SYSTEM; 188 goto out;
182 189
183 task = sas_alloc_task(GFP_ATOMIC); 190 task = sas_alloc_task(GFP_ATOMIC);
184 if (!task) 191 if (!task)
185 return AC_ERR_SYSTEM; 192 goto out;
186 task->dev = dev; 193 task->dev = dev;
187 task->task_proto = SAS_PROTOCOL_STP; 194 task->task_proto = SAS_PROTOCOL_STP;
188 task->task_done = sas_ata_task_done; 195 task->task_done = sas_ata_task_done;
@@ -227,21 +234,24 @@ static unsigned int sas_ata_qc_issue(struct ata_queued_cmd *qc)
227 ASSIGN_SAS_TASK(qc->scsicmd, task); 234 ASSIGN_SAS_TASK(qc->scsicmd, task);
228 235
229 if (sas_ha->lldd_max_execute_num < 2) 236 if (sas_ha->lldd_max_execute_num < 2)
230 res = i->dft->lldd_execute_task(task, 1, GFP_ATOMIC); 237 ret = i->dft->lldd_execute_task(task, 1, GFP_ATOMIC);
231 else 238 else
232 res = sas_queue_up(task); 239 ret = sas_queue_up(task);
233 240
234 /* Examine */ 241 /* Examine */
235 if (res) { 242 if (ret) {
236 SAS_DPRINTK("lldd_execute_task returned: %d\n", res); 243 SAS_DPRINTK("lldd_execute_task returned: %d\n", ret);
237 244
238 if (qc->scsicmd) 245 if (qc->scsicmd)
239 ASSIGN_SAS_TASK(qc->scsicmd, NULL); 246 ASSIGN_SAS_TASK(qc->scsicmd, NULL);
240 sas_free_task(task); 247 sas_free_task(task);
241 return AC_ERR_SYSTEM; 248 ret = AC_ERR_SYSTEM;
242 } 249 }
243 250
244 return 0; 251 out:
252 spin_lock(ap->lock);
253 local_irq_restore(flags);
254 return ret;
245} 255}
246 256
247static bool sas_ata_qc_fill_rtf(struct ata_queued_cmd *qc) 257static bool sas_ata_qc_fill_rtf(struct ata_queued_cmd *qc)