Skip to content

Commit aca7c37

Browse files
committed
Merge tag 'ata-6.10-rc6' of git://git.kernel.org/pub/scm/linux/kernel/git/libata/linux
Pull ata fixes from Niklas Cassel: - Add NOLPM quirk for for all Crucial BX SSD1 models. Considering that we now have had bug reports for 3 different BX SSD1 variants from Crucial with the same product name, make the quirk more inclusive, to catch more device models from the same generation. - Fix a trivial NULL pointer dereference in the error path for ata_host_release(). - Create a ata_port_free(), so that we don't miss freeing ata_port struct members when freeing a struct ata_port. - Fix a trivial double free in the error path for ata_host_alloc(). - Ensure that we remove the libata "remapped NVMe device count" sysfs entry on .probe() error. * tag 'ata-6.10-rc6' of git://git.kernel.org/pub/scm/linux/kernel/git/libata/linux: ata: ahci: Clean up sysfs file on error ata: libata-core: Fix double free on error ata,scsi: libata-core: Do not leak memory for ata_port struct members ata: libata-core: Fix null pointer dereference on error ata: libata-core: Add ATA_HORKAGE_NOLPM for all Crucial BX SSD1 models
2 parents e0b668b + eeb25a0 commit aca7c37

File tree

5 files changed

+36
-22
lines changed

5 files changed

+36
-22
lines changed

drivers/ata/ahci.c

Lines changed: 12 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1975,8 +1975,10 @@ static int ahci_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
19751975
n_ports = max(ahci_nr_ports(hpriv->cap), fls(hpriv->port_map));
19761976

19771977
host = ata_host_alloc_pinfo(&pdev->dev, ppi, n_ports);
1978-
if (!host)
1979-
return -ENOMEM;
1978+
if (!host) {
1979+
rc = -ENOMEM;
1980+
goto err_rm_sysfs_file;
1981+
}
19801982
host->private_data = hpriv;
19811983

19821984
if (ahci_init_msi(pdev, n_ports, hpriv) < 0) {
@@ -2031,11 +2033,11 @@ static int ahci_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
20312033
/* initialize adapter */
20322034
rc = ahci_configure_dma_masks(pdev, hpriv);
20332035
if (rc)
2034-
return rc;
2036+
goto err_rm_sysfs_file;
20352037

20362038
rc = ahci_pci_reset_controller(host);
20372039
if (rc)
2038-
return rc;
2040+
goto err_rm_sysfs_file;
20392041

20402042
ahci_pci_init_controller(host);
20412043
ahci_pci_print_info(host);
@@ -2044,10 +2046,15 @@ static int ahci_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
20442046

20452047
rc = ahci_host_activate(host, &ahci_sht);
20462048
if (rc)
2047-
return rc;
2049+
goto err_rm_sysfs_file;
20482050

20492051
pm_runtime_put_noidle(&pdev->dev);
20502052
return 0;
2053+
2054+
err_rm_sysfs_file:
2055+
sysfs_remove_file_from_group(&pdev->dev.kobj,
2056+
&dev_attr_remapped_nvme.attr, NULL);
2057+
return rc;
20512058
}
20522059

20532060
static void ahci_shutdown_one(struct pci_dev *pdev)

drivers/ata/libata-core.c

