From b2d01681ab2d7dd1735fefaacf0cbcb7d4e4f32a Mon Sep 17 00:00:00 2001 From: Bin Meng Date: Wed, 11 Oct 2023 21:15:44 +0800 Subject: ufs: Correct the UFS terminlogy UFS stands for Universal Flash Storage, not Subsytem. Signed-off-by: Bin Meng Reviewed-by: Simon Glass Reviewed-by: Neha Malcom Francis --- drivers/ufs/ufs-uclass.c | 2 +- drivers/ufs/ufs.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers') diff --git a/drivers/ufs/ufs-uclass.c b/drivers/ufs/ufs-uclass.c index ceea30c4a95..ffae811d462 100644 --- a/drivers/ufs/ufs-uclass.c +++ b/drivers/ufs/ufs-uclass.c @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0 /** - * ufs-uclass.c - Universal Flash Subsystem (UFS) Uclass driver + * ufs-uclass.c - Universal Flash Storage (UFS) Uclass driver * * Copyright (C) 2019 Texas Instruments Incorporated - http://www.ti.com */ diff --git a/drivers/ufs/ufs.c b/drivers/ufs/ufs.c index 7c48d57f99d..f534d6e29f7 100644 --- a/drivers/ufs/ufs.c +++ b/drivers/ufs/ufs.c @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0+ /** - * ufs.c - Universal Flash Subsystem (UFS) driver + * ufs.c - Universal Flash Storage (UFS) driver * * Taken from Linux Kernel v5.2 (drivers/scsi/ufs/ufshcd.c) and ported * to u-boot. -- cgit v1.3.1 From 1b3dab2d296c4ae8ccdd85986c26a77036c81d85 Mon Sep 17 00:00:00 2001 From: Bin Meng Date: Wed, 11 Oct 2023 21:15:45 +0800 Subject: ufs: Add a line feed to the end of some dev_xxx() messages Add a line feed to improve readability of some dev_xxx() messages. Signed-off-by: Bin Meng Reviewed-by: Neha Malcom Francis Reviewed-by: Simon Glass --- drivers/ufs/ufs.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) (limited to 'drivers') diff --git a/drivers/ufs/ufs.c b/drivers/ufs/ufs.c index f534d6e29f7..96801866d33 100644 --- a/drivers/ufs/ufs.c +++ b/drivers/ufs/ufs.c @@ -320,7 +320,7 @@ static int ufshcd_disable_tx_lcc(struct ufs_hba *hba, bool peer) UIC_ARG_MPHY_TX_GEN_SEL_INDEX(i)), 0); if (err) { - dev_err(hba->dev, "%s: TX LCC Disable failed, peer = %d, lane = %d, err = %d", + dev_err(hba->dev, "%s: TX LCC Disable failed, peer = %d, lane = %d, err = %d\n", __func__, peer, i, err); break; } @@ -441,7 +441,7 @@ static int ufshcd_make_hba_operational(struct ufs_hba *hba) ufshcd_enable_run_stop_reg(hba); } else { dev_err(hba->dev, - "Host controller not ready to process requests"); + "Host controller not ready to process requests\n"); err = -EIO; goto out; } @@ -930,7 +930,7 @@ static int ufshcd_copy_query_response(struct ufs_hba *hba) memcpy(hba->dev_cmd.query.descriptor, descp, resp_len); } else { dev_warn(hba->dev, - "%s: Response size is bigger than buffer", + "%s: Response size is bigger than buffer\n", __func__); return -EINVAL; } @@ -1179,11 +1179,11 @@ static int ufshcd_read_desc_length(struct ufs_hba *hba, enum desc_idn desc_id, &header_len); if (ret) { - dev_err(hba->dev, "%s: Failed to get descriptor header id %d", + dev_err(hba->dev, "%s: Failed to get descriptor header id %d\n", __func__, desc_id); return ret; } else if (desc_id != header[QUERY_DESC_DESC_TYPE_OFFSET]) { - dev_warn(hba->dev, "%s: descriptor header id %d and desc_id %d mismatch", + dev_warn(hba->dev, "%s: descriptor header id %d and desc_id %d mismatch\n", __func__, header[QUERY_DESC_DESC_TYPE_OFFSET], desc_id); ret = -EINVAL; @@ -1302,7 +1302,7 @@ int ufshcd_read_desc_param(struct ufs_hba *hba, enum desc_idn desc_id, /* Sanity checks */ if (ret || !buff_len) { - dev_err(hba->dev, "%s: Failed to get full descriptor length", + dev_err(hba->dev, "%s: Failed to get full descriptor length\n", __func__); return ret; } @@ -1323,14 +1323,14 @@ int ufshcd_read_desc_param(struct ufs_hba *hba, enum desc_idn desc_id, &buff_len); if (ret) { - dev_err(hba->dev, "%s: Failed reading descriptor. desc_id %d, desc_index %d, param_offset %d, ret %d", + dev_err(hba->dev, "%s: Failed reading descriptor. desc_id %d, desc_index %d, param_offset %d, ret %d\n", __func__, desc_id, desc_index, param_offset, ret); goto out; } /* Sanity check */ if (desc_buf[QUERY_DESC_DESC_TYPE_OFFSET] != desc_id) { - dev_err(hba->dev, "%s: invalid desc_id %d in descriptor header", + dev_err(hba->dev, "%s: invalid desc_id %d in descriptor header\n", __func__, desc_buf[QUERY_DESC_DESC_TYPE_OFFSET]); ret = -EINVAL; goto out; -- cgit v1.3.1 From e5c19ce47c7063553b26443560179307416e26f9 Mon Sep 17 00:00:00 2001 From: Bin Meng Date: Wed, 11 Oct 2023 21:15:49 +0800 Subject: ufs: Allow mmio registers on the PCI bus Check if the UFS controller is on the PCI bus, and get its register base address accordingly. Signed-off-by: Bin Meng Reviewed-by: Simon Glass Reviewed-by: Neha Malcom Francis --- drivers/ufs/ufs.c | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) (limited to 'drivers') diff --git a/drivers/ufs/ufs.c b/drivers/ufs/ufs.c index 96801866d33..fb2a607ef11 100644 --- a/drivers/ufs/ufs.c +++ b/drivers/ufs/ufs.c @@ -1914,6 +1914,7 @@ int ufshcd_probe(struct udevice *ufs_dev, struct ufs_hba_ops *hba_ops) struct ufs_hba *hba = dev_get_uclass_priv(ufs_dev); struct scsi_plat *scsi_plat; struct udevice *scsi_dev; + void __iomem *mmio_base; int err; device_find_first_child(ufs_dev, &scsi_dev); @@ -1927,7 +1928,14 @@ int ufshcd_probe(struct udevice *ufs_dev, struct ufs_hba_ops *hba_ops) hba->dev = ufs_dev; hba->ops = hba_ops; - hba->mmio_base = dev_read_addr_ptr(ufs_dev); + + if (device_is_on_pci_bus(ufs_dev)) { + mmio_base = dm_pci_map_bar(ufs_dev, PCI_BASE_ADDRESS_0, 0, 0, + PCI_REGION_TYPE, PCI_REGION_MEM); + } else { + mmio_base = dev_read_addr_ptr(ufs_dev); + } + hba->mmio_base = mmio_base; /* Set descriptor lengths to specification defaults */ ufshcd_def_desc_sizes(hba); -- cgit v1.3.1 From 2ec7d657c03dd583b4638bff6352ac3b88742c09 Mon Sep 17 00:00:00 2001 From: Bin Meng Date: Wed, 11 Oct 2023 21:15:50 +0800 Subject: ufs: Add a PCI based UFS controller driver This adds a simple PCI based UFS controller driver with a QEMU emulated UFS controller on the PCI bus. Requiring QEMU v8.2+. Signed-off-by: Bin Meng Reviewed-by: Neha Malcom Francis Reviewed-by: Simon Glass --- drivers/ufs/Kconfig | 11 +++++++++++ drivers/ufs/Makefile | 1 + drivers/ufs/ufs-pci.c | 45 +++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 57 insertions(+) create mode 100644 drivers/ufs/ufs-pci.c (limited to 'drivers') diff --git a/drivers/ufs/Kconfig b/drivers/ufs/Kconfig index 0e0cc58e3d6..42797ce0529 100644 --- a/drivers/ufs/Kconfig +++ b/drivers/ufs/Kconfig @@ -15,6 +15,17 @@ config CADENCE_UFS This selects the platform driver for the Cadence UFS host controller present on present TI's J721e devices. +config UFS_PCI + bool "PCI bus based UFS Controller support" + depends on PCI && UFS + help + This selects the PCI UFS Host Controller Interface. Select this if + you have UFS Host Controller with PCI Interface. + + If you have a controller with this interface, say Y here. + + If unsure, say N. + config TI_J721E_UFS bool "Glue Layer driver for UFS on TI J721E devices" help diff --git a/drivers/ufs/Makefile b/drivers/ufs/Makefile index 4f3344fd4e4..13f1e689ef6 100644 --- a/drivers/ufs/Makefile +++ b/drivers/ufs/Makefile @@ -6,4 +6,5 @@ obj-$(CONFIG_UFS) += ufs.o ufs-uclass.o obj-$(CONFIG_CADENCE_UFS) += cdns-platform.o obj-$(CONFIG_TI_J721E_UFS) += ti-j721e-ufs.o +obj-$(CONFIG_UFS_PCI) += ufs-pci.o obj-$(CONFIG_UFS_RENESAS) += ufs-renesas.o diff --git a/drivers/ufs/ufs-pci.c b/drivers/ufs/ufs-pci.c new file mode 100644 index 00000000000..ad41358727a --- /dev/null +++ b/drivers/ufs/ufs-pci.c @@ -0,0 +1,45 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Copyright (C) 2023 tinylab.org + * Author: Bin Meng + */ + +#include +#include +#include +#include +#include +#include +#include "ufs.h" + +static int ufs_pci_bind(struct udevice *dev) +{ + struct udevice *scsi_dev; + + return ufs_scsi_bind(dev, &scsi_dev); +} + +static int ufs_pci_probe(struct udevice *dev) +{ + int err; + + err = ufshcd_probe(dev, NULL); + if (err) + dev_err(dev, "%s failed (ret=%d)\n", __func__, err); + + return err; +} + +U_BOOT_DRIVER(ufs_pci) = { + .name = "ufs_pci", + .id = UCLASS_UFS, + .bind = ufs_pci_bind, + .probe = ufs_pci_probe, +}; + +static struct pci_device_id ufs_supported[] = { + { PCI_DEVICE(PCI_VENDOR_ID_REDHAT, PCI_DEVICE_ID_REDHAT_UFS) }, + {}, +}; + +U_BOOT_PCI_DEVICE(ufs_pci, ufs_supported); -- cgit v1.3.1 From 5b2d25a2e3c303515f6ce3b0ea7e984e1e6312da Mon Sep 17 00:00:00 2001 From: Bin Meng Date: Wed, 11 Oct 2023 21:15:51 +0800 Subject: ufs: Handle UFS 3.1 controllers Extend the version check to handle UFS 3.1 controllers as well. Tested on QEMU emulated UFS 3.1 controller. Signed-off-by: Bin Meng Reviewed-by: Neha Malcom Francis Reviewed-by: Simon Glass --- drivers/ufs/ufs.c | 3 ++- drivers/ufs/ufs.h | 1 + 2 files changed, 3 insertions(+), 1 deletion(-) (limited to 'drivers') diff --git a/drivers/ufs/ufs.c b/drivers/ufs/ufs.c index fb2a607ef11..6287ce91a3e 100644 --- a/drivers/ufs/ufs.c +++ b/drivers/ufs/ufs.c @@ -1953,7 +1953,8 @@ int ufshcd_probe(struct udevice *ufs_dev, struct ufs_hba_ops *hba_ops) hba->version != UFSHCI_VERSION_11 && hba->version != UFSHCI_VERSION_20 && hba->version != UFSHCI_VERSION_21 && - hba->version != UFSHCI_VERSION_30) + hba->version != UFSHCI_VERSION_30 && + hba->version != UFSHCI_VERSION_31) dev_err(hba->dev, "invalid UFS version 0x%x\n", hba->version); diff --git a/drivers/ufs/ufs.h b/drivers/ufs/ufs.h index 9daaf03d222..816a5ce0caf 100644 --- a/drivers/ufs/ufs.h +++ b/drivers/ufs/ufs.h @@ -782,6 +782,7 @@ enum { UFSHCI_VERSION_20 = 0x00000200, /* 2.0 */ UFSHCI_VERSION_21 = 0x00000210, /* 2.1 */ UFSHCI_VERSION_30 = 0x00000300, /* 3.0 */ + UFSHCI_VERSION_31 = 0x00000310, /* 3.1 */ }; /* Interrupt disable masks */ -- cgit v1.3.1