Merge tag 'rproc-v6.9' of git://git.kernel.org/pub/scm/linux/kernel/git/remoteproc...
authorLinus Torvalds <torvalds@linux-foundation.org>
Thu, 21 Mar 2024 17:37:39 +0000 (10:37 -0700)
committerLinus Torvalds <torvalds@linux-foundation.org>
Thu, 21 Mar 2024 17:37:39 +0000 (10:37 -0700)
Pull remoteproc updates from Bjorn Andersson:
 "Qualcomm SM8650 audio, compute and modem remoteproc are added.
  Qualcomm X1 Elite audio and compute remoteprocs are added, after
  support for shutting down the bootloader-loaded firmware loaded into
  the audio DSP..

  A dozen drivers in the subsystem are transitioned to use devres
  helpers for remoteproc and memory allocations - this makes it possible
  to acquire in-kernel handle to individual remoteproc instances in a
  cluster.

  The release of DMA memory for remoteproc virtio is corrected to ensure
  that restarting due to a watchdog bite doesn't attempt to allocate the
  memory again without first freeing it.

  Last, but not least, a couple of DeviceTree binding cleanups"

* tag 'rproc-v6.9' of git://git.kernel.org/pub/scm/linux/kernel/git/remoteproc/linux: (30 commits)
  remoteproc: qcom_q6v5_pas: Unload lite firmware on ADSP
  remoteproc: qcom_q6v5_pas: Add support for X1E80100 ADSP/CDSP
  dt-bindings: remoteproc: qcom,sm8550-pas: document the X1E80100 aDSP & cDSP
  remoteproc: qcom_wcnss: Use devm_rproc_alloc() helper
  remoteproc: qcom_q6v5_wcss: Use devm_rproc_alloc() helper
  remoteproc: qcom_q6v5_pas: Use devm_rproc_alloc() helper
  remoteproc: qcom_q6v5_mss: Use devm_rproc_alloc() helper
  remoteproc: qcom_q6v5_adsp: Use devm_rproc_alloc() helper
  dt-bindings: remoteproc: do not override firmware-name $ref
  dt-bindings: remoteproc: qcom,glink-rpm-edge: drop redundant type from label
  remoteproc: qcom: pas: correct data indentation
  remoteproc: Make rproc_get_by_phandle() work for clusters
  remoteproc: qcom: pas: Add SM8650 remoteproc support
  remoteproc: qcom: pas: make region assign more generic
  dt-bindings: remoteproc: qcom,sm8550-pas: document the SM8650 PAS
  remoteproc: k3-dsp: Use devm_rproc_add() helper
  remoteproc: k3-dsp: Use devm_ioremap_wc() helper
  remoteproc: k3-dsp: Add devm action to release tsp
  remoteproc: k3-dsp: Use devm_kzalloc() helper
  remoteproc: k3-dsp: Use devm_ti_sci_get_by_phandle() helper
  ...

25 files changed:
Documentation/devicetree/bindings/remoteproc/mtk,scp.yaml
Documentation/devicetree/bindings/remoteproc/qcom,glink-rpm-edge.yaml
Documentation/devicetree/bindings/remoteproc/qcom,qcs404-pas.yaml
Documentation/devicetree/bindings/remoteproc/qcom,sc7180-pas.yaml
Documentation/devicetree/bindings/remoteproc/qcom,sc7280-wpss-pil.yaml
Documentation/devicetree/bindings/remoteproc/qcom,sc8180x-pas.yaml
Documentation/devicetree/bindings/remoteproc/qcom,sm6115-pas.yaml
Documentation/devicetree/bindings/remoteproc/qcom,sm6350-pas.yaml
Documentation/devicetree/bindings/remoteproc/qcom,sm6375-pas.yaml
Documentation/devicetree/bindings/remoteproc/qcom,sm8150-pas.yaml
Documentation/devicetree/bindings/remoteproc/qcom,sm8350-pas.yaml
Documentation/devicetree/bindings/remoteproc/qcom,sm8550-pas.yaml
Documentation/devicetree/bindings/remoteproc/qcom,wcnss-pil.yaml
drivers/remoteproc/imx_dsp_rproc.c
drivers/remoteproc/imx_rproc.c
drivers/remoteproc/qcom_q6v5_adsp.c
drivers/remoteproc/qcom_q6v5_mss.c
drivers/remoteproc/qcom_q6v5_pas.c
drivers/remoteproc/qcom_q6v5_wcss.c
drivers/remoteproc/qcom_wcnss.c
drivers/remoteproc/remoteproc_core.c
drivers/remoteproc/remoteproc_virtio.c
drivers/remoteproc/st_remoteproc.c
drivers/remoteproc/stm32_rproc.c
drivers/remoteproc/ti_k3_dsp_remoteproc.c

index 09102dda4942c14121191c455e8edb6b3a6e3d42..507f98f73d235449cff58334cd9b07da2a0cdf3a 100644 (file)
@@ -47,7 +47,7 @@ properties:
     maxItems: 1
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description:
       If present, name (or relative path) of the file within the
       firmware search path containing the firmware image used when
@@ -115,7 +115,7 @@ patternProperties:
         maxItems: 1
 
       firmware-name:
-        $ref: /schemas/types.yaml#/definitions/string
+        maxItems: 1
         description:
           If present, name (or relative path) of the file within the
           firmware search path containing the firmware image used when
index 884158bccd50740edf5e2004289db4de752dfede..3766d4513b379010141c1d81f1f4b4df39e13b63 100644 (file)
@@ -18,7 +18,6 @@ properties:
     const: qcom,glink-rpm
 
   label:
-    $ref: /schemas/types.yaml#/definitions/string
     description:
       Name of the edge, used for debugging and identification purposes. The
       node name will be used if this is not present.
index eb868a7ff4cd819a3d09178e812481022436fe77..ad45fd00ae346e4a4a42659f466589718f6a6dff 100644 (file)
@@ -46,7 +46,7 @@ properties:
     description: Reference to the reserved-memory for the Hexagon core
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description: Firmware name for the Hexagon core
 
 required:
index c054b84fdcd5c51a31a628327bf2e99b851ff4d6..66b455d0a8e3271307028a23596d5d460f8b5d44 100644 (file)
@@ -45,7 +45,7 @@ properties:
   smd-edge: false
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description: Firmware name for the Hexagon core
 
 required:
index b6bd3343858450db5da8aa9ba51f6f01c97fd411..9381c7022ff499b99dc4179c93bce4960f78222c 100644 (file)
@@ -80,7 +80,7 @@ properties:
     description: Reference to the reserved-memory for the Hexagon core
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description:
       The name of the firmware which should be loaded for this remote
       processor.
index 4744a37b2b5d75b6ea5197414720cd9a465b631e..45ee9fbe09664ac93ab697d73d84ea55127a219b 100644 (file)
@@ -42,7 +42,7 @@ properties:
     description: Reference to the reserved-memory for the Hexagon core
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description: Firmware name for the Hexagon core
 
 required:
index 02828723591220abf50da6509b60d249dad9c59e..758adb06c8ddd915f52d8032537b90e23d9db72b 100644 (file)
@@ -47,7 +47,7 @@ properties:
   smd-edge: false
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description: Firmware name for the Hexagon core
 
 required:
index f7e40fb166da1f5bea65c6241ebfab2118510f4e..c1a3cc308bdb2d9ab73358d557c98442b9ac6a2a 100644 (file)
@@ -42,7 +42,7 @@ properties:
   smd-edge: false
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description: Firmware name for the Hexagon core
 
 required:
index 3e4a03eb4532b8f6eef7d5ce2ee5059691d4c6d1..7286b2baa19f2a8a41fbf193bd946a9cbe6b8fe1 100644 (file)
@@ -36,7 +36,7 @@ properties:
     description: Reference to the reserved-memory for the Hexagon core
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description: Firmware name for the Hexagon core
 
   smd-edge: false
index 238c6e5e67c5698baeaa2effad3e69ef37debf93..d67386c50fa4d6e4f9b844b36e17ffa1db613adb 100644 (file)
@@ -46,7 +46,7 @@ properties:
   smd-edge: false
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description: Firmware name for the Hexagon core
 
 required:
