summaryrefslogtreecommitdiffstats
path: root/drivers/scsi/cxlflash/ocxl_hw.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/cxlflash/ocxl_hw.c')
-rw-r--r--drivers/scsi/cxlflash/ocxl_hw.c44
1 files changed, 44 insertions, 0 deletions
diff --git a/drivers/scsi/cxlflash/ocxl_hw.c b/drivers/scsi/cxlflash/ocxl_hw.c
index e3a0a9b42e8f..85c0f84f2a68 100644
--- a/drivers/scsi/cxlflash/ocxl_hw.c
+++ b/drivers/scsi/cxlflash/ocxl_hw.c
@@ -32,6 +32,38 @@ static void ocxlflash_destroy_afu(void *afu_cookie)
}
/**
+ * ocxlflash_config_fn() - configure the host function
+ * @pdev: PCI device associated with the host.
+ * @afu: AFU associated with the host.
+ *
+ * Return: 0 on success, -errno on failure
+ */
+static int ocxlflash_config_fn(struct pci_dev *pdev, struct ocxl_hw_afu *afu)
+{
+ struct ocxl_fn_config *fcfg = &afu->fcfg;
+ struct device *dev = &pdev->dev;
+ int rc = 0;
+
+ /* Read DVSEC config of the function */
+ rc = ocxl_config_read_function(pdev, fcfg);
+ if (unlikely(rc)) {
+ dev_err(dev, "%s: ocxl_config_read_function failed rc=%d\n",
+ __func__, rc);
+ goto out;
+ }
+
+ /* Check if function has AFUs defined, only 1 per function supported */
+ if (fcfg->max_afu_index >= 0) {
+ afu->is_present = true;
+ if (fcfg->max_afu_index != 0)
+ dev_warn(dev, "%s: Unexpected AFU index value %d\n",
+ __func__, fcfg->max_afu_index);
+ }
+out:
+ return rc;
+}
+
+/**
* ocxlflash_create_afu() - create the AFU for OCXL
* @pdev: PCI device associated with the host.
*
@@ -41,6 +73,7 @@ static void *ocxlflash_create_afu(struct pci_dev *pdev)
{
struct device *dev = &pdev->dev;
struct ocxl_hw_afu *afu;
+ int rc;
afu = kzalloc(sizeof(*afu), GFP_KERNEL);
if (unlikely(!afu)) {
@@ -50,8 +83,19 @@ static void *ocxlflash_create_afu(struct pci_dev *pdev)
afu->pdev = pdev;
afu->dev = dev;
+
+ rc = ocxlflash_config_fn(pdev, afu);
+ if (unlikely(rc)) {
+ dev_err(dev, "%s: Function configuration failed rc=%d\n",
+ __func__, rc);
+ goto err1;
+ }
out:
return afu;
+err1:
+ kfree(afu);
+ afu = NULL;
+ goto out;
}
/* Backend ops to ocxlflash services */