Lines changed: 19 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -4137,8 +4137,7 @@ static const struct ata_blacklist_entry ata_device_blacklist [] = {
41374137
{ "PIONEER BD-RW BDR-205", NULL, ATA_HORKAGE_NOLPM },
41384138

41394139
/* Crucial devices with broken LPM support */
4140-
{ "CT500BX100SSD1", NULL, ATA_HORKAGE_NOLPM },
4141-
{ "CT240BX500SSD1", NULL, ATA_HORKAGE_NOLPM },
4140+
{ "CT*0BX*00SSD1", NULL, ATA_HORKAGE_NOLPM },
41424141

41434142
/* 512GB MX100 with MU01 firmware has both queued TRIM and LPM issues */
41444143
{ "Crucial_CT512MX100*", "MU01", ATA_HORKAGE_NO_NCQ_TRIM |
@@ -5490,6 +5489,18 @@ struct ata_port *ata_port_alloc(struct ata_host *host)
54905489
return ap;
54915490
}
54925491

5492+
void ata_port_free(struct ata_port *ap)
5493+
{
5494+
if (!ap)
5495+
return;
5496+
5497+
kfree(ap->pmp_link);
5498+
kfree(ap->slave_link);
5499+
kfree(ap->ncq_sense_buf);
5500+
kfree(ap);
5501+
}
5502+
EXPORT_SYMBOL_GPL(ata_port_free);
5503+
54935504
static void ata_devres_release(struct device *gendev, void *res)
54945505
{
54955506
struct ata_host *host = dev_get_drvdata(gendev);
@@ -5516,12 +5527,7 @@ static void ata_host_release(struct kref *kref)
55165527
int i;
55175528

55185529
for (i = 0; i < host->n_ports; i++) {
5519-
struct ata_port *ap = host->ports[i];
5520-
5521-
kfree(ap->pmp_link);
5522-
kfree(ap->slave_link);
5523-
kfree(ap->ncq_sense_buf);
5524-
kfree(ap);
5530+
ata_port_free(host->ports[i]);
55255531
host->ports[i] = NULL;
55265532
}
55275533
kfree(host);
@@ -5571,8 +5577,10 @@ struct ata_host *ata_host_alloc(struct device *dev, int max_ports)
55715577
if (!host)
55725578
return NULL;
55735579

5574-
if (!devres_open_group(dev, NULL, GFP_KERNEL))
5575-
goto err_free;
5580+
if (!devres_open_group(dev, NULL, GFP_KERNEL)) {
5581+
kfree(host);
5582+
return NULL;
5583+
}
55765584

55775585
dr = devres_alloc(ata_devres_release, 0, GFP_KERNEL);
55785586
if (!dr)
@@ -5604,8 +5612,6 @@ struct ata_host *ata_host_alloc(struct device *dev, int max_ports)
56045612

56055613
err_out:
56065614
devres_release_group(dev, NULL);
5607-
err_free:
5608-
kfree(host);
56095615
return NULL;
56105616
}
56115617
EXPORT_SYMBOL_GPL(ata_host_alloc);
@@ -5904,7 +5910,7 @@ int ata_host_register(struct ata_host *host, const struct scsi_host_template *sh
59045910
* allocation time.
59055911
*/
59065912
for (i = host->n_ports; host->ports[i]; i++)
5907-
kfree(host->ports[i]);
5913+
ata_port_free(host->ports[i]);
59085914

59095915
/* give ports names and add SCSI hosts */
59105916
for (i = 0; i < host->n_ports; i++) {

drivers/scsi/libsas/sas_ata.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -610,15 +610,15 @@ int sas_ata_init(struct domain_device *found_dev)
610610

611611
rc = ata_sas_tport_add(ata_host->dev, ap);
612612
if (rc)
613-
goto destroy_port;
613+
goto free_port;
614614

615615
found_dev->sata_dev.ata_host = ata_host;
616616
found_dev->sata_dev.ap = ap;
617617

618618
return 0;
619619

620-
destroy_port:
621-
kfree(ap);
620+
free_port:
621+
ata_port_free(ap);
622622
free_host:
623623
ata_host_put(ata_host);
624624
return rc;

drivers/scsi/libsas/sas_discover.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -301,7 +301,7 @@ void sas_free_device(struct kref *kref)
301301

302302
if (dev_is_sata(dev) && dev->sata_dev.ap) {
303303
ata_sas_tport_delete(dev->sata_dev.ap);
304-
kfree(dev->sata_dev.ap);
304+
ata_port_free(dev->sata_dev.ap);
305305
ata_host_put(dev->sata_dev.ata_host);
306306
dev->sata_dev.ata_host = NULL;
307307
dev->sata_dev.ap = NULL;

include/linux/libata.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1249,6 +1249,7 @@ extern int ata_slave_link_init(struct ata_port *ap);
12491249
extern struct ata_port *ata_sas_port_alloc(struct ata_host *,
12501250
struct ata_port_info *, struct Scsi_Host *);
12511251
extern void ata_port_probe(struct ata_port *ap);
1252+
extern void ata_port_free(struct ata_port *ap);
12521253
extern int ata_sas_tport_add(struct device *parent, struct ata_port *ap);
12531254
extern void ata_sas_tport_delete(struct ata_port *ap);
12541255
int ata_sas_device_configure(struct scsi_device *sdev, struct queue_limits *lim,

0 commit comments

Comments
 (0)