index 53cea8e53a311ebc9a8f6491b7b786acaa433af5..4b9fb74fb9e966b61d51fe578b636f967e4c6af8 100644 (file)
@@ -47,7 +47,7 @@ properties:
     description: Reference to the reserved-memory for the Hexagon core
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description: Firmware name for the Hexagon core
 
 required:
index 58120829fb06f5646f2c1af060bce326f2eec21b..73fda7565cd12fdc649baa1d406170096c4df7dd 100644 (file)
@@ -19,6 +19,11 @@ properties:
       - qcom,sm8550-adsp-pas
       - qcom,sm8550-cdsp-pas
       - qcom,sm8550-mpss-pas
+      - qcom,sm8650-adsp-pas
+      - qcom,sm8650-cdsp-pas
+      - qcom,sm8650-mpss-pas
+      - qcom,x1e80100-adsp-pas
+      - qcom,x1e80100-cdsp-pas
 
   reg:
     maxItems: 1
@@ -49,6 +54,8 @@ properties:
       - description: Memory region for main Firmware authentication
       - description: Memory region for Devicetree Firmware authentication
       - description: DSM Memory region
+      - description: DSM Memory region 2
+      - description: Memory region for Qlink Logging
 
 required:
   - compatible
@@ -63,6 +70,9 @@ allOf:
           enum:
             - qcom,sm8550-adsp-pas
             - qcom,sm8550-cdsp-pas
+            - qcom,sm8650-adsp-pas
+            - qcom,x1e80100-adsp-pas
+            - qcom,x1e80100-cdsp-pas
     then:
       properties:
         interrupts:
@@ -71,7 +81,26 @@ allOf:
           maxItems: 5
         memory-region:
           maxItems: 2
-    else:
+  - if:
+      properties:
+        compatible:
+          enum:
+            - qcom,sm8650-cdsp-pas
+    then:
+      properties:
+        interrupts:
+          maxItems: 5
+        interrupt-names:
+          maxItems: 5
+        memory-region:
+          minItems: 3
+          maxItems: 3
+  - if:
+      properties:
+        compatible:
+          enum:
+            - qcom,sm8550-mpss-pas
+    then:
       properties:
         interrupts:
           minItems: 6
@@ -79,12 +108,29 @@ allOf:
           minItems: 6
         memory-region:
           minItems: 3
+          maxItems: 3
+  - if:
+      properties:
+        compatible:
+          enum:
+            - qcom,sm8650-mpss-pas
+    then:
+      properties:
+        interrupts:
+          minItems: 6
+        interrupt-names:
+          minItems: 6
+        memory-region:
+          minItems: 5
+          maxItems: 5
 
   - if:
       properties:
         compatible:
           enum:
             - qcom,sm8550-adsp-pas
+            - qcom,sm8650-adsp-pas
+            - qcom,x1e80100-adsp-pas
     then:
       properties:
         power-domains:
@@ -101,6 +147,7 @@ allOf:
         compatible:
           enum:
             - qcom,sm8550-mpss-pas
+            - qcom,sm8650-mpss-pas
     then:
       properties:
         power-domains:
@@ -116,6 +163,8 @@ allOf:
         compatible:
           enum:
             - qcom,sm8550-cdsp-pas
+            - qcom,sm8650-cdsp-pas
+            - qcom,x1e80100-cdsp-pas
     then:
       properties:
         power-domains:
index 45eb42bd3c2cd8a061e7b7221bfffee1e28553ef..8e033b22d28cfa8203234f744b3b408e976e20c3 100644 (file)
@@ -51,7 +51,7 @@ properties:
       - const: stop-ack
 
   firmware-name:
-    $ref: /schemas/types.yaml#/definitions/string
+    maxItems: 1
     description:
       Relative firmware image path for the WCNSS core. Defaults to
       "wcnss.mdt".
index d73727a5828a4fa37d00b5b0f70cf4c2b186cc8b..087506e2150805d268ba669e307302828f0a331d 100644 (file)
@@ -1040,8 +1040,8 @@ static int imx_dsp_rproc_probe(struct platform_device *pdev)
                return ret;
        }
 
-       rproc = rproc_alloc(dev, "imx-dsp-rproc", &imx_dsp_rproc_ops, fw_name,
-                           sizeof(*priv));
+       rproc = devm_rproc_alloc(dev, "imx-dsp-rproc", &imx_dsp_rproc_ops,
+                                fw_name, sizeof(*priv));
        if (!rproc)
                return -ENOMEM;
 
@@ -1061,14 +1061,14 @@ static int imx_dsp_rproc_probe(struct platform_device *pdev)
        ret = imx_dsp_rproc_detect_mode(priv);
        if (ret) {
                dev_err(dev, "failed on imx_dsp_rproc_detect_mode\n");
-               goto err_put_rproc;
+               return ret;
        }
 
        /* There are multiple power domains required by DSP on some platform */
        ret = imx_dsp_attach_pm_domains(priv);
        if (ret) {
                dev_err(dev, "failed on imx_dsp_attach_pm_domains\n");
-               goto err_put_rproc;
+               return ret;
        }
        /* Get clocks */
        ret = imx_dsp_rproc_clk_get(priv);
@@ -1091,8 +1091,6 @@ static int imx_dsp_rproc_probe(struct platform_device *pdev)
 
 err_detach_domains:
        dev_pm_domain_detach_list(priv->pd_list);
-err_put_rproc:
-       rproc_free(rproc);
 
        return ret;
 }
@@ -1105,7 +1103,6 @@ static void imx_dsp_rproc_remove(struct platform_device *pdev)
        pm_runtime_disable(&pdev->dev);
        rproc_del(rproc);
        dev_pm_domain_detach_list(priv->pd_list);
-       rproc_free(rproc);
 }
 
 /* pm runtime functions */
index 3161f14442bc210eb8175e2922127e27d2bf875b..5a3fb902acc9f8e9aa6bca7b8c949b297a915a0a 100644 (file)
@@ -1049,16 +1049,14 @@ static int imx_rproc_probe(struct platform_device *pdev)
        int ret;
 
        /* set some other name then imx */
-       rproc = rproc_alloc(dev, "imx-rproc", &imx_rproc_ops,
-                           NULL, sizeof(*priv));
+       rproc = devm_rproc_alloc(dev, "imx-rproc", &imx_rproc_ops,
+                                NULL, sizeof(*priv));
        if (!rproc)
                return -ENOMEM;
 
        dcfg = of_device_get_match_data(dev);
-       if (!dcfg) {
-               ret = -EINVAL;
-               goto err_put_rproc;
-       }
+       if (!dcfg)
+               return -EINVAL;
 
        priv = rproc->priv;
        priv->rproc = rproc;
@@ -1069,8 +1067,7 @@ static int imx_rproc_probe(struct platform_device *pdev)
        priv->workqueue = create_workqueue(dev_name(dev));
        if (!priv->workqueue) {
                dev_err(dev, "cannot create workqueue\n");
-               ret = -ENOMEM;
-               goto err_put_rproc;
+               return -ENOMEM;
        }
 
        ret = imx_rproc_xtr_mbox_init(rproc);
@@ -1112,8 +1109,6 @@ err_put_mbox:
        imx_rproc_free_mbox(rproc);
 err_put_wkq:
        destroy_workqueue(priv->workqueue);
-err_put_rproc:
-       rproc_free(rproc);
 
        return ret;
 }
@@ -1128,7 +1123,6 @@ static void imx_rproc_remove(struct platform_device *pdev)
        imx_rproc_put_scu(rproc);
        imx_rproc_free_mbox(rproc);
        destroy_workqueue(priv->workqueue);
-       rproc_free(rproc);
 }
 
 static const struct of_device_id imx_rproc_of_match[] = {
index 93f9a1537ec60406ff826715453c02436ca2f65b..1d24c9b656a8299cd46e382a541df60a329cff11 100644 (file)
@@ -674,8 +674,8 @@ static int adsp_probe(struct platform_device *pdev)
                return ret;
        }
 
