cnss2: remove deprecated IOMMU APIs
IOMMU mapping APIs have been deprecated in favor of device
tree entries. Update CNSS functions as required. Keep the
old API and structure for backward compatibility. They will
be removed once WLAN driver switch to the new APIs.
CRs-Fixed: 2409946
Change-Id: I8b50fefd0acd9e48670e350d20da7b0633e336b3
Signed-off-by: Yuanyuan Liu <yuanliu@codeaurora.org>
diff --git a/drivers/net/wireless/cnss2/pci.c b/drivers/net/wireless/cnss2/pci.c
index 9fedf65..582aae0 100644
--- a/drivers/net/wireless/cnss2/pci.c
+++ b/drivers/net/wireless/cnss2/pci.c
@@ -934,99 +934,6 @@
return 0;
}
-static int cnss_pci_init_smmu(struct cnss_pci_data *pci_priv)
-{
- int ret = 0;
- struct device *dev;
- struct dma_iommu_mapping *mapping;
- int atomic_ctx = 1, s1_bypass = 1, fast = 1, cb_stall_disable = 1,
- no_cfre = 1;
-
- cnss_pr_dbg("Initializing SMMU\n");
-
- dev = &pci_priv->pci_dev->dev;
-
- mapping = __depr_arm_iommu_create_mapping(dev->bus,
- pci_priv->smmu_iova_start,
- pci_priv->smmu_iova_len);
- if (IS_ERR(mapping)) {
- ret = PTR_ERR(mapping);
- cnss_pr_err("Failed to create SMMU mapping, err = %d\n", ret);
- goto out;
- }
-
- if (pci_priv->smmu_s1_enable) {
- cnss_pr_dbg("Enabling SMMU S1 stage\n");
-
- ret = iommu_domain_set_attr(mapping->domain,
- DOMAIN_ATTR_ATOMIC,
- &atomic_ctx);
- if (ret) {
- pr_err("Failed to set SMMU atomic_ctx attribute, err = %d\n",
- ret);
- goto release_mapping;
- }
-
- ret = iommu_domain_set_attr(mapping->domain,
- DOMAIN_ATTR_FAST,
- &fast);
- if (ret) {
- pr_err("Failed to set SMMU fast attribute, err = %d\n",
- ret);
- goto release_mapping;
- }
-
- ret = iommu_domain_set_attr(mapping->domain,
- DOMAIN_ATTR_CB_STALL_DISABLE,
- &cb_stall_disable);
- if (ret) {
- pr_err("Failed to set SMMU cb_stall_disable attribute, err = %d\n",
- ret);
- goto release_mapping;
- }
-
- ret = iommu_domain_set_attr(mapping->domain,
- DOMAIN_ATTR_NO_CFRE,
- &no_cfre);
- if (ret) {
- pr_err("Failed to set SMMU no_cfre attribute, err = %d\n",
- ret);
- goto release_mapping;
- }
- } else {
- ret = iommu_domain_set_attr(mapping->domain,
- DOMAIN_ATTR_S1_BYPASS,
- &s1_bypass);
- if (ret) {
- pr_err("Failed to set SMMU s1_bypass attribute, err = %d\n",
- ret);
- goto release_mapping;
- }
- }
-
- ret = __depr_arm_iommu_attach_device(dev, mapping);
- if (ret) {
- pr_err("Failed to attach SMMU device, err = %d\n", ret);
- goto release_mapping;
- }
-
- pci_priv->smmu_mapping = mapping;
-
- return ret;
-release_mapping:
- __depr_arm_iommu_release_mapping(mapping);
-out:
- return ret;
-}
-
-static void cnss_pci_deinit_smmu(struct cnss_pci_data *pci_priv)
-{
- __depr_arm_iommu_detach_device(&pci_priv->pci_dev->dev);
- __depr_arm_iommu_release_mapping(pci_priv->smmu_mapping);
-
- pci_priv->smmu_mapping = NULL;
-}
-
static void cnss_pci_event_cb(struct msm_pcie_notify *notify)
{
unsigned long flags;
@@ -1709,10 +1616,21 @@
if (!pci_priv)
return NULL;
- return pci_priv->smmu_mapping;
+ return &pci_priv->smmu_mapping;
}
EXPORT_SYMBOL(cnss_smmu_get_mapping);
+struct iommu_domain *cnss_smmu_get_domain(struct device *dev)
+{
+ struct cnss_pci_data *pci_priv = cnss_get_pci_priv(to_pci_dev(dev));
+
+ if (!pci_priv)
+ return NULL;
+
+ return pci_priv->iommu_domain;
+}
+EXPORT_SYMBOL(cnss_smmu_get_domain);
+
int cnss_smmu_map(struct device *dev,
phys_addr_t paddr, uint32_t *iova_addr, size_t size)
{
@@ -1742,7 +1660,7 @@
return -ENOMEM;
}
- ret = iommu_map(pci_priv->smmu_mapping->domain, iova,
+ ret = iommu_map(pci_priv->iommu_domain, iova,
rounddown(paddr, PAGE_SIZE), len,
IOMMU_READ | IOMMU_WRITE);
if (ret) {
@@ -2615,6 +2533,9 @@
struct cnss_pci_data *pci_priv;
struct cnss_plat_data *plat_priv = cnss_bus_dev_to_plat_priv(NULL);
struct resource *res;
+ struct device_node *of_node;
+ const char *iommu_dma_type;
+ u32 addr_win[2];
cnss_pr_dbg("PCI is probing, vendor ID: 0x%x, device ID: 0x%x\n",
id->vendor, pci_dev->device);
@@ -2645,16 +2566,34 @@
if (ret)
goto unregister_subsys;
- res = platform_get_resource_byname(plat_priv->plat_dev, IORESOURCE_MEM,
- "smmu_iova_base");
- if (res) {
- if (of_property_read_bool(plat_priv->plat_dev->dev.of_node,
- "qcom,smmu-s1-enable"))
- pci_priv->smmu_s1_enable = true;
+ of_node = of_parse_phandle(pci_priv->pci_dev->dev.of_node,
+ "qcom,iommu-group", 0);
+ if (of_node) {
+ pci_priv->iommu_domain =
+ iommu_get_domain_for_dev(&pci_dev->dev);
+ pci_priv->smmu_mapping.domain = pci_priv->iommu_domain;
+ ret = of_property_read_string(of_node, "qcom,iommu-dma",
+ &iommu_dma_type);
+ if (!ret) {
+ if (!strcmp("fastmap", iommu_dma_type)) {
+ cnss_pr_dbg("Enabling SMMU S1 stage\n");
+ pci_priv->smmu_s1_enable = true;
+ }
+ }
- pci_priv->smmu_iova_start = res->start;
- pci_priv->smmu_iova_len = resource_size(res);
- cnss_pr_dbg("smmu_iova_start: %pa, smmu_iova_len: %zu\n",
+ ret = of_property_read_u32_array(of_node,
+ "qcom,iommu-dma-addr-pool",
+ addr_win,
+ ARRAY_SIZE(addr_win));
+ if (ret) {
+ cnss_pr_err("Invalid smmu size window, ret %d\n", ret);
+ of_node_put(of_node);
+ goto unregister_ramdump;
+ }
+
+ pci_priv->smmu_iova_start = addr_win[0];
+ pci_priv->smmu_iova_len = addr_win[1];
+ cnss_pr_dbg("smmu_iova_start: %pa, smmu_iova_len: 0x%zx\n",
&pci_priv->smmu_iova_start,
pci_priv->smmu_iova_len);
@@ -2664,22 +2603,17 @@
if (res) {
pci_priv->smmu_iova_ipa_start = res->start;
pci_priv->smmu_iova_ipa_len = resource_size(res);
- cnss_pr_dbg("smmu_iova_ipa_start: %pa, smmu_iova_ipa_len: %zu\n",
+ cnss_pr_dbg("smmu_iova_ipa_start: %pa, smmu_iova_ipa_len: 0x%zx\n",
&pci_priv->smmu_iova_ipa_start,
pci_priv->smmu_iova_ipa_len);
}
-
- ret = cnss_pci_init_smmu(pci_priv);
- if (ret) {
- cnss_pr_err("Failed to init SMMU, err = %d\n", ret);
- goto unregister_ramdump;
- }
+ of_node_put(of_node);
}
ret = cnss_reg_pci_event(pci_priv);
if (ret) {
cnss_pr_err("Failed to register PCI event, err = %d\n", ret);
- goto deinit_smmu;
+ goto unregister_ramdump;
}
ret = cnss_pci_enable_bus(pci_priv);
@@ -2733,10 +2667,9 @@
cnss_pci_disable_bus(pci_priv);
dereg_pci_event:
cnss_dereg_pci_event(pci_priv);
-deinit_smmu:
- if (pci_priv->smmu_mapping)
- cnss_pci_deinit_smmu(pci_priv);
unregister_ramdump:
+ pci_priv->iommu_domain = NULL;
+ pci_priv->smmu_mapping.domain = NULL;
cnss_unregister_ramdump(plat_priv);
unregister_subsys:
cnss_unregister_subsys(plat_priv);
@@ -2770,8 +2703,8 @@
cnss_pci_disable_bus(pci_priv);
cnss_dereg_pci_event(pci_priv);
- if (pci_priv->smmu_mapping)
- cnss_pci_deinit_smmu(pci_priv);
+ pci_priv->iommu_domain = NULL;
+ pci_priv->smmu_mapping.domain = NULL;
cnss_unregister_ramdump(plat_priv);
cnss_unregister_subsys(plat_priv);
plat_priv->bus_priv = NULL;
diff --git a/drivers/net/wireless/cnss2/pci.h b/drivers/net/wireless/cnss2/pci.h
index 87e0c1b..43e42d1 100644
--- a/drivers/net/wireless/cnss2/pci.h
+++ b/drivers/net/wireless/cnss2/pci.h
@@ -56,7 +56,8 @@
struct msm_pcie_register_event msm_pci_event;
atomic_t auto_suspended;
u8 monitor_wake_intr;
- struct dma_iommu_mapping *smmu_mapping;
+ struct dma_iommu_mapping smmu_mapping;
+ struct iommu_domain *iommu_domain;
u8 smmu_s1_enable;
dma_addr_t smmu_iova_start;
size_t smmu_iova_len;
diff --git a/include/net/cnss2.h b/include/net/cnss2.h
index 93cb55d..922e661 100644
--- a/include/net/cnss2.h
+++ b/include/net/cnss2.h
@@ -160,6 +160,7 @@
extern int cnss_get_platform_cap(struct device *dev,
struct cnss_platform_cap *cap);
extern struct dma_iommu_mapping *cnss_smmu_get_mapping(struct device *dev);
+extern struct iommu_domain *cnss_smmu_get_domain(struct device *dev);
extern int cnss_smmu_map(struct device *dev,
phys_addr_t paddr, uint32_t *iova_addr, size_t size);
extern int cnss_get_soc_info(struct device *dev, struct cnss_soc_info *info);