ata: move ata_qc_complete_multiple() to libata-sata.c
* move ata_qc_complete_multiple() to libata-sata.c Code size savings on m68k arch using (modified) atari_defconfig: text data bss dec hex filename before: 32559 572 40 33171 8193 drivers/ata/libata-core.o after: 32162 572 40 32774 8006 drivers/ata/libata-core.o Reviewed-by: Christoph Hellwig <hch@lst.de> Signed-off-by: Bartlomiej Zolnierkiewicz <b.zolnierkie@samsung.com> Signed-off-by: Jens Axboe <axboe@kernel.dk>
This commit is contained in:
Родитель
78c97c80d7
Коммит
61a11986d3
|
@ -4749,65 +4749,6 @@ u64 ata_qc_get_active(struct ata_port *ap)
|
|||
}
|
||||
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
|
||||
*
|
||||
* Complete in-flight commands. This functions is meant to be
|
||||
* called from low-level driver's interrupt routine to complete
|
||||
* requests normally. ap->qc_active and @qc_active is compared
|
||||
* and commands are completed accordingly.
|
||||
*
|
||||
* Always use this function when completing multiple NCQ commands
|
||||
* from IRQ handlers instead of calling ata_qc_complete()
|
||||
* multiple times to keep IRQ expect status properly in sync.
|
||||
*
|
||||
* LOCKING:
|
||||
* spin_lock_irqsave(host lock)
|
||||
*
|
||||
* RETURNS:
|
||||
* Number of completed commands on success, -errno otherwise.
|
||||
*/
|
||||
int ata_qc_complete_multiple(struct ata_port *ap, u64 qc_active)
|
||||
{
|
||||
u64 done_mask, ap_qc_active = ap->qc_active;
|
||||
int nr_done = 0;
|
||||
|
||||
/*
|
||||
* If the internal tag is set on ap->qc_active, then we care about
|
||||
* bit0 on the passed in qc_active mask. Move that bit up to match
|
||||
* the internal tag.
|
||||
*/
|
||||
if (ap_qc_active & (1ULL << ATA_TAG_INTERNAL)) {
|
||||
qc_active |= (qc_active & 0x01) << ATA_TAG_INTERNAL;
|
||||
qc_active ^= qc_active & 0x01;
|
||||
}
|
||||
|
||||
done_mask = ap_qc_active ^ qc_active;
|
||||
|
||||
if (unlikely(done_mask & qc_active)) {
|
||||
ata_port_err(ap, "illegal qc_active transition (%08llx->%08llx)\n",
|
||||
ap->qc_active, qc_active);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
while (done_mask) {
|
||||
struct ata_queued_cmd *qc;
|
||||
unsigned int tag = __ffs64(done_mask);
|
||||
|
||||
qc = ata_qc_from_tag(ap, tag);
|
||||
if (qc) {
|
||||
ata_qc_complete(qc);
|
||||
nr_done++;
|
||||
}
|
||||
done_mask &= ~(1ULL << tag);
|
||||
}
|
||||
|
||||
return nr_done;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(ata_qc_complete_multiple);
|
||||
|
||||
/**
|
||||
* ata_qc_issue - issue taskfile to device
|
||||
* @qc: command to issue to device
|
||||
|
|
|
@ -603,6 +603,65 @@ int sata_link_hardreset(struct ata_link *link, const unsigned long *timing,
|
|||
}
|
||||
EXPORT_SYMBOL_GPL(sata_link_hardreset);
|
||||
|
||||
/**
|
||||
* ata_qc_complete_multiple - Complete multiple qcs successfully
|
||||
* @ap: port in question
|
||||
* @qc_active: new qc_active mask
|
||||
*
|
||||
* Complete in-flight commands. This functions is meant to be
|
||||
* called from low-level driver's interrupt routine to complete
|
||||
* requests normally. ap->qc_active and @qc_active is compared
|
||||
* and commands are completed accordingly.
|
||||
*
|
||||
* Always use this function when completing multiple NCQ commands
|
||||
* from IRQ handlers instead of calling ata_qc_complete()
|
||||
* multiple times to keep IRQ expect status properly in sync.
|
||||
*
|
||||
* LOCKING:
|
||||
* spin_lock_irqsave(host lock)
|
||||
*
|
||||
* RETURNS:
|
||||
* Number of completed commands on success, -errno otherwise.
|
||||
*/
|
||||
int ata_qc_complete_multiple(struct ata_port *ap, u64 qc_active)
|
||||
{
|
||||
u64 done_mask, ap_qc_active = ap->qc_active;
|
||||
int nr_done = 0;
|
||||
|
||||
/*
|
||||
* If the internal tag is set on ap->qc_active, then we care about
|
||||
* bit0 on the passed in qc_active mask. Move that bit up to match
|
||||
* the internal tag.
|
||||
*/
|
||||
if (ap_qc_active & (1ULL << ATA_TAG_INTERNAL)) {
|
||||
qc_active |= (qc_active & 0x01) << ATA_TAG_INTERNAL;
|
||||
qc_active ^= qc_active & 0x01;
|
||||
}
|
||||
|
||||
done_mask = ap_qc_active ^ qc_active;
|
||||
|
||||
if (unlikely(done_mask & qc_active)) {
|
||||
ata_port_err(ap, "illegal qc_active transition (%08llx->%08llx)\n",
|
||||
ap->qc_active, qc_active);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
while (done_mask) {
|
||||
struct ata_queued_cmd *qc;
|
||||
unsigned int tag = __ffs64(done_mask);
|
||||
|
||||
qc = ata_qc_from_tag(ap, tag);
|
||||
if (qc) {
|
||||
ata_qc_complete(qc);
|
||||
nr_done++;
|
||||
}
|
||||
done_mask &= ~(1ULL << tag);
|
||||
}
|
||||
|
||||
return nr_done;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(ata_qc_complete_multiple);
|
||||
|
||||
/**
|
||||
* ata_slave_link_init - initialize slave link
|
||||
* @ap: port to initialize slave link for
|
||||
|
|
|
@ -1160,7 +1160,6 @@ extern void ata_id_c_string(const u16 *id, unsigned char *s,
|
|||
extern unsigned int ata_do_dev_read_id(struct ata_device *dev,
|
||||
struct ata_taskfile *tf, u16 *id);
|
||||
extern void ata_qc_complete(struct ata_queued_cmd *qc);
|
||||
extern int ata_qc_complete_multiple(struct ata_port *ap, u64 qc_active);
|
||||
extern u64 ata_qc_get_active(struct ata_port *ap);
|
||||
extern void ata_scsi_simulate(struct ata_device *dev, struct scsi_cmnd *cmd);
|
||||
extern int ata_std_bios_param(struct scsi_device *sdev,
|
||||
|
@ -1232,6 +1231,7 @@ extern int ata_slave_link_init(struct ata_port *ap);
|
|||
extern void ata_tf_to_fis(const struct ata_taskfile *tf,
|
||||
u8 pmp, int is_cmd, u8 *fis);
|
||||
extern void ata_tf_from_fis(const u8 *fis, struct ata_taskfile *tf);
|
||||
extern int ata_qc_complete_multiple(struct ata_port *ap, u64 qc_active);
|
||||
extern bool sata_lpm_ignore_phy_events(struct ata_link *link);
|
||||
|
||||
extern int ata_cable_40wire(struct ata_port *ap);
|
||||
|
|
Загрузка…
Ссылка в новой задаче