diff options
Diffstat (limited to 'drivers/ata/libata-core.c')
| -rw-r--r-- | drivers/ata/libata-core.c | 36 | 
1 files changed, 34 insertions, 2 deletions
diff --git a/drivers/ata/libata-core.c b/drivers/ata/libata-core.c index 28c492be0a57..6f4ab5c5b52d 100644 --- a/drivers/ata/libata-core.c +++ b/drivers/ata/libata-core.c @@ -4980,7 +4980,10 @@ int ata_std_qc_defer(struct ata_queued_cmd *qc)  	return ATA_DEFER_LINK;  } -void ata_noop_qc_prep(struct ata_queued_cmd *qc) { } +enum ata_completion_errors ata_noop_qc_prep(struct ata_queued_cmd *qc) +{ +	return AC_ERR_OK; +}  /**   *	ata_sg_init - Associate command with scatter-gather table. @@ -5326,6 +5329,30 @@ void ata_qc_complete(struct ata_queued_cmd *qc)  }  /** + *	ata_qc_get_active - get bitmask of active qcs + *	@ap: port in question + * + *	LOCKING: + *	spin_lock_irqsave(host lock) + * + *	RETURNS: + *	Bitmask of active qcs + */ +u64 ata_qc_get_active(struct ata_port *ap) +{ +	u64 qc_active = ap->qc_active; + +	/* ATA_TAG_INTERNAL is sent to hw as tag 0 */ +	if (qc_active & (1ULL << ATA_TAG_INTERNAL)) { +		qc_active |= (1 << 0); +		qc_active &= ~(1ULL << ATA_TAG_INTERNAL); +	} + +	return qc_active; +} +EXPORT_SYMBOL_GPL(ata_qc_get_active); + +/**   *	ata_qc_complete_multiple - Complete multiple qcs successfully   *	@ap: port in question   *	@qc_active: new qc_active mask @@ -5443,7 +5470,9 @@ void ata_qc_issue(struct ata_queued_cmd *qc)  		return;  	} -	ap->ops->qc_prep(qc); +	qc->err_mask |= ap->ops->qc_prep(qc); +	if (unlikely(qc->err_mask)) +		goto err;  	trace_ata_qc_issue(qc);  	qc->err_mask |= ap->ops->qc_issue(qc);  	if (unlikely(qc->err_mask)) @@ -6708,6 +6737,9 @@ void ata_host_detach(struct ata_host *host)  {  	int i; +	/* Ensure ata_port probe has completed */ +	async_synchronize_full(); +  	for (i = 0; i < host->n_ports; i++)  		ata_port_detach(host->ports[i]);  |