[libata] kill ata_sg_is_last()
Short term, this works around a bug introduced by early sg-chaining
work.
Long term, removing this function eliminates a branch from a hot
path loop in each scatter/gather table build. Also, as this code
demonstrates, we don't need to _track_ the end of the s/g list, as
long as we mark it in some way. And doing so programatically is nice.
So its a useful cleanup, regardless of its short term effects.
Based conceptually on a quick patch by Jens Axboe.
Signed-off-by: Jeff Garzik <jgarzik@redhat.com>
diff --git a/drivers/scsi/ipr.c b/drivers/scsi/ipr.c
index b41dfb5..c316a0b 100644
--- a/drivers/scsi/ipr.c
+++ b/drivers/scsi/ipr.c
@@ -5134,6 +5134,7 @@
u32 ioadl_flags = 0;
struct ipr_ioarcb *ioarcb = &ipr_cmd->ioarcb;
struct ipr_ioadl_desc *ioadl = ipr_cmd->ioadl;
+ struct ipr_ioadl_desc *last_ioadl = NULL;
int len = qc->nbytes + qc->pad_len;
struct scatterlist *sg;
@@ -5156,11 +5157,13 @@
ata_for_each_sg(sg, qc) {
ioadl->flags_and_data_len = cpu_to_be32(ioadl_flags | sg_dma_len(sg));
ioadl->address = cpu_to_be32(sg_dma_address(sg));
- if (ata_sg_is_last(sg, qc))
- ioadl->flags_and_data_len |= cpu_to_be32(IPR_IOADL_FLAGS_LAST);
- else
- ioadl++;
+
+ last_ioadl = ioadl;
+ ioadl++;
}
+
+ if (likely(last_ioadl))
+ last_ioadl->flags_and_data_len |= cpu_to_be32(IPR_IOADL_FLAGS_LAST);
}
/**