diff options
author | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-10-30 14:49:13 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-10-30 14:49:13 -0400 |
commit | 8c1ee54cb3ff750dc39a5e1db8075e2352bbd1b8 (patch) | |
tree | f49bd934f7e06950a6dd11436a1297cf734fb848 | |
parent | 97855b49b6bac0bd25f16b017883634d13591d00 (diff) | |
parent | e027bd36c146582cef382364e5c826db93d4427b (diff) |
Merge branch 'upstream-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jgarzik/libata-dev
* 'upstream-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jgarzik/libata-dev:
libata: implement and use ATA_QCFLAG_QUIET
libata: stop being overjealous about non-IO commands
libata: flush is an IO command
sata_promise: cleanups
sata_promise: ASIC PRD table bug workaround, take 2
-rw-r--r-- | drivers/ata/libata-eh.c | 20 | ||||
-rw-r--r-- | drivers/ata/libata-scsi.c | 7 | ||||
-rw-r--r-- | drivers/ata/sata_promise.c | 104 | ||||
-rw-r--r-- | drivers/ata/sata_sil24.c | 6 | ||||
-rw-r--r-- | include/linux/libata.h | 1 |
5 files changed, 115 insertions, 23 deletions
diff --git a/drivers/ata/libata-eh.c b/drivers/ata/libata-eh.c index fefea7470e51..8d64f8fd8f1d 100644 --- a/drivers/ata/libata-eh.c +++ b/drivers/ata/libata-eh.c | |||
@@ -1800,10 +1800,8 @@ static void ata_eh_link_autopsy(struct ata_link *link) | |||
1800 | qc->err_mask &= ~AC_ERR_OTHER; | 1800 | qc->err_mask &= ~AC_ERR_OTHER; |
1801 | 1801 | ||
1802 | /* SENSE_VALID trumps dev/unknown error and revalidation */ | 1802 | /* SENSE_VALID trumps dev/unknown error and revalidation */ |
1803 | if (qc->flags & ATA_QCFLAG_SENSE_VALID) { | 1803 | if (qc->flags & ATA_QCFLAG_SENSE_VALID) |
1804 | qc->err_mask &= ~(AC_ERR_DEV | AC_ERR_OTHER); | 1804 | qc->err_mask &= ~(AC_ERR_DEV | AC_ERR_OTHER); |
1805 | ehc->i.action &= ~ATA_EH_REVALIDATE; | ||
1806 | } | ||
1807 | 1805 | ||
1808 | /* accumulate error info */ | 1806 | /* accumulate error info */ |
1809 | ehc->i.dev = qc->dev; | 1807 | ehc->i.dev = qc->dev; |
@@ -1816,7 +1814,8 @@ static void ata_eh_link_autopsy(struct ata_link *link) | |||
1816 | if (ap->pflags & ATA_PFLAG_FROZEN || | 1814 | if (ap->pflags & ATA_PFLAG_FROZEN || |
1817 | all_err_mask & (AC_ERR_HSM | AC_ERR_TIMEOUT)) | 1815 | all_err_mask & (AC_ERR_HSM | AC_ERR_TIMEOUT)) |
1818 | ehc->i.action |= ATA_EH_SOFTRESET; | 1816 | ehc->i.action |= ATA_EH_SOFTRESET; |
1819 | else if (all_err_mask) | 1817 | else if ((is_io && all_err_mask) || |
1818 | (!is_io && (all_err_mask & ~AC_ERR_DEV))) | ||
1820 | ehc->i.action |= ATA_EH_REVALIDATE; | 1819 | ehc->i.action |= ATA_EH_REVALIDATE; |
1821 | 1820 | ||
1822 | /* if we have offending qcs and the associated failed device */ | 1821 | /* if we have offending qcs and the associated failed device */ |
@@ -1879,7 +1878,9 @@ static void ata_eh_link_report(struct ata_link *link) | |||
1879 | for (tag = 0; tag < ATA_MAX_QUEUE; tag++) { | 1878 | for (tag = 0; tag < ATA_MAX_QUEUE; tag++) { |
1880 | struct ata_queued_cmd *qc = __ata_qc_from_tag(ap, tag); | 1879 | struct ata_queued_cmd *qc = __ata_qc_from_tag(ap, tag); |
1881 | 1880 | ||
1882 | if (!(qc->flags & ATA_QCFLAG_FAILED) || qc->dev->link != link) | 1881 | if (!(qc->flags & ATA_QCFLAG_FAILED) || qc->dev->link != link || |
1882 | ((qc->flags & ATA_QCFLAG_QUIET) && | ||
1883 | qc->err_mask == AC_ERR_DEV)) | ||
1883 | continue; | 1884 | continue; |
1884 | if (qc->flags & ATA_QCFLAG_SENSE_VALID && !qc->err_mask) | 1885 | if (qc->flags & ATA_QCFLAG_SENSE_VALID && !qc->err_mask) |
1885 | continue; | 1886 | continue; |
@@ -2697,8 +2698,15 @@ void ata_eh_finish(struct ata_port *ap) | |||
2697 | /* FIXME: Once EH migration is complete, | 2698 | /* FIXME: Once EH migration is complete, |
2698 | * generate sense data in this function, | 2699 | * generate sense data in this function, |
2699 | * considering both err_mask and tf. | 2700 | * considering both err_mask and tf. |
2701 | * | ||
2702 | * There's no point in retrying invalid | ||
2703 | * (detected by libata) and non-IO device | ||
2704 | * errors (rejected by device). Finish them | ||
2705 | * immediately. | ||
2700 | */ | 2706 | */ |
2701 | if (qc->err_mask & AC_ERR_INVALID) | 2707 | if ((qc->err_mask & AC_ERR_INVALID) || |
2708 | (!(qc->flags & ATA_QCFLAG_IO) && | ||
2709 | qc->err_mask == AC_ERR_DEV)) | ||
2702 | ata_eh_qc_complete(qc); | 2710 | ata_eh_qc_complete(qc); |
2703 | else | 2711 | else |
2704 | ata_eh_qc_retry(qc); | 2712 | ata_eh_qc_retry(qc); |
diff --git a/drivers/ata/libata-scsi.c b/drivers/ata/libata-scsi.c index 93bd36c19690..fc89590d3772 100644 --- a/drivers/ata/libata-scsi.c +++ b/drivers/ata/libata-scsi.c | |||
@@ -1108,6 +1108,9 @@ static unsigned int ata_scsi_flush_xlat(struct ata_queued_cmd *qc) | |||
1108 | else | 1108 | else |
1109 | tf->command = ATA_CMD_FLUSH; | 1109 | tf->command = ATA_CMD_FLUSH; |
1110 | 1110 | ||
1111 | /* flush is critical for IO integrity, consider it an IO command */ | ||
1112 | qc->flags |= ATA_QCFLAG_IO; | ||
1113 | |||
1111 | return 0; | 1114 | return 0; |
1112 | } | 1115 | } |
1113 | 1116 | ||
@@ -2764,8 +2767,8 @@ static unsigned int ata_scsi_pass_thru(struct ata_queued_cmd *qc) | |||
2764 | */ | 2767 | */ |
2765 | qc->nbytes = scsi_bufflen(scmd); | 2768 | qc->nbytes = scsi_bufflen(scmd); |
2766 | 2769 | ||
2767 | /* request result TF */ | 2770 | /* request result TF and be quiet about device error */ |
2768 | qc->flags |= ATA_QCFLAG_RESULT_TF; | 2771 | qc->flags |= ATA_QCFLAG_RESULT_TF | ATA_QCFLAG_QUIET; |
2769 | 2772 | ||
2770 | return 0; | 2773 | return 0; |
2771 | 2774 | ||
diff --git a/drivers/ata/sata_promise.c b/drivers/ata/sata_promise.c index deb26f04f2d7..825e717bcef9 100644 --- a/drivers/ata/sata_promise.c +++ b/drivers/ata/sata_promise.c | |||
@@ -2,6 +2,7 @@ | |||
2 | * sata_promise.c - Promise SATA | 2 | * sata_promise.c - Promise SATA |
3 | * | 3 | * |
4 | * Maintained by: Jeff Garzik <jgarzik@pobox.com> | 4 | * Maintained by: Jeff Garzik <jgarzik@pobox.com> |
5 | * Mikael Pettersson <mikpe@it.uu.se> | ||
5 | * Please ALWAYS copy linux-ide@vger.kernel.org | 6 | * Please ALWAYS copy linux-ide@vger.kernel.org |
6 | * on emails. | 7 | * on emails. |
7 | * | 8 | * |
@@ -45,11 +46,12 @@ | |||
45 | #include "sata_promise.h" | 46 | #include "sata_promise.h" |
46 | 47 | ||
47 | #define DRV_NAME "sata_promise" | 48 | #define DRV_NAME "sata_promise" |
48 | #define DRV_VERSION "2.10" | 49 | #define DRV_VERSION "2.11" |
49 | 50 | ||
50 | enum { | 51 | enum { |
51 | PDC_MAX_PORTS = 4, | 52 | PDC_MAX_PORTS = 4, |
52 | PDC_MMIO_BAR = 3, | 53 | PDC_MMIO_BAR = 3, |
54 | PDC_MAX_PRD = LIBATA_MAX_PRD - 1, /* -1 for ASIC PRD bug workaround */ | ||
53 | 55 | ||
54 | /* register offsets */ | 56 | /* register offsets */ |
55 | PDC_FEATURE = 0x04, /* Feature/Error reg (per port) */ | 57 | PDC_FEATURE = 0x04, /* Feature/Error reg (per port) */ |
@@ -157,7 +159,7 @@ static struct scsi_host_template pdc_ata_sht = { | |||
157 | .queuecommand = ata_scsi_queuecmd, | 159 | .queuecommand = ata_scsi_queuecmd, |
158 | .can_queue = ATA_DEF_QUEUE, | 160 | .can_queue = ATA_DEF_QUEUE, |
159 | .this_id = ATA_SHT_THIS_ID, | 161 | .this_id = ATA_SHT_THIS_ID, |
160 | .sg_tablesize = LIBATA_MAX_PRD, | 162 | .sg_tablesize = PDC_MAX_PRD, |
161 | .cmd_per_lun = ATA_SHT_CMD_PER_LUN, | 163 | .cmd_per_lun = ATA_SHT_CMD_PER_LUN, |
162 | .emulated = ATA_SHT_EMULATED, | 164 | .emulated = ATA_SHT_EMULATED, |
163 | .use_clustering = ATA_SHT_USE_CLUSTERING, | 165 | .use_clustering = ATA_SHT_USE_CLUSTERING, |
@@ -240,7 +242,7 @@ static const struct ata_port_operations pdc_pata_ops = { | |||
240 | }; | 242 | }; |
241 | 243 | ||
242 | static const struct ata_port_info pdc_port_info[] = { | 244 | static const struct ata_port_info pdc_port_info[] = { |
243 | /* board_2037x */ | 245 | [board_2037x] = |
244 | { | 246 | { |
245 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SATA | | 247 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SATA | |
246 | PDC_FLAG_SATA_PATA, | 248 | PDC_FLAG_SATA_PATA, |
@@ -250,7 +252,7 @@ static const struct ata_port_info pdc_port_info[] = { | |||
250 | .port_ops = &pdc_old_sata_ops, | 252 | .port_ops = &pdc_old_sata_ops, |
251 | }, | 253 | }, |
252 | 254 | ||
253 | /* board_2037x_pata */ | 255 | [board_2037x_pata] = |
254 | { | 256 | { |
255 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SLAVE_POSS, | 257 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SLAVE_POSS, |
256 | .pio_mask = 0x1f, /* pio0-4 */ | 258 | .pio_mask = 0x1f, /* pio0-4 */ |
@@ -259,7 +261,7 @@ static const struct ata_port_info pdc_port_info[] = { | |||
259 | .port_ops = &pdc_pata_ops, | 261 | .port_ops = &pdc_pata_ops, |
260 | }, | 262 | }, |
261 | 263 | ||
262 | /* board_20319 */ | 264 | [board_20319] = |
263 | { | 265 | { |
264 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SATA | | 266 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SATA | |
265 | PDC_FLAG_4_PORTS, | 267 | PDC_FLAG_4_PORTS, |
@@ -269,7 +271,7 @@ static const struct ata_port_info pdc_port_info[] = { | |||
269 | .port_ops = &pdc_old_sata_ops, | 271 | .port_ops = &pdc_old_sata_ops, |
270 | }, | 272 | }, |
271 | 273 | ||
272 | /* board_20619 */ | 274 | [board_20619] = |
273 | { | 275 | { |
274 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SLAVE_POSS | | 276 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SLAVE_POSS | |
275 | PDC_FLAG_4_PORTS, | 277 | PDC_FLAG_4_PORTS, |
@@ -279,7 +281,7 @@ static const struct ata_port_info pdc_port_info[] = { | |||
279 | .port_ops = &pdc_pata_ops, | 281 | .port_ops = &pdc_pata_ops, |
280 | }, | 282 | }, |
281 | 283 | ||
282 | /* board_2057x */ | 284 | [board_2057x] = |
283 | { | 285 | { |
284 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SATA | | 286 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SATA | |
285 | PDC_FLAG_GEN_II | PDC_FLAG_SATA_PATA, | 287 | PDC_FLAG_GEN_II | PDC_FLAG_SATA_PATA, |
@@ -289,7 +291,7 @@ static const struct ata_port_info pdc_port_info[] = { | |||
289 | .port_ops = &pdc_sata_ops, | 291 | .port_ops = &pdc_sata_ops, |
290 | }, | 292 | }, |
291 | 293 | ||
292 | /* board_2057x_pata */ | 294 | [board_2057x_pata] = |
293 | { | 295 | { |
294 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SLAVE_POSS | | 296 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SLAVE_POSS | |
295 | PDC_FLAG_GEN_II, | 297 | PDC_FLAG_GEN_II, |
@@ -299,7 +301,7 @@ static const struct ata_port_info pdc_port_info[] = { | |||
299 | .port_ops = &pdc_pata_ops, | 301 | .port_ops = &pdc_pata_ops, |
300 | }, | 302 | }, |
301 | 303 | ||
302 | /* board_40518 */ | 304 | [board_40518] = |
303 | { | 305 | { |
304 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SATA | | 306 | .flags = PDC_COMMON_FLAGS | ATA_FLAG_SATA | |
305 | PDC_FLAG_GEN_II | PDC_FLAG_4_PORTS, | 307 | PDC_FLAG_GEN_II | PDC_FLAG_4_PORTS, |
@@ -523,6 +525,84 @@ static void pdc_atapi_pkt(struct ata_queued_cmd *qc) | |||
523 | memcpy(buf+31, cdb, cdb_len); | 525 | memcpy(buf+31, cdb, cdb_len); |
524 | } | 526 | } |
525 | 527 | ||
528 | /** | ||
529 | * pdc_fill_sg - Fill PCI IDE PRD table | ||
530 | * @qc: Metadata associated with taskfile to be transferred | ||
531 | * | ||
532 | * Fill PCI IDE PRD (scatter-gather) table with segments | ||
533 | * associated with the current disk command. | ||
534 | * Make sure hardware does not choke on it. | ||
535 | * | ||
536 | * LOCKING: | ||
537 | * spin_lock_irqsave(host lock) | ||
538 | * | ||
539 | */ | ||
540 | static void pdc_fill_sg(struct ata_queued_cmd *qc) | ||
541 | { | ||
542 | struct ata_port *ap = qc->ap; | ||
543 | struct scatterlist *sg; | ||
544 | unsigned int idx; | ||
545 | const u32 SG_COUNT_ASIC_BUG = 41*4; | ||
546 | |||
547 | if (!(qc->flags & ATA_QCFLAG_DMAMAP)) | ||
548 | return; | ||
549 | |||
550 | WARN_ON(qc->__sg == NULL); | ||
551 | WARN_ON(qc->n_elem == 0 && qc->pad_len == 0); | ||
552 | |||
553 | idx = 0; | ||
554 | ata_for_each_sg(sg, qc) { | ||
555 | u32 addr, offset; | ||
556 | u32 sg_len, len; | ||
557 | |||
558 | /* determine if physical DMA addr spans 64K boundary. | ||
559 | * Note h/w doesn't support 64-bit, so we unconditionally | ||
560 | * truncate dma_addr_t to u32. | ||
561 | */ | ||
562 | addr = (u32) sg_dma_address(sg); | ||
563 | sg_len = sg_dma_len(sg); | ||
564 | |||
565 | while (sg_len) { | ||
566 | offset = addr & 0xffff; | ||
567 | len = sg_len; | ||
568 | if ((offset + sg_len) > 0x10000) | ||
569 | len = 0x10000 - offset; | ||
570 | |||
571 | ap->prd[idx].addr = cpu_to_le32(addr); | ||
572 | ap->prd[idx].flags_len = cpu_to_le32(len & 0xffff); | ||
573 | VPRINTK("PRD[%u] = (0x%X, 0x%X)\n", idx, addr, len); | ||
574 | |||
575 | idx++; | ||
576 | sg_len -= len; | ||
577 | addr += len; | ||
578 | } | ||
579 | } | ||
580 | |||
581 | if (idx) { | ||
582 | u32 len = le32_to_cpu(ap->prd[idx - 1].flags_len); | ||
583 | |||
584 | if (len > SG_COUNT_ASIC_BUG) { | ||
585 | u32 addr; | ||
586 | |||
587 | VPRINTK("Splitting last PRD.\n"); | ||
588 | |||
589 | addr = le32_to_cpu(ap->prd[idx - 1].addr); | ||
590 | ap->prd[idx - 1].flags_len -= cpu_to_le32(SG_COUNT_ASIC_BUG); | ||
591 | VPRINTK("PRD[%u] = (0x%X, 0x%X)\n", idx - 1, addr, SG_COUNT_ASIC_BUG); | ||
592 | |||
593 | addr = addr + len - SG_COUNT_ASIC_BUG; | ||
594 | len = SG_COUNT_ASIC_BUG; | ||
595 | ap->prd[idx].addr = cpu_to_le32(addr); | ||
596 | ap->prd[idx].flags_len = cpu_to_le32(len); | ||
597 | VPRINTK("PRD[%u] = (0x%X, 0x%X)\n", idx, addr, len); | ||
598 | |||
599 | idx++; | ||
600 | } | ||
601 | |||
602 | ap->prd[idx - 1].flags_len |= cpu_to_le32(ATA_PRD_EOT); | ||
603 | } | ||
604 | } | ||
605 | |||
526 | static void pdc_qc_prep(struct ata_queued_cmd *qc) | 606 | static void pdc_qc_prep(struct ata_queued_cmd *qc) |
527 | { | 607 | { |
528 | struct pdc_port_priv *pp = qc->ap->private_data; | 608 | struct pdc_port_priv *pp = qc->ap->private_data; |
@@ -532,7 +612,7 @@ static void pdc_qc_prep(struct ata_queued_cmd *qc) | |||
532 | 612 | ||
533 | switch (qc->tf.protocol) { | 613 | switch (qc->tf.protocol) { |
534 | case ATA_PROT_DMA: | 614 | case ATA_PROT_DMA: |
535 | ata_qc_prep(qc); | 615 | pdc_fill_sg(qc); |
536 | /* fall through */ | 616 | /* fall through */ |
537 | 617 | ||
538 | case ATA_PROT_NODATA: | 618 | case ATA_PROT_NODATA: |
@@ -548,11 +628,11 @@ static void pdc_qc_prep(struct ata_queued_cmd *qc) | |||
548 | break; | 628 | break; |
549 | 629 | ||
550 | case ATA_PROT_ATAPI: | 630 | case ATA_PROT_ATAPI: |
551 | ata_qc_prep(qc); | 631 | pdc_fill_sg(qc); |
552 | break; | 632 | break; |
553 | 633 | ||
554 | case ATA_PROT_ATAPI_DMA: | 634 | case ATA_PROT_ATAPI_DMA: |
555 | ata_qc_prep(qc); | 635 | pdc_fill_sg(qc); |
556 | /*FALLTHROUGH*/ | 636 | /*FALLTHROUGH*/ |
557 | case ATA_PROT_ATAPI_NODATA: | 637 | case ATA_PROT_ATAPI_NODATA: |
558 | pdc_atapi_pkt(qc); | 638 | pdc_atapi_pkt(qc); |
diff --git a/drivers/ata/sata_sil24.c b/drivers/ata/sata_sil24.c index 3c481e0e0c03..187dcb02c681 100644 --- a/drivers/ata/sata_sil24.c +++ b/drivers/ata/sata_sil24.c | |||
@@ -265,11 +265,11 @@ static struct sil24_cerr_info { | |||
265 | unsigned int err_mask, action; | 265 | unsigned int err_mask, action; |
266 | const char *desc; | 266 | const char *desc; |
267 | } sil24_cerr_db[] = { | 267 | } sil24_cerr_db[] = { |
268 | [0] = { AC_ERR_DEV, ATA_EH_REVALIDATE, | 268 | [0] = { AC_ERR_DEV, 0, |
269 | "device error" }, | 269 | "device error" }, |
270 | [PORT_CERR_DEV] = { AC_ERR_DEV, ATA_EH_REVALIDATE, | 270 | [PORT_CERR_DEV] = { AC_ERR_DEV, 0, |
271 | "device error via D2H FIS" }, | 271 | "device error via D2H FIS" }, |
272 | [PORT_CERR_SDB] = { AC_ERR_DEV, ATA_EH_REVALIDATE, | 272 | [PORT_CERR_SDB] = { AC_ERR_DEV, 0, |
273 | "device error via SDB FIS" }, | 273 | "device error via SDB FIS" }, |
274 | [PORT_CERR_DATA] = { AC_ERR_ATA_BUS, ATA_EH_SOFTRESET, | 274 | [PORT_CERR_DATA] = { AC_ERR_ATA_BUS, ATA_EH_SOFTRESET, |
275 | "error in data FIS" }, | 275 | "error in data FIS" }, |
diff --git a/include/linux/libata.h b/include/linux/libata.h index 147ccc40c8af..1e277852ba42 100644 --- a/include/linux/libata.h +++ b/include/linux/libata.h | |||
@@ -221,6 +221,7 @@ enum { | |||
221 | ATA_QCFLAG_IO = (1 << 3), /* standard IO command */ | 221 | ATA_QCFLAG_IO = (1 << 3), /* standard IO command */ |
222 | ATA_QCFLAG_RESULT_TF = (1 << 4), /* result TF requested */ | 222 | ATA_QCFLAG_RESULT_TF = (1 << 4), /* result TF requested */ |
223 | ATA_QCFLAG_CLEAR_EXCL = (1 << 5), /* clear excl_link on completion */ | 223 | ATA_QCFLAG_CLEAR_EXCL = (1 << 5), /* clear excl_link on completion */ |
224 | ATA_QCFLAG_QUIET = (1 << 6), /* don't report device error */ | ||
224 | 225 | ||
225 | ATA_QCFLAG_FAILED = (1 << 16), /* cmd failed and is owned by EH */ | 226 | ATA_QCFLAG_FAILED = (1 << 16), /* cmd failed and is owned by EH */ |
226 | ATA_QCFLAG_SENSE_VALID = (1 << 17), /* sense data valid */ | 227 | ATA_QCFLAG_SENSE_VALID = (1 << 17), /* sense data valid */ |