-       rproc = rproc_alloc(&pdev->dev, pdev->name, &adsp_ops,
-                           firmware_name, sizeof(*adsp));
+       rproc = devm_rproc_alloc(&pdev->dev, pdev->name, &adsp_ops,
+                                firmware_name, sizeof(*adsp));
        if (!rproc) {
                dev_err(&pdev->dev, "unable to allocate remoteproc\n");
                return -ENOMEM;
@@ -700,16 +700,16 @@ static int adsp_probe(struct platform_device *pdev)
 
        ret = adsp_alloc_memory_region(adsp);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        ret = adsp_init_clock(adsp, desc->clk_ids);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        ret = qcom_rproc_pds_attach(adsp, desc->pd_names, desc->num_pds);
        if (ret < 0) {
                dev_err(&pdev->dev, "Failed to attach proxy power domains\n");
-               goto free_rproc;
+               return ret;
        }
 
        ret = adsp_init_reset(adsp);
@@ -744,9 +744,6 @@ static int adsp_probe(struct platform_device *pdev)
 disable_pm:
        qcom_rproc_pds_detach(adsp);
 
-free_rproc:
-       rproc_free(rproc);
-
        return ret;
 }
 
@@ -761,7 +758,6 @@ static void adsp_remove(struct platform_device *pdev)
        qcom_remove_sysmon_subdev(adsp->sysmon);
        qcom_remove_ssr_subdev(adsp->rproc, &adsp->ssr_subdev);
        qcom_rproc_pds_detach(adsp);
-       rproc_free(adsp->rproc);
 }
 
 static const struct adsp_pil_data adsp_resource_init = {
index 394b2c1cb5e218bad7a11c0dfbc0c25de4bebf99..1779fc890e10243742ff17b06a75d8785338b2b7 100644 (file)
@@ -1990,8 +1990,8 @@ static int q6v5_probe(struct platform_device *pdev)
                return ret;
        }
 
-       rproc = rproc_alloc(&pdev->dev, pdev->name, &q6v5_ops,
-                           mba_image, sizeof(*qproc));
+       rproc = devm_rproc_alloc(&pdev->dev, pdev->name, &q6v5_ops,
+                                mba_image, sizeof(*qproc));
        if (!rproc) {
                dev_err(&pdev->dev, "failed to allocate rproc\n");
                return -ENOMEM;
@@ -2008,7 +2008,7 @@ static int q6v5_probe(struct platform_device *pdev)
                                            1, &qproc->hexagon_mdt_image);
        if (ret < 0 && ret != -EINVAL) {
                dev_err(&pdev->dev, "unable to read mpss firmware-name\n");
-               goto free_rproc;
+               return ret;
        }
 
        platform_set_drvdata(pdev, qproc);
@@ -2019,17 +2019,17 @@ static int q6v5_probe(struct platform_device *pdev)
        qproc->has_spare_reg = desc->has_spare_reg;
        ret = q6v5_init_mem(qproc, pdev);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        ret = q6v5_alloc_memory_region(qproc);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        ret = q6v5_init_clocks(&pdev->dev, qproc->proxy_clks,
                               desc->proxy_clk_names);
        if (ret < 0) {
                dev_err(&pdev->dev, "Failed to get proxy clocks.\n");
-               goto free_rproc;
+               return ret;
        }
        qproc->proxy_clk_count = ret;
 
@@ -2037,7 +2037,7 @@ static int q6v5_probe(struct platform_device *pdev)
                               desc->reset_clk_names);
        if (ret < 0) {
                dev_err(&pdev->dev, "Failed to get reset clocks.\n");
-               goto free_rproc;
+               return ret;
        }
        qproc->reset_clk_count = ret;
 
@@ -2045,7 +2045,7 @@ static int q6v5_probe(struct platform_device *pdev)
                               desc->active_clk_names);
        if (ret < 0) {
                dev_err(&pdev->dev, "Failed to get active clocks.\n");
-               goto free_rproc;
+               return ret;
        }
        qproc->active_clk_count = ret;
 
@@ -2053,7 +2053,7 @@ static int q6v5_probe(struct platform_device *pdev)
                                  desc->proxy_supply);
        if (ret < 0) {
                dev_err(&pdev->dev, "Failed to get proxy regulators.\n");
-               goto free_rproc;
+               return ret;
        }
        qproc->proxy_reg_count = ret;
 
@@ -2061,7 +2061,7 @@ static int q6v5_probe(struct platform_device *pdev)
                                  desc->active_supply);
        if (ret < 0) {
                dev_err(&pdev->dev, "Failed to get active regulators.\n");
-               goto free_rproc;
+               return ret;
        }
        qproc->active_reg_count = ret;
 
@@ -2074,12 +2074,12 @@ static int q6v5_probe(struct platform_device *pdev)
                                          desc->fallback_proxy_supply);
                if (ret < 0) {
                        dev_err(&pdev->dev, "Failed to get fallback proxy regulators.\n");
-                       goto free_rproc;
+                       return ret;
                }
                qproc->fallback_proxy_reg_count = ret;
        } else if (ret < 0) {
                dev_err(&pdev->dev, "Failed to init power domains\n");
-               goto free_rproc;
+               return ret;
        } else {
                qproc->proxy_pd_count = ret;
        }
@@ -2127,8 +2127,6 @@ remove_subdevs:
        qcom_remove_glink_subdev(rproc, &qproc->glink_subdev);
 detach_proxy_pds:
        q6v5_pds_detach(qproc, qproc->proxy_pds, qproc->proxy_pd_count);
-free_rproc:
-       rproc_free(rproc);
 
        return ret;
 }
@@ -2149,8 +2147,6 @@ static void q6v5_remove(struct platform_device *pdev)
        qcom_remove_glink_subdev(rproc, &qproc->glink_subdev);
 
        q6v5_pds_detach(qproc, qproc->proxy_pds, qproc->proxy_pd_count);
