提交 b4eea67a 编写于 作者: L Linus Torvalds

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:
  ahci: sis can't do PMP
  ata_piix: add TECRA M4 to broken suspend list
  LIBATA: Add HAVE_PATA_PLATFORM to select PATA_PLATFORM driver
  sata_mv: warn on PIO with multiple DRQs
  sata_mv: enable async_notify for 60x1 Rev.C0 and higher
  libata: don't check whether to use DMA or not for no data commands
  ahci: jmb361 has only one port
...@@ -651,9 +651,17 @@ config PATA_WINBOND_VLB ...@@ -651,9 +651,17 @@ config PATA_WINBOND_VLB
Support for the Winbond W83759A controller on Vesa Local Bus Support for the Winbond W83759A controller on Vesa Local Bus
systems. systems.
config HAVE_PATA_PLATFORM
bool
help
This is an internal configuration node for any machine that
uses pata-platform driver to enable the relevant driver in the
configuration structure without having to submit endless patches
to update the PATA_PLATFORM entry.
config PATA_PLATFORM config PATA_PLATFORM
tristate "Generic platform device PATA support" tristate "Generic platform device PATA support"
depends on EMBEDDED || ARCH_RPC || PPC depends on EMBEDDED || ARCH_RPC || PPC || HAVE_PATA_PLATFORM
help help
This option enables support for generic directly connected ATA This option enables support for generic directly connected ATA
devices commonly found on embedded systems. devices commonly found on embedded systems.
......
...@@ -90,6 +90,7 @@ enum { ...@@ -90,6 +90,7 @@ enum {
board_ahci_mv = 4, board_ahci_mv = 4,
board_ahci_sb700 = 5, board_ahci_sb700 = 5,
board_ahci_mcp65 = 6, board_ahci_mcp65 = 6,
board_ahci_nopmp = 7,
/* global controller registers */ /* global controller registers */
HOST_CAP = 0x00, /* host capabilities */ HOST_CAP = 0x00, /* host capabilities */
...@@ -401,6 +402,14 @@ static const struct ata_port_info ahci_port_info[] = { ...@@ -401,6 +402,14 @@ static const struct ata_port_info ahci_port_info[] = {
.udma_mask = ATA_UDMA6, .udma_mask = ATA_UDMA6,
.port_ops = &ahci_ops, .port_ops = &ahci_ops,
}, },
/* board_ahci_nopmp */
{
AHCI_HFLAGS (AHCI_HFLAG_NO_PMP),
.flags = AHCI_FLAG_COMMON,
.pio_mask = 0x1f, /* pio0-4 */
.udma_mask = ATA_UDMA6,
.port_ops = &ahci_ops,
},
}; };
static const struct pci_device_id ahci_pci_tbl[] = { static const struct pci_device_id ahci_pci_tbl[] = {
...@@ -525,9 +534,9 @@ static const struct pci_device_id ahci_pci_tbl[] = { ...@@ -525,9 +534,9 @@ static const struct pci_device_id ahci_pci_tbl[] = {
{ PCI_VDEVICE(NVIDIA, 0x0bc7), board_ahci }, /* MCP7B */ { PCI_VDEVICE(NVIDIA, 0x0bc7), board_ahci }, /* MCP7B */
/* SiS */ /* SiS */
{ PCI_VDEVICE(SI, 0x1184), board_ahci }, /* SiS 966 */ { PCI_VDEVICE(SI, 0x1184), board_ahci_nopmp }, /* SiS 966 */
{ PCI_VDEVICE(SI, 0x1185), board_ahci }, /* SiS 966 */ { PCI_VDEVICE(SI, 0x1185), board_ahci_nopmp }, /* SiS 968 */
{ PCI_VDEVICE(SI, 0x0186), board_ahci }, /* SiS 968 */ { PCI_VDEVICE(SI, 0x0186), board_ahci_nopmp }, /* SiS 968 */
/* Marvell */ /* Marvell */
{ PCI_VDEVICE(MARVELL, 0x6145), board_ahci_mv }, /* 6145 */ { PCI_VDEVICE(MARVELL, 0x6145), board_ahci_mv }, /* 6145 */
...@@ -653,6 +662,14 @@ static void ahci_save_initial_config(struct pci_dev *pdev, ...@@ -653,6 +662,14 @@ static void ahci_save_initial_config(struct pci_dev *pdev,
cap &= ~HOST_CAP_PMP; cap &= ~HOST_CAP_PMP;
} }
if (pdev->vendor == PCI_VENDOR_ID_JMICRON && pdev->device == 0x2361 &&
port_map != 1) {
dev_printk(KERN_INFO, &pdev->dev,
"JMB361 has only one port, port_map 0x%x -> 0x%x\n",
port_map, 1);
port_map = 1;
}
/* /*
* Temporary Marvell 6145 hack: PATA port presence * Temporary Marvell 6145 hack: PATA port presence
* is asserted through the standard AHCI port * is asserted through the standard AHCI port
......
...@@ -1042,6 +1042,13 @@ static int piix_broken_suspend(void) ...@@ -1042,6 +1042,13 @@ static int piix_broken_suspend(void)
DMI_MATCH(DMI_PRODUCT_NAME, "Tecra M4"), DMI_MATCH(DMI_PRODUCT_NAME, "Tecra M4"),
}, },
}, },
{
.ident = "TECRA M4",
.matches = {
DMI_MATCH(DMI_SYS_VENDOR, "TOSHIBA"),
DMI_MATCH(DMI_PRODUCT_NAME, "TECRA M4"),
},
},
{ {
.ident = "TECRA M5", .ident = "TECRA M5",
.matches = { .matches = {
......
...@@ -4297,7 +4297,7 @@ void ata_sg_clean(struct ata_queued_cmd *qc) ...@@ -4297,7 +4297,7 @@ void ata_sg_clean(struct ata_queued_cmd *qc)
} }
/** /**
* ata_check_atapi_dma - Check whether ATAPI DMA can be supported * atapi_check_dma - Check whether ATAPI DMA can be supported
* @qc: Metadata associated with taskfile to check * @qc: Metadata associated with taskfile to check
* *
* Allow low-level driver to filter ATA PACKET commands, returning * Allow low-level driver to filter ATA PACKET commands, returning
...@@ -4310,7 +4310,7 @@ void ata_sg_clean(struct ata_queued_cmd *qc) ...@@ -4310,7 +4310,7 @@ void ata_sg_clean(struct ata_queued_cmd *qc)
* RETURNS: 0 when ATAPI DMA can be used * RETURNS: 0 when ATAPI DMA can be used
* nonzero otherwise * nonzero otherwise
*/ */
int ata_check_atapi_dma(struct ata_queued_cmd *qc) int atapi_check_dma(struct ata_queued_cmd *qc)
{ {
struct ata_port *ap = qc->ap; struct ata_port *ap = qc->ap;
......
...@@ -2343,8 +2343,8 @@ static unsigned int atapi_xlat(struct ata_queued_cmd *qc) ...@@ -2343,8 +2343,8 @@ static unsigned int atapi_xlat(struct ata_queued_cmd *qc)
{ {
struct scsi_cmnd *scmd = qc->scsicmd; struct scsi_cmnd *scmd = qc->scsicmd;
struct ata_device *dev = qc->dev; struct ata_device *dev = qc->dev;
int using_pio = (dev->flags & ATA_DFLAG_PIO);
int nodata = (scmd->sc_data_direction == DMA_NONE); int nodata = (scmd->sc_data_direction == DMA_NONE);
int using_pio = !nodata && (dev->flags & ATA_DFLAG_PIO);
unsigned int nbytes; unsigned int nbytes;
memset(qc->cdb, 0, dev->cdb_len); memset(qc->cdb, 0, dev->cdb_len);
...@@ -2362,7 +2362,7 @@ static unsigned int atapi_xlat(struct ata_queued_cmd *qc) ...@@ -2362,7 +2362,7 @@ static unsigned int atapi_xlat(struct ata_queued_cmd *qc)
ata_qc_set_pc_nbytes(qc); ata_qc_set_pc_nbytes(qc);
/* check whether ATAPI DMA is safe */ /* check whether ATAPI DMA is safe */
if (!using_pio && ata_check_atapi_dma(qc)) if (!nodata && !using_pio && atapi_check_dma(qc))
using_pio = 1; using_pio = 1;
/* Some controller variants snoop this value for Packet /* Some controller variants snoop this value for Packet
...@@ -2402,13 +2402,11 @@ static unsigned int atapi_xlat(struct ata_queued_cmd *qc) ...@@ -2402,13 +2402,11 @@ static unsigned int atapi_xlat(struct ata_queued_cmd *qc)
qc->tf.lbam = (nbytes & 0xFF); qc->tf.lbam = (nbytes & 0xFF);
qc->tf.lbah = (nbytes >> 8); qc->tf.lbah = (nbytes >> 8);
if (using_pio || nodata) { if (nodata)
/* no data, or PIO data xfer */ qc->tf.protocol = ATAPI_PROT_NODATA;
if (nodata) else if (using_pio)
qc->tf.protocol = ATAPI_PROT_NODATA; qc->tf.protocol = ATAPI_PROT_PIO;
else else {
qc->tf.protocol = ATAPI_PROT_PIO;
} else {
/* DMA data xfer */ /* DMA data xfer */
qc->tf.protocol = ATAPI_PROT_DMA; qc->tf.protocol = ATAPI_PROT_DMA;
qc->tf.feature |= ATAPI_PKT_DMA; qc->tf.feature |= ATAPI_PKT_DMA;
......
...@@ -106,7 +106,7 @@ extern void ata_sg_clean(struct ata_queued_cmd *qc); ...@@ -106,7 +106,7 @@ extern void ata_sg_clean(struct ata_queued_cmd *qc);
extern void ata_qc_free(struct ata_queued_cmd *qc); extern void ata_qc_free(struct ata_queued_cmd *qc);
extern void ata_qc_issue(struct ata_queued_cmd *qc); extern void ata_qc_issue(struct ata_queued_cmd *qc);
extern void __ata_qc_complete(struct ata_queued_cmd *qc); extern void __ata_qc_complete(struct ata_queued_cmd *qc);
extern int ata_check_atapi_dma(struct ata_queued_cmd *qc); extern int atapi_check_dma(struct ata_queued_cmd *qc);
extern void swap_buf_le16(u16 *buf, unsigned int buf_words); extern void swap_buf_le16(u16 *buf, unsigned int buf_words);
extern void ata_dev_init(struct ata_device *dev); extern void ata_dev_init(struct ata_device *dev);
extern void ata_link_init(struct ata_port *ap, struct ata_link *link, int pmp); extern void ata_link_init(struct ata_port *ap, struct ata_link *link, int pmp);
......
...@@ -1322,6 +1322,9 @@ static int mv_port_start(struct ata_port *ap) ...@@ -1322,6 +1322,9 @@ static int mv_port_start(struct ata_port *ap)
goto out_port_free_dma_mem; goto out_port_free_dma_mem;
memset(pp->crpb, 0, MV_CRPB_Q_SZ); memset(pp->crpb, 0, MV_CRPB_Q_SZ);
/* 6041/6081 Rev. "C0" (and newer) are okay with async notify */
if (hpriv->hp_flags & MV_HP_ERRATA_60X1C0)
ap->flags |= ATA_FLAG_AN;
/* /*
* For GEN_I, there's no NCQ, so we only allocate a single sg_tbl. * For GEN_I, there's no NCQ, so we only allocate a single sg_tbl.
* For later hardware, we need one unique sg_tbl per NCQ tag. * For later hardware, we need one unique sg_tbl per NCQ tag.
...@@ -1592,6 +1595,24 @@ static unsigned int mv_qc_issue(struct ata_queued_cmd *qc) ...@@ -1592,6 +1595,24 @@ static unsigned int mv_qc_issue(struct ata_queued_cmd *qc)
if ((qc->tf.protocol != ATA_PROT_DMA) && if ((qc->tf.protocol != ATA_PROT_DMA) &&
(qc->tf.protocol != ATA_PROT_NCQ)) { (qc->tf.protocol != ATA_PROT_NCQ)) {
static int limit_warnings = 10;
/*
* Errata SATA#16, SATA#24: warn if multiple DRQs expected.
*
* Someday, we might implement special polling workarounds
* for these, but it all seems rather unnecessary since we
* normally use only DMA for commands which transfer more
* than a single block of data.
*
* Much of the time, this could just work regardless.
* So for now, just log the incident, and allow the attempt.
*/
if (limit_warnings && (qc->nbytes / qc->sect_size) > 1) {
--limit_warnings;
ata_link_printk(qc->dev->link, KERN_WARNING, DRV_NAME
": attempting PIO w/multiple DRQ: "
"this may fail due to h/w errata\n");
}
/* /*
* We're about to send a non-EDMA capable command to the * We're about to send a non-EDMA capable command to the
* port. Turn off EDMA so there won't be problems accessing * port. Turn off EDMA so there won't be problems accessing
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册