-
-       rproc_free(rproc);
 }
 
 static const struct rproc_hexagon_res sc7180_mss = {
index a9dd58608052c285aa87010b1ead045162970d63..54d8005d40a3435cf1207780de7fe6d99c8e92f4 100644 (file)
 
 #define ADSP_DECRYPT_SHUTDOWN_DELAY_MS 100
 
+#define MAX_ASSIGN_COUNT 3
+
 struct adsp_data {
        int crash_reason_smem;
        const char *firmware_name;
        const char *dtb_firmware_name;
        int pas_id;
        int dtb_pas_id;
+       int lite_pas_id;
        unsigned int minidump_id;
        bool auto_boot;
        bool decrypt_shutdown;
@@ -51,6 +54,9 @@ struct adsp_data {
        int ssctl_id;
 
        int region_assign_idx;
+       int region_assign_count;
+       bool region_assign_shared;
+       int region_assign_vmid;
 };
 
 struct qcom_adsp {
@@ -72,6 +78,7 @@ struct qcom_adsp {
        const char *dtb_firmware_name;
        int pas_id;
        int dtb_pas_id;
+       int lite_pas_id;
        unsigned int minidump_id;
        int crash_reason_smem;
        bool decrypt_shutdown;
@@ -87,15 +94,18 @@ struct qcom_adsp {
        phys_addr_t dtb_mem_phys;
        phys_addr_t mem_reloc;
        phys_addr_t dtb_mem_reloc;
-       phys_addr_t region_assign_phys;
+       phys_addr_t region_assign_phys[MAX_ASSIGN_COUNT];
        void *mem_region;
        void *dtb_mem_region;
        size_t mem_size;
        size_t dtb_mem_size;
-       size_t region_assign_size;
+       size_t region_assign_size[MAX_ASSIGN_COUNT];
 
        int region_assign_idx;
-       u64 region_assign_perms;
+       int region_assign_count;
+       bool region_assign_shared;
+       int region_assign_vmid;
+       u64 region_assign_owners[MAX_ASSIGN_COUNT];
 
        struct qcom_rproc_glink glink_subdev;
        struct qcom_rproc_subdev smd_subdev;
@@ -210,6 +220,9 @@ static int adsp_load(struct rproc *rproc, const struct firmware *fw)
        /* Store firmware handle to be used in adsp_start() */
        adsp->firmware = fw;
 
+       if (adsp->lite_pas_id)
+               ret = qcom_scm_pas_shutdown(adsp->lite_pas_id);
+
        if (adsp->dtb_pas_id) {
                ret = request_firmware(&adsp->dtb_firmware, adsp->dtb_firmware_name, adsp->dev);
                if (ret) {
@@ -590,37 +603,53 @@ static int adsp_alloc_memory_region(struct qcom_adsp *adsp)
 
 static int adsp_assign_memory_region(struct qcom_adsp *adsp)
 {
-       struct reserved_mem *rmem = NULL;
-       struct qcom_scm_vmperm perm;
+       struct qcom_scm_vmperm perm[MAX_ASSIGN_COUNT];
        struct device_node *node;
+       unsigned int perm_size;
+       int offset;
        int ret;
 
        if (!adsp->region_assign_idx)
                return 0;
 
-       node = of_parse_phandle(adsp->dev->of_node, "memory-region", adsp->region_assign_idx);
-       if (node)
-               rmem = of_reserved_mem_lookup(node);
-       of_node_put(node);
-       if (!rmem) {
-               dev_err(adsp->dev, "unable to resolve shareable memory-region\n");
-               return -EINVAL;
-       }
+       for (offset = 0; offset < adsp->region_assign_count; ++offset) {
+               struct reserved_mem *rmem = NULL;
+
+               node = of_parse_phandle(adsp->dev->of_node, "memory-region",
+                                       adsp->region_assign_idx + offset);
+               if (node)
+                       rmem = of_reserved_mem_lookup(node);
+               of_node_put(node);
+               if (!rmem) {
+                       dev_err(adsp->dev, "unable to resolve shareable memory-region index %d\n",
+                               offset);
+                       return -EINVAL;
+               }
 
-       perm.vmid = QCOM_SCM_VMID_MSS_MSA;
-       perm.perm = QCOM_SCM_PERM_RW;
+               if (adsp->region_assign_shared)  {
+                       perm[0].vmid = QCOM_SCM_VMID_HLOS;
+                       perm[0].perm = QCOM_SCM_PERM_RW;
+                       perm[1].vmid = adsp->region_assign_vmid;
+                       perm[1].perm = QCOM_SCM_PERM_RW;
+                       perm_size = 2;
+               } else {
+                       perm[0].vmid = adsp->region_assign_vmid;
+                       perm[0].perm = QCOM_SCM_PERM_RW;
+                       perm_size = 1;
+               }
 
-       adsp->region_assign_phys = rmem->base;
-       adsp->region_assign_size = rmem->size;
-       adsp->region_assign_perms = BIT(QCOM_SCM_VMID_HLOS);
+               adsp->region_assign_phys[offset] = rmem->base;
+               adsp->region_assign_size[offset] = rmem->size;
+               adsp->region_assign_owners[offset] = BIT(QCOM_SCM_VMID_HLOS);
 
-       ret = qcom_scm_assign_mem(adsp->region_assign_phys,
-                                 adsp->region_assign_size,
-                                 &adsp->region_assign_perms,
-                                 &perm, 1);
-       if (ret < 0) {
-               dev_err(adsp->dev, "assign memory failed\n");
-               return ret;
+               ret = qcom_scm_assign_mem(adsp->region_assign_phys[offset],
+                                         adsp->region_assign_size[offset],
+                                         &adsp->region_assign_owners[offset],
+                                         perm, perm_size);
+               if (ret < 0) {
+                       dev_err(adsp->dev, "assign memory %d failed\n", offset);
+                       return ret;
+               }
        }
 
        return 0;
@@ -629,20 +658,23 @@ static int adsp_assign_memory_region(struct qcom_adsp *adsp)
 static void adsp_unassign_memory_region(struct qcom_adsp *adsp)
 {
        struct qcom_scm_vmperm perm;
+       int offset;
        int ret;
 
-       if (!adsp->region_assign_idx)
+       if (!adsp->region_assign_idx || adsp->region_assign_shared)
                return;
 
-       perm.vmid = QCOM_SCM_VMID_HLOS;
-       perm.perm = QCOM_SCM_PERM_RW;
+       for (offset = 0; offset < adsp->region_assign_count; ++offset) {
+               perm.vmid = QCOM_SCM_VMID_HLOS;
+               perm.perm = QCOM_SCM_PERM_RW;
 
-       ret = qcom_scm_assign_mem(adsp->region_assign_phys,
-                                 adsp->region_assign_size,
-                                 &adsp->region_assign_perms,
-                                 &perm, 1);
-       if (ret < 0)
-               dev_err(adsp->dev, "unassign memory failed\n");
+               ret = qcom_scm_assign_mem(adsp->region_assign_phys[offset],
+                                         adsp->region_assign_size[offset],
+                                         &adsp->region_assign_owners[offset],
+                                         &perm, 1);
+               if (ret < 0)
+                       dev_err(adsp->dev, "unassign memory %d failed\n", offset);
+       }
 }
 
 static int adsp_probe(struct platform_device *pdev)
@@ -678,7 +710,7 @@ static int adsp_probe(struct platform_device *pdev)
        if (desc->minidump_id)
                ops = &adsp_minidump_ops;
 
-       rproc = rproc_alloc(&pdev->dev, pdev->name, ops, fw_name, sizeof(*adsp));
+       rproc = devm_rproc_alloc(&pdev->dev, pdev->name, ops, fw_name, sizeof(*adsp));
 
        if (!rproc) {
                dev_err(&pdev->dev, "unable to allocate remoteproc\n");
@@ -693,9 +725,13 @@ static int adsp_probe(struct platform_device *pdev)
        adsp->rproc = rproc;
        adsp->minidump_id = desc->minidump_id;
        adsp->pas_id = desc->pas_id;
+       adsp->lite_pas_id = desc->lite_pas_id;
        adsp->info_name = desc->sysmon_name;
        adsp->decrypt_shutdown = desc->decrypt_shutdown;
        adsp->region_assign_idx = desc->region_assign_idx;
+       adsp->region_assign_count = min_t(int, MAX_ASSIGN_COUNT, desc->region_assign_count);
+       adsp->region_assign_vmid = desc->region_assign_vmid;
+       adsp->region_assign_shared = desc->region_assign_shared;
        if (dtb_fw_name) {
                adsp->dtb_firmware_name = dtb_fw_name;
                adsp->dtb_pas_id = desc->dtb_pas_id;
@@ -754,7 +790,6 @@ detach_proxy_pds:
        adsp_pds_detach(adsp, adsp->proxy_pds, adsp->proxy_pd_count);
 free_rproc:
        device_init_wakeup(adsp->dev, false);
-       rproc_free(rproc);
 
        return ret;
 }
@@ -773,28 +808,27 @@ static void adsp_remove(struct platform_device *pdev)
        qcom_remove_ssr_subdev(adsp->rproc, &adsp->ssr_subdev);
        adsp_pds_detach(adsp, adsp->proxy_pds, adsp->proxy_pd_count);
        device_init_wakeup(adsp->dev, false);
-       rproc_free(adsp->rproc);
 }
 
 static const struct adsp_data adsp_resource_init = {
-               .crash_reason_smem = 423,
-               .firmware_name = "adsp.mdt",
-               .pas_id = 1,
-               .auto_boot = true,
-               .ssr_name = "lpass",
-               .sysmon_name = "adsp",
-               .ssctl_id = 0x14,
+       .crash_reason_smem = 423,
+       .firmware_name = "adsp.mdt",
+       .pas_id = 1,
+       .auto_boot = true,
+       .ssr_name = "lpass",
+       .sysmon_name = "adsp",
+       .ssctl_id = 0x14,
 };
 
 static const struct adsp_data sdm845_adsp_resource_init = {
-               .crash_reason_smem = 423,
-               .firmware_name = "adsp.mdt",
-               .pas_id = 1,
-               .auto_boot = true,
-               .load_state = "adsp",
-               .ssr_name = "lpass",
-               .sysmon_name = "adsp",
-               .ssctl_id = 0x14,
+       .crash_reason_smem = 423,
+       .firmware_name = "adsp.mdt",
+       .pas_id = 1,
+       .auto_boot = true,
+       .load_state = "adsp",
+       .ssr_name = "lpass",
+       .sysmon_name = "adsp",
+       .ssctl_id = 0x14,
 };
 
 static const struct adsp_data sm6350_adsp_resource = {
@@ -829,18 +863,18 @@ static const struct adsp_data sm6375_mpss_resource = {
 };
 
 static const struct adsp_data sm8150_adsp_resource = {
-               .crash_reason_smem = 423,
-               .firmware_name = "adsp.mdt",
-               .pas_id = 1,
-               .auto_boot = true,
-               .proxy_pd_names = (char*[]){
-                       "cx",
-                       NULL
-               },
-               .load_state = "adsp",
-               .ssr_name = "lpass",
-               .sysmon_name = "adsp",
-               .ssctl_id = 0x14,
+       .crash_reason_smem = 423,
+       .firmware_name = "adsp.mdt",
+       .pas_id = 1,
+       .auto_boot = true,
+       .proxy_pd_names = (char*[]){
+               "cx",
+               NULL
+       },
+       .load_state = "adsp",
+       .ssr_name = "lpass",
+       .sysmon_name = "adsp",
+       .ssctl_id = 0x14,
 };
 
 static const struct adsp_data sm8250_adsp_resource = {
@@ -876,17 +910,17 @@ static const struct adsp_data sm8350_adsp_resource = {
 };
 
 static const struct adsp_data msm8996_adsp_resource = {
-               .crash_reason_smem = 423,
-               .firmware_name = "adsp.mdt",
-               .pas_id = 1,
-               .auto_boot = true,
-               .proxy_pd_names = (char*[]){
-                       "cx",
-                       NULL
-               },
-               .ssr_name = "lpass",
-               .sysmon_name = "adsp",
-               .ssctl_id = 0x14,
+       .crash_reason_smem = 423,
+       .firmware_name = "adsp.mdt",
+       .pas_id = 1,
+       .auto_boot = true,
+       .proxy_pd_names = (char*[]){
+               "cx",
+               NULL
+       },
+       .ssr_name = "lpass",
+       .sysmon_name = "adsp",
+       .ssctl_id = 0x14,
 };
 
 static const struct adsp_data cdsp_resource_init = {
@@ -984,6 +1018,46 @@ static const struct adsp_data sc8280xp_nsp1_resource = {
        .ssctl_id = 0x20,
 };
 
+static const struct adsp_data x1e80100_adsp_resource = {
+       .crash_reason_smem = 423,
+       .firmware_name = "adsp.mdt",
+       .dtb_firmware_name = "adsp_dtb.mdt",
+       .pas_id = 1,
+       .dtb_pas_id = 0x24,
+       .lite_pas_id = 0x1f,
+       .minidump_id = 5,
+       .auto_boot = true,
+       .proxy_pd_names = (char*[]){
+               "lcx",
+               "lmx",
+               NULL
+       },
+       .load_state = "adsp",
+       .ssr_name = "lpass",
+       .sysmon_name = "adsp",
+       .ssctl_id = 0x14,
+};
+
+static const struct adsp_data x1e80100_cdsp_resource = {
+       .crash_reason_smem = 601,
+       .firmware_name = "cdsp.mdt",
+       .dtb_firmware_name = "cdsp_dtb.mdt",
+       .pas_id = 18,
+       .dtb_pas_id = 0x25,
+       .minidump_id = 7,
+       .auto_boot = true,
+       .proxy_pd_names = (char*[]){
+               "cx",
+               "mxc",
+               "nsp",
+               NULL
+       },
+       .load_state = "cdsp",
+       .ssr_name = "cdsp",
+       .sysmon_name = "cdsp",
+       .ssctl_id = 0x17,
+};
+
 static const struct adsp_data sm8350_cdsp_resource = {
        .crash_reason_smem = 601,
        .firmware_name = "cdsp.mdt",
@@ -1033,33 +1107,33 @@ static const struct adsp_data sc8180x_mpss_resource = {
 };
 
 static const struct adsp_data msm8996_slpi_resource_init = {
-               .crash_reason_smem = 424,
-               .firmware_name = "slpi.mdt",
-               .pas_id = 12,
-               .auto_boot = true,
-               .proxy_pd_names = (char*[]){
-                       "ssc_cx",
-                       NULL
-               },
-               .ssr_name = "dsps",
-               .sysmon_name = "slpi",
-               .ssctl_id = 0x16,
+       .crash_reason_smem = 424,
+       .firmware_name = "slpi.mdt",
+       .pas_id = 12,
+       .auto_boot = true,
+       .proxy_pd_names = (char*[]){
+               "ssc_cx",
+               NULL
+       },
+       .ssr_name = "dsps",
+       .sysmon_name = "slpi",
+       .ssctl_id = 0x16,
 };
 
 static const struct adsp_data sdm845_slpi_resource_init = {
-               .crash_reason_smem = 424,
-               .firmware_name = "slpi.mdt",
-               .pas_id = 12,
-               .auto_boot = true,
-               .proxy_pd_names = (char*[]){
-                       "lcx",
-                       "lmx",
-                       NULL
-               },
-               .load_state = "slpi",
-               .ssr_name = "dsps",
-               .sysmon_name = "slpi",
-               .ssctl_id = 0x16,
+       .crash_reason_smem = 424,
+       .firmware_name = "slpi.mdt",
+       .pas_id = 12,
+       .auto_boot = true,
+       .proxy_pd_names = (char*[]){
+               "lcx",
+               "lmx",
+               NULL
+       },
+       .load_state = "slpi",
+       .ssr_name = "dsps",
+       .sysmon_name = "slpi",
+       .ssctl_id = 0x16,
 };
 
 static const struct adsp_data wcss_resource_init = {
@@ -1163,6 +1237,8 @@ static const struct adsp_data sm8550_mpss_resource = {
        .sysmon_name = "modem",
        .ssctl_id = 0x12,
        .region_assign_idx = 2,
+       .region_assign_count = 1,
+       .region_assign_vmid = QCOM_SCM_VMID_MSS_MSA,
 };
 
 static const struct adsp_data sc7280_wpss_resource = {
@@ -1181,6 +1257,53 @@ static const struct adsp_data sc7280_wpss_resource = {
        .ssctl_id = 0x19,
 };
 
+static const struct adsp_data sm8650_cdsp_resource = {
+       .crash_reason_smem = 601,
+       .firmware_name = "cdsp.mdt",
+       .dtb_firmware_name = "cdsp_dtb.mdt",
+       .pas_id = 18,
+       .dtb_pas_id = 0x25,
+       .minidump_id = 7,
+       .auto_boot = true,
+       .proxy_pd_names = (char*[]){
+               "cx",
+               "mxc",
+               "nsp",
+               NULL
+       },
+       .load_state = "cdsp",
+       .ssr_name = "cdsp",
+       .sysmon_name = "cdsp",
+       .ssctl_id = 0x17,
+       .region_assign_idx = 2,
+       .region_assign_count = 1,
+       .region_assign_shared = true,
+       .region_assign_vmid = QCOM_SCM_VMID_CDSP,
+};
+
+static const struct adsp_data sm8650_mpss_resource = {
+       .crash_reason_smem = 421,
+       .firmware_name = "modem.mdt",
+       .dtb_firmware_name = "modem_dtb.mdt",
+       .pas_id = 4,
+       .dtb_pas_id = 0x26,
+       .minidump_id = 3,
+       .auto_boot = false,
+       .decrypt_shutdown = true,
+       .proxy_pd_names = (char*[]){
+               "cx",
+               "mss",
+               NULL
+       },
+       .load_state = "modem",
+       .ssr_name = "mpss",
+       .sysmon_name = "modem",
+       .ssctl_id = 0x12,
+       .region_assign_idx = 2,
+       .region_assign_count = 3,
+       .region_assign_vmid = QCOM_SCM_VMID_MSS_MSA,
+};
+
 static const struct of_device_id adsp_of_match[] = {
        { .compatible = "qcom,msm8226-adsp-pil", .data = &adsp_resource_init},
        { .compatible = "qcom,msm8953-adsp-pil", .data = &msm8996_adsp_resource},
@@ -1236,6 +1359,11 @@ static const struct of_device_id adsp_of_match[] = {
        { .compatible = "qcom,sm8550-adsp-pas", .data = &sm8550_adsp_resource},
        { .compatible = "qcom,sm8550-cdsp-pas", .data = &sm8550_cdsp_resource},
        { .compatible = "qcom,sm8550-mpss-pas", .data = &sm8550_mpss_resource},
+       { .compatible = "qcom,sm8650-adsp-pas", .data = &sm8550_adsp_resource},
+       { .compatible = "qcom,sm8650-cdsp-pas", .data = &sm8650_cdsp_resource},
+       { .compatible = "qcom,sm8650-mpss-pas", .data = &sm8650_mpss_resource},
+       { .compatible = "qcom,x1e80100-adsp-pas", .data = &x1e80100_adsp_resource},
+       { .compatible = "qcom,x1e80100-cdsp-pas", .data = &x1e80100_cdsp_resource},
        { },
 };
 MODULE_DEVICE_TABLE(of, adsp_of_match);
index cff1fa07d1def7fb0ad462d162e68248888cdfde..94f68c919ee622d2cad0845f56d3cc4aa4e30b63 100644 (file)
@@ -1011,8 +1011,8 @@ static int q6v5_wcss_probe(struct platform_device *pdev)
        if (!desc)
                return -EINVAL;
 
-       rproc = rproc_alloc(&pdev->dev, pdev->name, desc->ops,
-                           desc->firmware_name, sizeof(*wcss));
+       rproc = devm_rproc_alloc(&pdev->dev, pdev->name, desc->ops,
+                                desc->firmware_name, sizeof(*wcss));
        if (!rproc) {
                dev_err(&pdev->dev, "failed to allocate rproc\n");
                return -ENOMEM;
@@ -1027,29 +1027,29 @@ static int q6v5_wcss_probe(struct platform_device *pdev)
 
        ret = q6v5_wcss_init_mmio(wcss, pdev);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        ret = q6v5_alloc_memory_region(wcss);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        if (wcss->version == WCSS_QCS404) {
                ret = q6v5_wcss_init_clock(wcss);
                if (ret)
-                       goto free_rproc;
+                       return ret;
 
                ret = q6v5_wcss_init_regulator(wcss);
                if (ret)
-                       goto free_rproc;
+                       return ret;
        }
 
        ret = q6v5_wcss_init_reset(wcss, desc);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        ret = qcom_q6v5_init(&wcss->q6v5, pdev, rproc, desc->crash_reason_smem, NULL, NULL);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        qcom_add_glink_subdev(rproc, &wcss->glink_subdev, "q6wcss");
        qcom_add_ssr_subdev(rproc, &wcss->ssr_subdev, "q6wcss");
@@ -1061,16 +1061,11 @@ static int q6v5_wcss_probe(struct platform_device *pdev)
 
        ret = rproc_add(rproc);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        platform_set_drvdata(pdev, rproc);
 
        return 0;
-
-free_rproc:
-       rproc_free(rproc);
-
-       return ret;
 }
 
 static void q6v5_wcss_remove(struct platform_device *pdev)
@@ -1080,7 +1075,6 @@ static void q6v5_wcss_remove(struct platform_device *pdev)
 
        qcom_q6v5_deinit(&wcss->q6v5);
        rproc_del(rproc);
-       rproc_free(rproc);
 }
 
 static const struct wcss_data wcss_ipq8074_res_init = {
index 90de22c81da9761ec560f198c13d9d1b8d639ffe..a7bb9da27029db23f3759b19e423fab11b8430e4 100644 (file)
@@ -555,8 +555,8 @@ static int wcnss_probe(struct platform_device *pdev)
        if (ret < 0 && ret != -EINVAL)
                return ret;
 
-       rproc = rproc_alloc(&pdev->dev, pdev->name, &wcnss_ops,
-                           fw_name, sizeof(*wcnss));
+       rproc = devm_rproc_alloc(&pdev->dev, pdev->name, &wcnss_ops,
+                                fw_name, sizeof(*wcnss));
        if (!rproc) {
                dev_err(&pdev->dev, "unable to allocate remoteproc\n");
                return -ENOMEM;
@@ -574,14 +574,12 @@ static int wcnss_probe(struct platform_device *pdev)
        mutex_init(&wcnss->iris_lock);
 
        mmio = devm_platform_ioremap_resource_byname(pdev, "pmu");
-       if (IS_ERR(mmio)) {
-               ret = PTR_ERR(mmio);
-               goto free_rproc;
-       }
+       if (IS_ERR(mmio))
+               return PTR_ERR(mmio);
 
        ret = wcnss_alloc_memory_region(wcnss);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        wcnss->pmu_cfg = mmio + data->pmu_offset;
        wcnss->spare_out = mmio + data->spare_offset;
@@ -592,7 +590,7 @@ static int wcnss_probe(struct platform_device *pdev)
         */
        ret = wcnss_init_pds(wcnss, data->pd_names);
        if (ret && (ret != -ENODATA || !data->num_pd_vregs))
-               goto free_rproc;
+               return ret;
 
        ret = wcnss_init_regulators(wcnss, data->vregs, data->num_vregs,
                                    data->num_pd_vregs);
@@ -656,8 +654,6 @@ remove_iris:
        qcom_iris_remove(wcnss->iris);
 detach_pds:
        wcnss_release_pds(wcnss);
-free_rproc:
-       rproc_free(rproc);
 
        return ret;
 }
@@ -673,7 +669,6 @@ static void wcnss_remove(struct platform_device *pdev)
        qcom_remove_sysmon_subdev(wcnss->sysmon);
        qcom_remove_smd_subdev(wcnss->rproc, &wcnss->smd_subdev);
        wcnss_release_pds(wcnss);
-       rproc_free(wcnss->rproc);
 }
 
 static const struct of_device_id wcnss_of_match[] = {
index 695cce218e8c6423c67658b5e9be49d0ff1920cc..f276956f2c5cec3b0e0f9809d54f3b75c08a15f7 100644 (file)
@@ -33,6 +33,7 @@
 #include <linux/idr.h>
 #include <linux/elf.h>
 #include <linux/crc32.h>
+#include <linux/of_platform.h>
 #include <linux/of_reserved_mem.h>
 #include <linux/virtio_ids.h>
 #include <linux/virtio_ring.h>
@@ -2112,6 +2113,7 @@ EXPORT_SYMBOL(rproc_detach);
 struct rproc *rproc_get_by_phandle(phandle phandle)
 {
        struct rproc *rproc = NULL, *r;
+       struct device_driver *driver;
        struct device_node *np;
 
        np = of_find_node_by_phandle(phandle);
@@ -2122,7 +2124,26 @@ struct rproc *rproc_get_by_phandle(phandle phandle)
        list_for_each_entry_rcu(r, &rproc_list, node) {
                if (r->dev.parent && device_match_of_node(r->dev.parent, np)) {
                        /* prevent underlying implementation from being removed */
-                       if (!try_module_get(r->dev.parent->driver->owner)) {
+
+                       /*
+                        * If the remoteproc's parent has a driver, the
+                        * remoteproc is not part of a cluster and we can use
+                        * that driver.
+                        */
+                       driver = r->dev.parent->driver;
+
+                       /*
+                        * If the remoteproc's parent does not have a driver,
+                        * look for the driver associated with the cluster.
+                        */
+                       if (!driver) {
+                               if (r->dev.parent->parent)
+                                       driver = r->dev.parent->parent->driver;
+                               if (!driver)
+                                       break;
+                       }
+
+                       if (!try_module_get(driver->owner)) {
                                dev_err(&r->dev, "can't get owner\n");
                                break;
                        }
@@ -2533,7 +2554,11 @@ EXPORT_SYMBOL(rproc_free);
  */
 void rproc_put(struct rproc *rproc)
 {
-       module_put(rproc->dev.parent->driver->owner);
+       if (rproc->dev.parent->driver)
+               module_put(rproc->dev.parent->driver->owner);
+       else
+               module_put(rproc->dev.parent->parent->driver->owner);
+
        put_device(&rproc->dev);
 }
 EXPORT_SYMBOL(rproc_put);
index 83d76915a6ad6f28f930b705c274dc82897b36de..25b66b113b69594b7edf01caff62bda8435c9bbb 100644 (file)
@@ -351,6 +351,9 @@ static void rproc_virtio_dev_release(struct device *dev)
 
        kfree(vdev);
 
+       of_reserved_mem_device_release(&rvdev->pdev->dev);
+       dma_release_coherent_memory(&rvdev->pdev->dev);
+
        put_device(&rvdev->pdev->dev);
 }
 
@@ -584,9 +587,6 @@ static void rproc_virtio_remove(struct platform_device *pdev)
        rproc_remove_subdev(rproc, &rvdev->subdev);
        rproc_remove_rvdev(rvdev);
 
-       of_reserved_mem_device_release(&pdev->dev);
-       dma_release_coherent_memory(&pdev->dev);
-
        put_device(&rproc->dev);
 }
 
index cb163766c56d526333dabbdc5a42b09a1fe65546..1340be9d0110175c41318208ece611d882da2399 100644 (file)
@@ -347,23 +347,21 @@ static int st_rproc_probe(struct platform_device *pdev)
        int enabled;
        int ret, i;
 
-       rproc = rproc_alloc(dev, np->name, &st_rproc_ops, NULL, sizeof(*ddata));
+       rproc = devm_rproc_alloc(dev, np->name, &st_rproc_ops, NULL, sizeof(*ddata));
        if (!rproc)
                return -ENOMEM;
 
        rproc->has_iommu = false;
        ddata = rproc->priv;
        ddata->config = (struct st_rproc_config *)device_get_match_data(dev);
-       if (!ddata->config) {
-               ret = -ENODEV;
-               goto free_rproc;
-       }
+       if (!ddata->config)
+               return -ENODEV;
 
        platform_set_drvdata(pdev, rproc);
 
        ret = st_rproc_parse_dt(pdev);
        if (ret)
-               goto free_rproc;
+               return ret;
 
        enabled = st_rproc_state(pdev);
        if (enabled < 0) {
@@ -439,8 +437,7 @@ free_mbox:
                mbox_free_channel(ddata->mbox_chan[i]);
 free_clk:
        clk_unprepare(ddata->clk);
-free_rproc:
-       rproc_free(rproc);
+
        return ret;
 }
 
@@ -456,8 +453,6 @@ static void st_rproc_remove(struct platform_device *pdev)
 
        for (i = 0; i < ST_RPROC_MAX_VRING * MBOX_MAX; i++)
                mbox_free_channel(ddata->mbox_chan[i]);
-
-       rproc_free(rproc);
 }
 
 static struct platform_driver st_rproc_driver = {
index 4f469f0bcf8b29d5cecbfa3acab4e83c0dd5c695..88623df7d0c35a0ab1971befbe076721f2316822 100644 (file)
@@ -120,7 +120,7 @@ static int stm32_rproc_mem_alloc(struct rproc *rproc,
        void *va;
 
        dev_dbg(dev, "map memory: %pad+%zx\n", &mem->dma, mem->len);
-       va = ioremap_wc(mem->dma, mem->len);
+       va = (__force void *)ioremap_wc(mem->dma, mem->len);
        if (IS_ERR_OR_NULL(va)) {
                dev_err(dev, "Unable to map memory region: %pad+0x%zx\n",
                        &mem->dma, mem->len);
@@ -137,7 +137,7 @@ static int stm32_rproc_mem_release(struct rproc *rproc,
                                   struct rproc_mem_entry *mem)
 {
        dev_dbg(rproc->dev.parent, "unmap memory: %pa\n", &mem->dma);
-       iounmap(mem->va);
+       iounmap((__force __iomem void *)mem->va);
 
        return 0;
 }
@@ -657,7 +657,7 @@ done:
         * entire area by overwriting it with the initial values stored in rproc->clean_table.
         */
        *table_sz = RSC_TBL_SIZE;
-       return (struct resource_table *)ddata->rsc_va;
+       return (__force struct resource_table *)ddata->rsc_va;
 }
 
 static const struct rproc_ops st_rproc_ops = {
@@ -843,7 +843,7 @@ static int stm32_rproc_probe(struct platform_device *pdev)
        if (ret)
                return ret;
 
-       rproc = rproc_alloc(dev, np->name, &st_rproc_ops, NULL, sizeof(*ddata));
+       rproc = devm_rproc_alloc(dev, np->name, &st_rproc_ops, NULL, sizeof(*ddata));
        if (!rproc)
                return -ENOMEM;
 
@@ -897,7 +897,6 @@ free_rproc:
                dev_pm_clear_wake_irq(dev);
                device_init_wakeup(dev, false);
        }
-       rproc_free(rproc);
        return ret;
 }
 
@@ -918,7 +917,6 @@ static void stm32_rproc_remove(struct platform_device *pdev)
                dev_pm_clear_wake_irq(dev);
                device_init_wakeup(dev, false);
        }
-       rproc_free(rproc);
 }
 
 static int stm32_rproc_suspend(struct device *dev)
index ab882e3b7130bcb50df0840207b112280e3f80b9..3555b535b16838bf7a7c9125c2f6c5619051f497 100644 (file)
@@ -550,6 +550,13 @@ static int k3_dsp_rproc_of_get_memories(struct platform_device *pdev,
        return 0;
 }
 
+static void k3_dsp_mem_release(void *data)
+{
+       struct device *dev = data;
+
+       of_reserved_mem_device_release(dev);
+}
+
 static int k3_dsp_reserved_mem_init(struct k3_dsp_rproc *kproc)
 {
        struct device *dev = kproc->dev;
@@ -579,27 +586,25 @@ static int k3_dsp_reserved_mem_init(struct k3_dsp_rproc *kproc)
                        ERR_PTR(ret));
                return ret;
        }
+       ret = devm_add_action_or_reset(dev, k3_dsp_mem_release, dev);
+       if (ret)
+               return ret;
 
        num_rmems--;
-       kproc->rmem = kcalloc(num_rmems, sizeof(*kproc->rmem), GFP_KERNEL);
-       if (!kproc->rmem) {
-               ret = -ENOMEM;
-               goto release_rmem;
-       }
+       kproc->rmem = devm_kcalloc(dev, num_rmems, sizeof(*kproc->rmem), GFP_KERNEL);
+       if (!kproc->rmem)
+               return -ENOMEM;
 
        /* use remaining reserved memory regions for static carveouts */
        for (i = 0; i < num_rmems; i++) {
                rmem_np = of_parse_phandle(np, "memory-region", i + 1);
-               if (!rmem_np) {
-                       ret = -EINVAL;
-                       goto unmap_rmem;
-               }
+               if (!rmem_np)
+                       return -EINVAL;
 
                rmem = of_reserved_mem_lookup(rmem_np);
                if (!rmem) {
                        of_node_put(rmem_np);
-                       ret = -EINVAL;
-                       goto unmap_rmem;
+                       return -EINVAL;
                }
                of_node_put(rmem_np);
 
@@ -607,12 +612,11 @@ static int k3_dsp_reserved_mem_init(struct k3_dsp_rproc *kproc)
                /* 64-bit address regions currently not supported */
                kproc->rmem[i].dev_addr = (u32)rmem->base;
                kproc->rmem[i].size = rmem->size;
-               kproc->rmem[i].cpu_addr = ioremap_wc(rmem->base, rmem->size);
+               kproc->rmem[i].cpu_addr = devm_ioremap_wc(dev, rmem->base, rmem->size);
                if (!kproc->rmem[i].cpu_addr) {
                        dev_err(dev, "failed to map reserved memory#%d at %pa of size %pa\n",
                                i + 1, &rmem->base, &rmem->size);
-                       ret = -ENOMEM;
-                       goto unmap_rmem;
+                       return -ENOMEM;
                }
 
                dev_dbg(dev, "reserved memory%d: bus addr %pa size 0x%zx va %pK da 0x%x\n",
@@ -623,25 +627,13 @@ static int k3_dsp_reserved_mem_init(struct k3_dsp_rproc *kproc)
        kproc->num_rmems = num_rmems;
 
        return 0;
-
-unmap_rmem:
-       for (i--; i >= 0; i--)
-               iounmap(kproc->rmem[i].cpu_addr);
-       kfree(kproc->rmem);
-release_rmem:
-       of_reserved_mem_device_release(kproc->dev);
-       return ret;
 }
 
-static void k3_dsp_reserved_mem_exit(struct k3_dsp_rproc *kproc)
+static void k3_dsp_release_tsp(void *data)
 {
-       int i;
+       struct ti_sci_proc *tsp = data;
 
-       for (i = 0; i < kproc->num_rmems; i++)
-               iounmap(kproc->rmem[i].cpu_addr);
-       kfree(kproc->rmem);
-
-       of_reserved_mem_device_release(kproc->dev);
+       ti_sci_proc_release(tsp);
 }
 
 static
@@ -657,7 +649,7 @@ struct ti_sci_proc *k3_dsp_rproc_of_get_tsp(struct device *dev,
        if (ret < 0)
                return ERR_PTR(ret);
 
-       tsp = kzalloc(sizeof(*tsp), GFP_KERNEL);
+       tsp = devm_kzalloc(dev, sizeof(*tsp), GFP_KERNEL);
        if (!tsp)
                return ERR_PTR(-ENOMEM);
 
@@ -680,7 +672,6 @@ static int k3_dsp_rproc_probe(struct platform_device *pdev)
        const char *fw_name;
        bool p_state = false;
        int ret = 0;
-       int ret1;
 
        data = of_device_get_match_data(dev);
        if (!data)
@@ -690,8 +681,8 @@ static int k3_dsp_rproc_probe(struct platform_device *pdev)
        if (ret)
                return dev_err_probe(dev, ret, "failed to parse firmware-name property\n");
 
-       rproc = rproc_alloc(dev, dev_name(dev), &k3_dsp_rproc_ops, fw_name,
-                           sizeof(*kproc));
+       rproc = devm_rproc_alloc(dev, dev_name(dev), &k3_dsp_rproc_ops,
+                                fw_name, sizeof(*kproc));
        if (!rproc)
                return -ENOMEM;
 
@@ -706,56 +697,46 @@ static int k3_dsp_rproc_probe(struct platform_device *pdev)
        kproc->dev = dev;
        kproc->data = data;
 
-       kproc->ti_sci = ti_sci_get_by_phandle(np, "ti,sci");
-       if (IS_ERR(kproc->ti_sci)) {
-               ret = dev_err_probe(dev, PTR_ERR(kproc->ti_sci),
-                                   "failed to get ti-sci handle\n");
-               kproc->ti_sci = NULL;
-               goto free_rproc;
-       }
+       kproc->ti_sci = devm_ti_sci_get_by_phandle(dev, "ti,sci");
+       if (IS_ERR(kproc->ti_sci))
+               return dev_err_probe(dev, PTR_ERR(kproc->ti_sci),
+                                    "failed to get ti-sci handle\n");
 
        ret = of_property_read_u32(np, "ti,sci-dev-id", &kproc->ti_sci_id);
-       if (ret) {
-               dev_err_probe(dev, ret, "missing 'ti,sci-dev-id' property\n");
-               goto put_sci;
-       }
+       if (ret)
+               return dev_err_probe(dev, ret, "missing 'ti,sci-dev-id' property\n");
 
        kproc->reset = devm_reset_control_get_exclusive(dev, NULL);
-       if (IS_ERR(kproc->reset)) {
-               ret = dev_err_probe(dev, PTR_ERR(kproc->reset),
-                                   "failed to get reset\n");
-               goto put_sci;
-       }
+       if (IS_ERR(kproc->reset))
+               return dev_err_probe(dev, PTR_ERR(kproc->reset),
+                                    "failed to get reset\n");
 
        kproc->tsp = k3_dsp_rproc_of_get_tsp(dev, kproc->ti_sci);
-       if (IS_ERR(kproc->tsp)) {
-               ret = dev_err_probe(dev, PTR_ERR(kproc->tsp),
-                                   "failed to construct ti-sci proc control\n");
-               goto put_sci;
-       }
+       if (IS_ERR(kproc->tsp))
+               return dev_err_probe(dev, PTR_ERR(kproc->tsp),
+                                    "failed to construct ti-sci proc control\n");
 
        ret = ti_sci_proc_request(kproc->tsp);
        if (ret < 0) {
                dev_err_probe(dev, ret, "ti_sci_proc_request failed\n");
-               goto free_tsp;
+               return ret;
        }
+       ret = devm_add_action_or_reset(dev, k3_dsp_release_tsp, kproc->tsp);
+       if (ret)
+               return ret;
 
        ret = k3_dsp_rproc_of_get_memories(pdev, kproc);
        if (ret)
-               goto release_tsp;
+               return ret;
 
        ret = k3_dsp_reserved_mem_init(kproc);
-       if (ret) {
-               dev_err_probe(dev, ret, "reserved memory init failed\n");
-               goto release_tsp;
-       }
+       if (ret)
+               return dev_err_probe(dev, ret, "reserved memory init failed\n");
 
        ret = kproc->ti_sci->ops.dev_ops.is_on(kproc->ti_sci, kproc->ti_sci_id,
                                               NULL, &p_state);
-       if (ret) {
-               dev_err_probe(dev, ret, "failed to get initial state, mode cannot be determined\n");
-               goto release_mem;
-       }
+       if (ret)
+               return dev_err_probe(dev, ret, "failed to get initial state, mode cannot be determined\n");
 
        /* configure J721E devices for either remoteproc or IPC-only mode */
        if (p_state) {
@@ -779,8 +760,7 @@ static int k3_dsp_rproc_probe(struct platform_device *pdev)
                if (data->uses_lreset) {
                        ret = reset_control_status(kproc->reset);
                        if (ret < 0) {
-                               dev_err_probe(dev, ret, "failed to get reset status\n");
-                               goto release_mem;
+                               return dev_err_probe(dev, ret, "failed to get reset status\n");
                        } else if (ret == 0) {
                                dev_warn(dev, "local reset is deasserted for device\n");
                                k3_dsp_rproc_reset(kproc);
@@ -788,31 +768,13 @@ static int k3_dsp_rproc_probe(struct platform_device *pdev)
                }
        }
 
-       ret = rproc_add(rproc);
-       if (ret) {
-               dev_err_probe(dev, ret, "failed to add register device with remoteproc core\n");
-               goto release_mem;
-       }
+       ret = devm_rproc_add(dev, rproc);
+       if (ret)
+               return dev_err_probe(dev, ret, "failed to add register device with remoteproc core\n");
 
        platform_set_drvdata(pdev, kproc);
 
        return 0;
-
-release_mem:
-       k3_dsp_reserved_mem_exit(kproc);
-release_tsp:
-       ret1 = ti_sci_proc_release(kproc->tsp);
-       if (ret1)
-               dev_err(dev, "failed to release proc (%pe)\n", ERR_PTR(ret1));
-free_tsp:
-       kfree(kproc->tsp);
-put_sci:
-       ret1 = ti_sci_put_handle(kproc->ti_sci);
-       if (ret1)
-               dev_err(dev, "failed to put ti_sci handle (%pe)\n", ERR_PTR(ret1));
-free_rproc:
-       rproc_free(rproc);
-       return ret;
 }
 
 static void k3_dsp_rproc_remove(struct platform_device *pdev)
@@ -824,27 +786,9 @@ static void k3_dsp_rproc_remove(struct platform_device *pdev)
 
        if (rproc->state == RPROC_ATTACHED) {
                ret = rproc_detach(rproc);
-               if (ret) {
-                       /* Note this error path leaks resources */
+               if (ret)
                        dev_err(dev, "failed to detach proc (%pe)\n", ERR_PTR(ret));
-                       return;
-               }
        }
-
-       rproc_del(kproc->rproc);
-
-       ret = ti_sci_proc_release(kproc->tsp);
-       if (ret)
-               dev_err(dev, "failed to release proc (%pe)\n", ERR_PTR(ret));
-
-       kfree(kproc->tsp);
-
-       ret = ti_sci_put_handle(kproc->ti_sci);
-       if (ret)
-               dev_err(dev, "failed to put ti_sci handle (%pe)\n", ERR_PTR(ret));
-
-       k3_dsp_reserved_mem_exit(kproc);
-       rproc_free(kproc->rproc);
 }
 
 static const struct k3_dsp_mem_data c66_mems[] = {