linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema
@ 2025-12-19  4:34 Alexandru Gagniuc
  2025-12-19  4:34 ` [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader Alexandru Gagniuc
                   ` (9 more replies)
  0 siblings, 10 replies; 31+ messages in thread
From: Alexandru Gagniuc @ 2025-12-19  4:34 UTC (permalink / raw)
  To: andersson, mathieu.poirier, krzk+dt, Rob Herring, Conor Dooley,
	Alexandru Gagniuc
  Cc: linux-arm-msm, linux-remoteproc, devicetree, linux-kernel

Convert the QCS404 and IPQ WCSS Peripheral Image Loader bindings to DT
schema. The text bindngs incorrectly implied that IPQ8074 needs only
one qcom,smem-states entry. This is only true for QCS404. IPQ8074
requires both "stop" and "shutdown".

The example is to be added in a subsequent commit that adds the
IPQ9574 binding.

Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>

---
Changes since RFC
 - rename binding from ipq9574 to ipq8074
 - use a real person instead of placeholder as maintainer
 - drop redundant minItems and descriptions
 - merge if: clauses as suggested by Krzysztof
 - various other fixes suggested by Krzysztof

I used my name as a placeholder for the "maintainer" field. Krzysztof
mentioned to get the "SOC maintainer" using get_maintainer. I don't
know how to do that, and I don't see anyone listed for QCS404,
IPQ8074, or IPQ9574. The bindings apply to any of those SOCs.
---
 .../remoteproc/qcom,ipq8074-wcss-pil.yaml     | 156 ++++++++++++++++++
 .../bindings/remoteproc/qcom,q6v5.txt         | 102 ------------
 2 files changed, 156 insertions(+), 102 deletions(-)
 create mode 100644 Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml
 delete mode 100644 Documentation/devicetree/bindings/remoteproc/qcom,q6v5.txt

diff --git a/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml b/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml
new file mode 100644
index 0000000000000..dea46cb9f93fe
--- /dev/null
+++ b/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml
@@ -0,0 +1,156 @@
+# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
+%YAML 1.2
+---
+$id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml#
+$schema: http://devicetree.org/meta-schemas/core.yaml#
+
+title: Qualcomm IPQ WCSS Peripheral Image Loader
+
+maintainers:
+  - Alexandru Gagniuc <mr.nuke.me@gmail.com>
+
+description:
+  The IPQ WCSS peripheral image loader is used to load firmware on the Qualcomm
+  Q6 processor that exposes WiFi-6 devices to the OS via the AHB bus. It is
+  generally used by ath11k to start up the wireless firmware.
+
+properties:
+  compatible:
+    enum:
+      - qcom,ipq8074-wcss-pil
+      - qcom,qcs404-wcss-pil
+
+  reg:
+    maxItems: 2
+
+  reg-names:
+    items:
+      - const: qdsp6
+      - const: rmb
+
+  interrupts:
+    maxItems: 5
+
+  interrupt-names:
+    items:
+      - const: wdog
+      - const: fatal
+      - const: ready
+      - const: handover
+      - const: stop-ack
+
+  resets:
+    maxItems: 3
+
+  reset-names:
+    items:
+      - const: wcss_aon_reset
+      - const: wcss_reset
+      - const: wcss_q6_reset
+
+  clocks:
+    maxItems: 10
+
+  clock-names:
+    maxItems: 10
+
+  cx-supply:
+    description:
+      reference to the regulators used for the booting of the Hexagon core
+
+  memory-region:
+    maxItems: 1
+
+  qcom,halt-regs:
+    $ref: /schemas/types.yaml#/definitions/phandle-array
+    description:
+      A phandle reference to a syscon representing TCSR followed by the three
+      offsets within syscon for q6, wcss and nc halt registers.
+    items:
+      - items:
+          - description: phandle to TCSR_MUTEX registers
+          - description: offset to the Q6 halt register
+          - description: offset to the wcss halt register
+          - description: offset to the nc halt register
+
+  qcom,smem-states:
+    $ref: /schemas/types.yaml#/definitions/phandle-array
+    maxItems: 2
+    description: States used by the AP to signal the remote processor
+
+  qcom,smem-state-names:
+    maxItems: 2
+    description:
+      Names of the states used by the AP to signal the remote processor
+
+  glink-edge:
+    $ref: /schemas/remoteproc/qcom,glink-edge.yaml#
+    description:
+      Qualcomm G-Link subnode which represents communication edge, channels
+      and devices related to the Modem.
+
+required:
+  - compatible
+  - reg
+  - reg-names
+  - interrupts-extended
+  - interrupt-names
+  - memory-region
+  - qcom,halt-regs
+  - qcom,smem-states
+  - qcom,smem-state-names
+
+allOf:
+  - if:
+      properties:
+        compatible:
+          contains:
+            enum:
+              - qcom,ipq8074-wcss-pil
+    then:
+      properties:
+        qcom,smem-states:
+          items:
+            - description: Shutdown Q6
+            - description: Stop Q6
+        qcom,smem-state-names:
+          items:
+            - const: shutdown
+            - const: stop
+        clock-names: false
+        clocks: false
+
+  - if:
+      properties:
+        compatible:
+          contains:
+            enum:
+              - qcom,qcs404-wcss-pil
+    then:
+      properties:
+        qcom,smem-states:
+          maxItems: 1
+        qcom,smem-state-names:
+          items:
+            - const: stop
+        clocks:
+          minItems: 10
+          maxItems: 10
+        clock-names:
+          items:
+            - const: xo
+            - const: gcc_abhs_cbcr
+            - const: gcc_axim_cbcr
+            - const: lcc_ahbfabric_cbc
+            - const: tcsr_lcc_cbc
+            - const: lcc_abhs_cbc
+            - const: lcc_tcm_slave_cbc
+            - const: lcc_abhm_cbc
+            - const: lcc_axim_cbc
+            - const: lcc_bcr_sleep
+      required:
+        - clocks
+        - clock-names
+        - cx-supply
+
+additionalProperties: false
diff --git a/Documentation/devicetree/bindings/remoteproc/qcom,q6v5.txt b/Documentation/devicetree/bindings/remoteproc/qcom,q6v5.txt
deleted file mode 100644
index 573a88b606773..0000000000000
--- a/Documentation/devicetree/bindings/remoteproc/qcom,q6v5.txt
+++ /dev/null
@@ -1,102 +0,0 @@
-Qualcomm Hexagon Peripheral Image Loader
-
-This document defines the binding for a component that loads and boots firmware
-on the Qualcomm Hexagon core.
-
-- compatible:
-	Usage: required
-	Value type: <string>
-	Definition: must be one of:
-		    "qcom,ipq8074-wcss-pil"
-		    "qcom,qcs404-wcss-pil"
-
-- reg:
-	Usage: required
-	Value type: <prop-encoded-array>
-	Definition: must specify the base address and size of the qdsp6 and
-		    rmb register blocks
-
-- reg-names:
-	Usage: required
-	Value type: <stringlist>
-	Definition: must be "q6dsp" and "rmb"
-
-- interrupts-extended:
-	Usage: required
-	Value type: <prop-encoded-array>
-	Definition: reference to the interrupts that match interrupt-names
-
-- interrupt-names:
-	Usage: required
-	Value type: <stringlist>
-	Definition: must be "wdog", "fatal", "ready", "handover", "stop-ack"
-
-- clocks:
-	Usage: required
-	Value type: <phandle>
-	Definition: reference to the clocks that match clock-names
-
-- clock-names:
-	Usage: required
-	Value type: <stringlist>
-	Definition: The clocks needed depend on the compatible string:
-	qcom,ipq8074-wcss-pil:
-		    no clock names required
-	qcom,qcs404-wcss-pil:
-		    must be "xo", "gcc_abhs_cbcr", "gcc_abhs_cbcr",
-		    "gcc_axim_cbcr", "lcc_ahbfabric_cbc", "tcsr_lcc_cbc",
-		    "lcc_abhs_cbc", "lcc_tcm_slave_cbc", "lcc_abhm_cbc",
-		    "lcc_axim_cbc", "lcc_bcr_sleep"
-
-- resets:
-	Usage: required
-	Value type: <phandle>
-	Definition: reference to the list of 3 reset-controllers for the
-		    wcss sub-system
-
-- reset-names:
-	Usage: required
-	Value type: <stringlist>
-	Definition: must be "wcss_aon_reset", "wcss_reset", "wcss_q6_reset"
-		    for the wcss sub-system
-
-- memory-region:
-	Usage: required
-	Value type: <phandle>
-	Definition: reference to wcss reserved-memory region.
-
-For the compatible string below the following supplies are required:
-  "qcom,qcs404-wcss-pil"
-- cx-supply:
-	Usage: required
-	Value type: <phandle>
-	Definition: reference to the regulators to be held on behalf of the
-		    booting of the Hexagon core
-
-- qcom,smem-states:
-	Usage: required
-	Value type: <phandle>
-	Definition: reference to the smem state for requesting the Hexagon to
-		    shut down
-
-- qcom,smem-state-names:
-	Usage: required
-	Value type: <stringlist>
-	Definition: must be "stop"
-
-- qcom,halt-regs:
-	Usage: required
-	Value type: <prop-encoded-array>
-	Definition: a phandle reference to a syscon representing TCSR followed
-		    by the three offsets within syscon for q6, wcss and nc
-		    halt registers.
-
-- memory-region:
-	Usage: required
-	Value type: <phandle>
-	Definition: reference to the reserved-memory for the region
-
-The Hexagon node may also have an subnode named either "smd-edge" or
-"glink-edge" that describes the communication edge, channels and devices
-related to the Hexagon.  See ../soc/qcom/qcom,smd.yaml and
-../soc/qcom/qcom,glink.txt for details on how to describe these.
-- 
2.45.1


^ permalink raw reply related	[flat|nested] 31+ messages in thread

* [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader
  2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
@ 2025-12-19  4:34 ` Alexandru Gagniuc
  2025-12-19  5:37   ` Rob Herring (Arm)
                     ` (2 more replies)
  2025-12-19  4:34 ` [PATCH 3/9] dt-bindings: clock: gcc-ipq9574: add wcss remoteproc clocks Alexandru Gagniuc
                   ` (8 subsequent siblings)
  9 siblings, 3 replies; 31+ messages in thread
From: Alexandru Gagniuc @ 2025-12-19  4:34 UTC (permalink / raw)
  To: andersson, mathieu.poirier, krzk+dt, Rob Herring, Conor Dooley,
	Alexandru Gagniuc
  Cc: linux-arm-msm, linux-remoteproc, devicetree, linux-kernel

Document the IPQ9574 native (non-PAS) WCSS image loader. It is similar
to IPQ8074 WCSS, but requires several new clocks. These clocks must be
enabled by the host in non-PAS mode, and are not optional. Add an
example that uses the "qcom,ipq9574-wcss-pil" binding.

Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
---
 .../remoteproc/qcom,ipq8074-wcss-pil.yaml     | 115 +++++++++++++++++-
 1 file changed, 113 insertions(+), 2 deletions(-)

diff --git a/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml b/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml
index dea46cb9f93fe..a665b704a835f 100644
--- a/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml
+++ b/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml
@@ -18,6 +18,7 @@ properties:
   compatible:
     enum:
       - qcom,ipq8074-wcss-pil
+      - qcom,ipq9574-wcss-pil
       - qcom,qcs404-wcss-pil
 
   reg:
@@ -49,10 +50,10 @@ properties:
       - const: wcss_q6_reset
 
   clocks:
-    maxItems: 10
+    maxItems: 13
 
   clock-names:
-    maxItems: 10
+    maxItems: 13
 
   cx-supply:
     description:
@@ -107,6 +108,7 @@ allOf:
           contains:
             enum:
               - qcom,ipq8074-wcss-pil
+              - qcom,ipq9574-wcss-pil
     then:
       properties:
         qcom,smem-states:
@@ -117,9 +119,47 @@ allOf:
           items:
             - const: shutdown
             - const: stop
+
+  - if:
+      properties:
+        compatible:
+          contains:
+            enum:
+              - qcom,ipq8074-wcss-pil
+    then:
+      properties:
         clock-names: false
         clocks: false
 
+  - if:
+      properties:
+        compatible:
+          contains:
+            enum:
+              - qcom,ipq9574-wcss-pil
+    then:
+      properties:
+        clocks:
+          minItems: 13
+        clock-names:
+          items:
+            - const: anoc_wcss_axi_m
+            - const: wcss_ahb_s
+            - const: wcss_ecahb
+            - const: wcss_acmt
+            - const: wcss_axi_m
+            - const: q6_axim
+            - const: q6_axim2
+            - const: q6_ahb
+            - const: q6_ahb_s
+            - const: q6ss_boot
+            - const: mem_noc_q6_axi
+            - const: wcss_q6_tbu
+            - const: sys_noc_wcss_ahb
+      required:
+        - clocks
+        - clock-names
+
   - if:
       properties:
         compatible:
@@ -154,3 +194,74 @@ allOf:
         - cx-supply
 
 additionalProperties: false
+
+examples:
+  - |
+    #include <dt-bindings/clock/qcom,ipq9574-gcc.h>
+    #include <dt-bindings/interrupt-controller/arm-gic.h>
+    #include <dt-bindings/reset/qcom,ipq9574-gcc.h>
+
+    q6v5_wcss: remoteproc@cd00000 {
+        compatible = "qcom,ipq9574-wcss-pil";
+        reg = <0x0cd00000 0x4040>,
+              <0x004ab000 0x20>;
+        reg-names = "qdsp6", "rmb";
+
+        interrupts-extended = <&intc GIC_SPI 325 IRQ_TYPE_EDGE_RISING>,
+                              <&wcss_smp2p_in 0 IRQ_TYPE_NONE>,
+                              <&wcss_smp2p_in 1 IRQ_TYPE_NONE>,
+                              <&wcss_smp2p_in 2 IRQ_TYPE_NONE>,
+                              <&wcss_smp2p_in 3 IRQ_TYPE_NONE>;
+        interrupt-names = "wdog", "fatal", "ready",
+                          "handover", "stop-ack";
+
+        resets = <&gcc GCC_WCSSAON_RESET>,
+                 <&gcc GCC_WCSS_BCR>,
+                 <&gcc GCC_WCSS_Q6_BCR>;
+        reset-names = "wcss_aon_reset",
+                      "wcss_reset",
+                      "wcss_q6_reset";
+
+        clocks = <&gcc GCC_ANOC_WCSS_AXI_M_CLK>,
+                 <&gcc GCC_Q6_AHB_CLK>,
+                 <&gcc GCC_Q6_AHB_S_CLK>,
+                 <&gcc GCC_Q6_AXIM_CLK>,
+                 <&gcc GCC_Q6SS_BOOT_CLK>,
+                 <&gcc GCC_MEM_NOC_Q6_AXI_CLK>,
+                 <&gcc GCC_SYS_NOC_WCSS_AHB_CLK>,
+                 <&gcc GCC_WCSS_ACMT_CLK>,
+                 <&gcc GCC_WCSS_ECAHB_CLK>,
+                 <&gcc GCC_WCSS_Q6_TBU_CLK>,
+                 <&gcc GCC_WCSS_AHB_S_CLK>,
+                 <&gcc GCC_Q6_AXIM2_CLK>,
+                 <&gcc GCC_WCSS_AXI_M_CLK>;
+
+        clock-names = "anoc_wcss_axi_m",
+                      "q6_ahb",
+                      "q6_ahb_s",
+                      "q6_axim",
+                      "q6ss_boot",
+                      "mem_noc_q6_axi",
+                      "sys_noc_wcss_ahb",
+                      "wcss_acmt",
+                      "wcss_ecahb",
+                      "wcss_q6_tbu",
+                      "q6_axim2",
+                      "wcss_ahb_s",
+                      "wcss_axi_m";
+
+        qcom,halt-regs = <&tcsr 0x18000 0x1b000 0xe000>;
+
+        qcom,smem-states = <&wcss_smp2p_out 0>,
+                           <&wcss_smp2p_out 1>;
+        qcom,smem-state-names = "shutdown",
+                                "stop";
+        memory-region = <&q6_region>;
+
+        glink-edge {
+            interrupts = <GIC_SPI 321 IRQ_TYPE_EDGE_RISING>;
+            label = "rtr";
+            qcom,remote-pid = <1>;
+            mboxes = <&apcs_glb 8>;
+        };
+    };
-- 
2.45.1


^ permalink raw reply related	[flat|nested] 31+ messages in thread

* [PATCH 3/9] dt-bindings: clock: gcc-ipq9574: add wcss remoteproc clocks
  2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
  2025-12-19  4:34 ` [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader Alexandru Gagniuc
@ 2025-12-19  4:34 ` Alexandru Gagniuc
  2025-12-19  4:34 ` [PATCH 4/9] arm64: dts: qcom: ipq9574: add wcss remoteproc nodes Alexandru Gagniuc
                   ` (7 subsequent siblings)
  9 siblings, 0 replies; 31+ messages in thread
From: Alexandru Gagniuc @ 2025-12-19  4:34 UTC (permalink / raw)
  To: andersson, mathieu.poirier, krzk+dt, Michael Turquette,
	Stephen Boyd, Rob Herring, Conor Dooley
  Cc: Alexandru Gagniuc, linux-arm-msm, linux-clk, devicetree,
	linux-kernel

Commit da040d560319 ("dt-bindings: clock: qcom: gcc-ipq9574: remove q6
bring up clock macros") removed these clocks on the idea that Q6
firmware is responsible for clock bringup. That statement seems
incorrect, as these clocks need to be enabled before the Q6 is booted.
Otherwise, the host CPU core that starts the Q6 hangs.

Perhaps the statement meant that the TrustZone firmware will start the
clocks. This only happens in PAS mode. Under native OS loading, the
host needs these clocks, so add them back.

Besides the clocks that were erroneously removed, also add defines for
GCC_WCSS_AHB_S_CLK, GCC_WCSS_AXI_M_CLK, and GCC_Q6_AXIM2_CLK, as all
these clocks are required to operate the remoteproc.

Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
---
 include/dt-bindings/clock/qcom,ipq9574-gcc.h | 22 ++++++++++++++++++++
 1 file changed, 22 insertions(+)

diff --git a/include/dt-bindings/clock/qcom,ipq9574-gcc.h b/include/dt-bindings/clock/qcom,ipq9574-gcc.h
index 0e7c319897f3a..8c74f50a27909 100644
--- a/include/dt-bindings/clock/qcom,ipq9574-gcc.h
+++ b/include/dt-bindings/clock/qcom,ipq9574-gcc.h
@@ -132,8 +132,16 @@
 #define GCC_NSSNOC_SNOC_1_CLK				123
 #define GCC_QDSS_ETR_USB_CLK				124
 #define WCSS_AHB_CLK_SRC				125
+#define GCC_Q6_AHB_CLK					126
+#define GCC_Q6_AHB_S_CLK				127
+#define GCC_WCSS_ECAHB_CLK				128
+#define GCC_WCSS_ACMT_CLK				129
+#define GCC_SYS_NOC_WCSS_AHB_CLK			130
 #define WCSS_AXI_M_CLK_SRC				131
+#define GCC_ANOC_WCSS_AXI_M_CLK				132
 #define QDSS_AT_CLK_SRC					133
+#define GCC_Q6SS_ATBM_CLK				134
+#define GCC_WCSS_DBG_IFC_ATB_CLK			135
 #define GCC_NSSNOC_ATB_CLK				136
 #define GCC_QDSS_AT_CLK					137
 #define GCC_SYS_NOC_AT_CLK				138
@@ -146,18 +154,27 @@
 #define QDSS_TRACECLKIN_CLK_SRC				145
 #define GCC_QDSS_TRACECLKIN_CLK				146
 #define QDSS_TSCTR_CLK_SRC				147
+#define GCC_Q6_TSCTR_1TO2_CLK				148
+#define GCC_WCSS_DBG_IFC_NTS_CLK			149
 #define GCC_QDSS_TSCTR_DIV2_CLK				150
 #define GCC_QDSS_TS_CLK					151
 #define GCC_QDSS_TSCTR_DIV4_CLK				152
 #define GCC_NSS_TS_CLK					153
 #define GCC_QDSS_TSCTR_DIV8_CLK				154
 #define GCC_QDSS_TSCTR_DIV16_CLK			155
+#define GCC_Q6SS_PCLKDBG_CLK				156
+#define GCC_Q6SS_TRIG_CLK				157
+#define GCC_WCSS_DBG_IFC_APB_CLK			158
+#define GCC_WCSS_DBG_IFC_DAPBUS_CLK			159
 #define GCC_QDSS_DAP_CLK				160
 #define GCC_QDSS_APB2JTAG_CLK				161
 #define GCC_QDSS_TSCTR_DIV3_CLK				162
 #define QPIC_IO_MACRO_CLK_SRC				163
 #define GCC_QPIC_IO_MACRO_CLK                           164
 #define Q6_AXI_CLK_SRC					165
+#define GCC_Q6_AXIM_CLK					166
+#define GCC_WCSS_Q6_TBU_CLK				167
+#define GCC_MEM_NOC_Q6_AXI_CLK				168
 #define Q6_AXIM2_CLK_SRC				169
 #define NSSNOC_MEMNOC_BFDCD_CLK_SRC			170
 #define GCC_NSSNOC_MEMNOC_CLK				171
@@ -182,6 +199,7 @@
 #define GCC_UNIPHY2_SYS_CLK				190
 #define GCC_CMN_12GPLL_SYS_CLK				191
 #define GCC_NSSNOC_XO_DCD_CLK				192
+#define GCC_Q6SS_BOOT_CLK				193
 #define UNIPHY_SYS_CLK_SRC				194
 #define NSS_TS_CLK_SRC					195
 #define GCC_ANOC_PCIE0_1LANE_M_CLK			196
@@ -203,4 +221,8 @@
 #define GCC_PCIE2_PIPE_CLK				212
 #define GCC_PCIE3_PIPE_CLK				213
 #define GPLL0_OUT_AUX					214
+#define GCC_WCSS_AHB_S_CLK				215
+#define GCC_WCSS_AXI_M_CLK				216
+#define GCC_Q6_AXIM2_CLK				217
+
 #endif
-- 
2.45.1


^ permalink raw reply related	[flat|nested] 31+ messages in thread

* [PATCH 4/9] arm64: dts: qcom: ipq9574: add wcss remoteproc nodes
  2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
  2025-12-19  4:34 ` [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader Alexandru Gagniuc
  2025-12-19  4:34 ` [PATCH 3/9] dt-bindings: clock: gcc-ipq9574: add wcss remoteproc clocks Alexandru Gagniuc
@ 2025-12-19  4:34 ` Alexandru Gagniuc
  2025-12-19 13:43   ` Konrad Dybcio
  2025-12-19  4:34 ` [PATCH 5/9] clk: qcom: gcc-ipq9574: add wcss remoteproc clocks Alexandru Gagniuc
                   ` (6 subsequent siblings)
  9 siblings, 1 reply; 31+ messages in thread
From: Alexandru Gagniuc @ 2025-12-19  4:34 UTC (permalink / raw)
  To: andersson, mathieu.poirier, krzk+dt, Konrad Dybcio, Rob Herring,
	Conor Dooley
  Cc: Alexandru Gagniuc, linux-arm-msm, devicetree, linux-kernel

The WCSS remoteproc is typically used by ath11k to load wifi firmware
to the Hexagon q6 procesor. Add the nodes required to bring up this
processor.

Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
---
 arch/arm64/boot/dts/qcom/ipq9574.dtsi | 101 ++++++++++++++++++++++++++
 1 file changed, 101 insertions(+)

diff --git a/arch/arm64/boot/dts/qcom/ipq9574.dtsi b/arch/arm64/boot/dts/qcom/ipq9574.dtsi
index 86c9cb9fffc98..56e6f1370d6c3 100644
--- a/arch/arm64/boot/dts/qcom/ipq9574.dtsi
+++ b/arch/arm64/boot/dts/qcom/ipq9574.dtsi
@@ -226,6 +226,37 @@ smem@4aa00000 {
 			hwlocks = <&tcsr_mutex 3>;
 			no-map;
 		};
+
+
+		q6_region: wcnss@4ab00000 {
+			no-map;
+			reg = <0x0 0x4ab00000 0x0 0x02b00000>;
+		};
+	};
+
+	wcss: smp2p-wcss {
+		compatible = "qcom,smp2p";
+		qcom,smem = <435>, <428>;
+
+		interrupt-parent = <&intc>;
+		interrupts = <GIC_SPI 322 IRQ_TYPE_EDGE_RISING>;
+
+		mboxes = <&apcs_glb 9>;
+
+		qcom,local-pid = <0>;
+		qcom,remote-pid = <1>;
+
+		wcss_smp2p_out: master-kernel {
+			qcom,entry-name = "master-kernel";
+			qcom,smp2p-feature-ssr-ack;
+			#qcom,smem-state-cells = <1>;
+		};
+
+		wcss_smp2p_in: slave-kernel {
+			qcom,entry-name = "slave-kernel";
+			interrupt-controller;
+			#interrupt-cells = <2>;
+		};
 	};
 
 	soc: soc@0 {
@@ -903,6 +934,76 @@ frame@b128000 {
 			};
 		};
 
+		q6v5_wcss: remoteproc@cd00000 {
+			compatible = "qcom,ipq9574-wcss-pil";
+			reg = <0x0cd00000 0x4040>,
+			      <0x004ab000 0x20>;
+			reg-names = "qdsp6",
+				    "rmb";
+
+			interrupts-extended = <&intc GIC_SPI 325 IRQ_TYPE_EDGE_RISING>,
+					      <&wcss_smp2p_in 0 IRQ_TYPE_NONE>,
+					      <&wcss_smp2p_in 1 IRQ_TYPE_NONE>,
+					      <&wcss_smp2p_in 2 IRQ_TYPE_NONE>,
+					      <&wcss_smp2p_in 3 IRQ_TYPE_NONE>;
+			interrupt-names = "wdog",
+					  "fatal",
+					  "ready",
+					  "handover",
+					  "stop-ack";
+
+			resets = <&gcc GCC_WCSSAON_RESET>,
+				 <&gcc GCC_WCSS_BCR>,
+				 <&gcc GCC_WCSS_Q6_BCR>;
+			reset-names = "wcss_aon_reset",
+				      "wcss_reset",
+				      "wcss_q6_reset";
+
+			clocks = <&gcc GCC_ANOC_WCSS_AXI_M_CLK>,
+				 <&gcc GCC_Q6_AHB_CLK>,
+				 <&gcc GCC_Q6_AHB_S_CLK>,
+				 <&gcc GCC_Q6_AXIM_CLK>,
+				 <&gcc GCC_Q6SS_BOOT_CLK>,
+				 <&gcc GCC_MEM_NOC_Q6_AXI_CLK>,
+				 <&gcc GCC_SYS_NOC_WCSS_AHB_CLK>,
+				 <&gcc GCC_WCSS_ACMT_CLK>,
+				 <&gcc GCC_WCSS_ECAHB_CLK>,
+				 <&gcc GCC_WCSS_Q6_TBU_CLK>,
+				 <&gcc GCC_WCSS_AHB_S_CLK>,
+				 <&gcc GCC_Q6_AXIM2_CLK>,
+				 <&gcc GCC_WCSS_AXI_M_CLK>;
+
+			clock-names = "anoc_wcss_axi_m",
+				      "q6_ahb",
+				      "q6_ahb_s",
+				      "q6_axim",
+				      "q6ss_boot",
+				      "mem_noc_q6_axi",
+				      "sys_noc_wcss_ahb",
+				      "wcss_acmt",
+				      "wcss_ecahb",
+				      "wcss_q6_tbu",
+				      "q6_axim2",
+				      "wcss_ahb_s",
+				      "wcss_axi_m";
+
+			qcom,halt-regs = <&tcsr 0x18000 0x1b000 0xe000>;
+
+			qcom,smem-states = <&wcss_smp2p_out 0>,
+					   <&wcss_smp2p_out 1>;
+			qcom,smem-state-names = "shutdown",
+						"stop";
+
+			memory-region = <&q6_region>;
+
+			glink-edge {
+				interrupts = <GIC_SPI 321 IRQ_TYPE_EDGE_RISING>;
+				label = "rtr";
+				qcom,remote-pid = <1>;
+				mboxes = <&apcs_glb 8>;
+			};
+		};
+
 		pcie1: pcie@10000000 {
 			compatible = "qcom,pcie-ipq9574";
 			reg = <0x10000000 0xf1d>,
-- 
2.45.1


^ permalink raw reply related	[flat|nested] 31+ messages in thread

* [PATCH 5/9] clk: qcom: gcc-ipq9574: add wcss remoteproc clocks
  2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
                   ` (2 preceding siblings ...)
  2025-12-19  4:34 ` [PATCH 4/9] arm64: dts: qcom: ipq9574: add wcss remoteproc nodes Alexandru Gagniuc
@ 2025-12-19  4:34 ` Alexandru Gagniuc
  2025-12-19  4:34 ` [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574 Alexandru Gagniuc
                   ` (5 subsequent siblings)
  9 siblings, 0 replies; 31+ messages in thread
From: Alexandru Gagniuc @ 2025-12-19  4:34 UTC (permalink / raw)
  To: andersson, mathieu.poirier, krzk+dt, Michael Turquette,
	Stephen Boyd
  Cc: Alexandru Gagniuc, linux-arm-msm, linux-clk, linux-kernel

Commit fa1d525404b6 ("clk: qcom: ipq9574: remove q6 bring up clocks")
removed these clocks on the idea that Q6 firmware is responsible for
clock bringup. That statement seems incorrect, as these clocks need to
be enabled before the Q6 is booted. Otherwise, the host CPU core that
starts the Q6 hangs.

Perhaps the statement meant that the TrustZone firmware will start the
clocks. This only happens in PAS mode. Under native OS loading, the
host needs to enable these clocks, so add them back.

Besides the clocks that were erroneously removed, also add defines for
GCC_WCSS_AHB_S_CLK, GCC_WCSS_AXI_M_CLK, and GCC_Q6_AXIM2_CLK. These
clocks are required in order to operate the remoteproc.

Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
---
 drivers/clk/qcom/gcc-ipq9574.c | 378 +++++++++++++++++++++++++++++++++
 1 file changed, 378 insertions(+)

diff --git a/drivers/clk/qcom/gcc-ipq9574.c b/drivers/clk/qcom/gcc-ipq9574.c
index 6dc86e686de46..aef5ed5cd9f50 100644
--- a/drivers/clk/qcom/gcc-ipq9574.c
+++ b/drivers/clk/qcom/gcc-ipq9574.c
@@ -2659,6 +2659,24 @@ static struct clk_rcg2 system_noc_bfdcd_clk_src = {
 	},
 };
 
+static struct clk_branch gcc_q6ss_boot_clk = {
+	.halt_reg = 0x25080,
+	.halt_check = BRANCH_HALT_SKIP,
+	.clkr = {
+		.enable_reg = 0x25080,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_q6ss_boot_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&system_noc_bfdcd_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
 static struct clk_branch gcc_nssnoc_snoc_clk = {
 	.halt_reg = 0x17028,
 	.clkr = {
@@ -2729,6 +2747,108 @@ static struct clk_rcg2 wcss_ahb_clk_src = {
 	},
 };
 
+static struct clk_branch gcc_q6_ahb_clk = {
+	.halt_reg = 0x25014,
+	.clkr = {
+		.enable_reg = 0x25014,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_q6_ahb_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&wcss_ahb_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_q6_ahb_s_clk = {
+	.halt_reg = 0x25018,
+	.clkr = {
+		.enable_reg = 0x25018,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_q6_ahb_s_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&wcss_ahb_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_wcss_ecahb_clk = {
+	.halt_reg = 0x25058,
+	.clkr = {
+		.enable_reg = 0x25058,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_wcss_ecahb_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&wcss_ahb_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_wcss_acmt_clk = {
+	.halt_reg = 0x2505c,
+	.clkr = {
+		.enable_reg = 0x2505c,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_wcss_acmt_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&wcss_ahb_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+
+static struct clk_branch gcc_wcss_ahb_s_clk = {
+	.halt_reg = 0x25060,
+	.clkr = {
+		.enable_reg = 0x25060,
+		.enable_mask = BIT(0),
+		.hw.init = &(struct clk_init_data) {
+			.name = "gcc_wcss_ahb_s_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+					&wcss_ahb_clk_src.clkr.hw },
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_sys_noc_wcss_ahb_clk = {
+	.halt_reg = 0x2e030,
+	.clkr = {
+		.enable_reg = 0x2e030,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_sys_noc_wcss_ahb_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&wcss_ahb_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
 static const struct freq_tbl ftbl_wcss_axi_m_clk_src[] = {
 	F(24000000, P_XO, 1, 0, 0),
 	F(133333333, P_GPLL0, 6, 0, 0),
@@ -2749,6 +2869,39 @@ static struct clk_rcg2 wcss_axi_m_clk_src = {
 	},
 };
 
+static struct clk_branch gcc_wcss_axi_m_clk = {
+	.halt_reg = 0x25064,
+	.clkr = {
+		.enable_reg = 0x25064,
+		.enable_mask = BIT(0),
+		.hw.init = &(struct clk_init_data) {
+			.name = "gcc_wcss_axi_m_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+					&wcss_axi_m_clk_src.clkr.hw },
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_anoc_wcss_axi_m_clk = {
+	.halt_reg = 0x2e0a8,
+	.clkr = {
+		.enable_reg = 0x2e0a8,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_anoc_wcss_axi_m_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&wcss_axi_m_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
 static const struct freq_tbl ftbl_qdss_at_clk_src[] = {
 	F(240000000, P_GPLL4, 5, 0, 0),
 	{ }
@@ -2767,6 +2920,40 @@ static struct clk_rcg2 qdss_at_clk_src = {
 	},
 };
 
+static struct clk_branch gcc_q6ss_atbm_clk = {
+	.halt_reg = 0x2501c,
+	.clkr = {
+		.enable_reg = 0x2501c,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_q6ss_atbm_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&qdss_at_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_wcss_dbg_ifc_atb_clk = {
+	.halt_reg = 0x2503c,
+	.clkr = {
+		.enable_reg = 0x2503c,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_wcss_dbg_ifc_atb_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&qdss_at_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
 static struct clk_branch gcc_nssnoc_atb_clk = {
 	.halt_reg = 0x17014,
 	.clkr = {
@@ -3003,6 +3190,40 @@ static struct clk_fixed_factor qdss_tsctr_div2_clk_src = {
 	},
 };
 
+static struct clk_branch gcc_q6_tsctr_1to2_clk = {
+	.halt_reg = 0x25020,
+	.clkr = {
+		.enable_reg = 0x25020,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_q6_tsctr_1to2_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&qdss_tsctr_div2_clk_src.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_wcss_dbg_ifc_nts_clk = {
+	.halt_reg = 0x25040,
+	.clkr = {
+		.enable_reg = 0x25040,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_wcss_dbg_ifc_nts_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&qdss_tsctr_div2_clk_src.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
 static struct clk_branch gcc_qdss_tsctr_div2_clk = {
 	.halt_reg = 0x2d044,
 	.clkr = {
@@ -3177,6 +3398,74 @@ static struct clk_branch gcc_qdss_tsctr_div16_clk = {
 	},
 };
 
+static struct clk_branch gcc_q6ss_pclkdbg_clk = {
+	.halt_reg = 0x25024,
+	.clkr = {
+		.enable_reg = 0x25024,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_q6ss_pclkdbg_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&qdss_dap_sync_clk_src.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_q6ss_trig_clk = {
+	.halt_reg = 0x25068,
+	.clkr = {
+		.enable_reg = 0x25068,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_q6ss_trig_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&qdss_dap_sync_clk_src.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_wcss_dbg_ifc_apb_clk = {
+	.halt_reg = 0x25038,
+	.clkr = {
+		.enable_reg = 0x25038,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_wcss_dbg_ifc_apb_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&qdss_dap_sync_clk_src.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_wcss_dbg_ifc_dapbus_clk = {
+	.halt_reg = 0x25044,
+	.clkr = {
+		.enable_reg = 0x25044,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_wcss_dbg_ifc_dapbus_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&qdss_dap_sync_clk_src.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
 static struct clk_branch gcc_qdss_dap_clk = {
 	.halt_reg = 0x2d058,
 	.clkr = {
@@ -3298,6 +3587,58 @@ static struct clk_rcg2 q6_axi_clk_src = {
 	},
 };
 
+static struct clk_branch gcc_q6_axim_clk = {
+	.halt_reg = 0x2500c,
+	.clkr = {
+		.enable_reg = 0x2500c,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_q6_axim_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&q6_axi_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_wcss_q6_tbu_clk = {
+	.halt_reg = 0x12050,
+	.halt_check = BRANCH_HALT_DELAY,
+	.clkr = {
+		.enable_reg = 0xb00c,
+		.enable_mask = BIT(6),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_wcss_q6_tbu_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&q6_axi_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
+static struct clk_branch gcc_mem_noc_q6_axi_clk = {
+	.halt_reg = 0x19010,
+	.clkr = {
+		.enable_reg = 0x19010,
+		.enable_mask = BIT(0),
+		.hw.init = &(const struct clk_init_data) {
+			.name = "gcc_mem_noc_q6_axi_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+				&q6_axi_clk_src.clkr.hw
+			},
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
 static const struct freq_tbl ftbl_q6_axim2_clk_src[] = {
 	F(342857143, P_GPLL4, 3.5, 0, 0),
 	{ }
@@ -3323,6 +3664,22 @@ static struct clk_rcg2 q6_axim2_clk_src = {
 	},
 };
 
+static struct clk_branch gcc_q6_axim2_clk = {
+	.halt_reg = 0x25010,
+	.clkr = {
+		.enable_reg = 0x25010,
+		.enable_mask = BIT(0),
+		.hw.init = &(struct clk_init_data) {
+			.name = "gcc_q6_axim2_clk",
+			.parent_hws = (const struct clk_hw *[]) {
+					&q6_axim2_clk_src.clkr.hw },
+			.num_parents = 1,
+			.flags = CLK_SET_RATE_PARENT,
+			.ops = &clk_branch2_ops,
+		},
+	},
+};
+
 static const struct freq_tbl ftbl_nssnoc_memnoc_bfdcd_clk_src[] = {
 	F(533333333, P_GPLL0, 1.5, 0, 0),
 	{ }
@@ -3847,8 +4204,18 @@ static struct clk_regmap *gcc_ipq9574_clks[] = {
 	[GCC_NSSNOC_SNOC_1_CLK] = &gcc_nssnoc_snoc_1_clk.clkr,
 	[GCC_QDSS_ETR_USB_CLK] = &gcc_qdss_etr_usb_clk.clkr,
 	[WCSS_AHB_CLK_SRC] = &wcss_ahb_clk_src.clkr,
+	[GCC_Q6_AHB_CLK] = &gcc_q6_ahb_clk.clkr,
+	[GCC_Q6_AHB_S_CLK] = &gcc_q6_ahb_s_clk.clkr,
+	[GCC_WCSS_ECAHB_CLK] = &gcc_wcss_ecahb_clk.clkr,
+	[GCC_WCSS_ACMT_CLK] = &gcc_wcss_acmt_clk.clkr,
+	[GCC_WCSS_AHB_S_CLK] = &gcc_wcss_ahb_s_clk.clkr,
+	[GCC_SYS_NOC_WCSS_AHB_CLK] = &gcc_sys_noc_wcss_ahb_clk.clkr,
 	[WCSS_AXI_M_CLK_SRC] = &wcss_axi_m_clk_src.clkr,
+	[GCC_WCSS_AXI_M_CLK] = &gcc_wcss_axi_m_clk.clkr,
+	[GCC_ANOC_WCSS_AXI_M_CLK] = &gcc_anoc_wcss_axi_m_clk.clkr,
 	[QDSS_AT_CLK_SRC] = &qdss_at_clk_src.clkr,
+	[GCC_Q6SS_ATBM_CLK] = &gcc_q6ss_atbm_clk.clkr,
+	[GCC_WCSS_DBG_IFC_ATB_CLK] = &gcc_wcss_dbg_ifc_atb_clk.clkr,
 	[GCC_NSSNOC_ATB_CLK] = &gcc_nssnoc_atb_clk.clkr,
 	[GCC_QDSS_AT_CLK] = &gcc_qdss_at_clk.clkr,
 	[GCC_SYS_NOC_AT_CLK] = &gcc_sys_noc_at_clk.clkr,
@@ -3861,19 +4228,29 @@ static struct clk_regmap *gcc_ipq9574_clks[] = {
 	[QDSS_TRACECLKIN_CLK_SRC] = &qdss_traceclkin_clk_src.clkr,
 	[GCC_QDSS_TRACECLKIN_CLK] = &gcc_qdss_traceclkin_clk.clkr,
 	[QDSS_TSCTR_CLK_SRC] = &qdss_tsctr_clk_src.clkr,
+	[GCC_Q6_TSCTR_1TO2_CLK] = &gcc_q6_tsctr_1to2_clk.clkr,
+	[GCC_WCSS_DBG_IFC_NTS_CLK] = &gcc_wcss_dbg_ifc_nts_clk.clkr,
 	[GCC_QDSS_TSCTR_DIV2_CLK] = &gcc_qdss_tsctr_div2_clk.clkr,
 	[GCC_QDSS_TS_CLK] = &gcc_qdss_ts_clk.clkr,
 	[GCC_QDSS_TSCTR_DIV4_CLK] = &gcc_qdss_tsctr_div4_clk.clkr,
 	[GCC_NSS_TS_CLK] = &gcc_nss_ts_clk.clkr,
 	[GCC_QDSS_TSCTR_DIV8_CLK] = &gcc_qdss_tsctr_div8_clk.clkr,
 	[GCC_QDSS_TSCTR_DIV16_CLK] = &gcc_qdss_tsctr_div16_clk.clkr,
+	[GCC_Q6SS_PCLKDBG_CLK] = &gcc_q6ss_pclkdbg_clk.clkr,
+	[GCC_Q6SS_TRIG_CLK] = &gcc_q6ss_trig_clk.clkr,
+	[GCC_WCSS_DBG_IFC_APB_CLK] = &gcc_wcss_dbg_ifc_apb_clk.clkr,
+	[GCC_WCSS_DBG_IFC_DAPBUS_CLK] = &gcc_wcss_dbg_ifc_dapbus_clk.clkr,
 	[GCC_QDSS_DAP_CLK] = &gcc_qdss_dap_clk.clkr,
 	[GCC_QDSS_APB2JTAG_CLK] = &gcc_qdss_apb2jtag_clk.clkr,
 	[GCC_QDSS_TSCTR_DIV3_CLK] = &gcc_qdss_tsctr_div3_clk.clkr,
 	[QPIC_IO_MACRO_CLK_SRC] = &qpic_io_macro_clk_src.clkr,
 	[GCC_QPIC_IO_MACRO_CLK] = &gcc_qpic_io_macro_clk.clkr,
 	[Q6_AXI_CLK_SRC] = &q6_axi_clk_src.clkr,
+	[GCC_Q6_AXIM_CLK] = &gcc_q6_axim_clk.clkr,
+	[GCC_WCSS_Q6_TBU_CLK] = &gcc_wcss_q6_tbu_clk.clkr,
+	[GCC_MEM_NOC_Q6_AXI_CLK] = &gcc_mem_noc_q6_axi_clk.clkr,
 	[Q6_AXIM2_CLK_SRC] = &q6_axim2_clk_src.clkr,
+	[GCC_Q6_AXIM2_CLK] = &gcc_q6_axim2_clk.clkr,
 	[NSSNOC_MEMNOC_BFDCD_CLK_SRC] = &nssnoc_memnoc_bfdcd_clk_src.clkr,
 	[GCC_NSSNOC_MEMNOC_CLK] = &gcc_nssnoc_memnoc_clk.clkr,
 	[GCC_NSSNOC_MEM_NOC_1_CLK] = &gcc_nssnoc_mem_noc_1_clk.clkr,
@@ -3896,6 +4273,7 @@ static struct clk_regmap *gcc_ipq9574_clks[] = {
 	[GCC_UNIPHY1_SYS_CLK] = &gcc_uniphy1_sys_clk.clkr,
 	[GCC_UNIPHY2_SYS_CLK] = &gcc_uniphy2_sys_clk.clkr,
 	[GCC_CMN_12GPLL_SYS_CLK] = &gcc_cmn_12gpll_sys_clk.clkr,
+	[GCC_Q6SS_BOOT_CLK] = &gcc_q6ss_boot_clk.clkr,
 	[UNIPHY_SYS_CLK_SRC] = &uniphy_sys_clk_src.clkr,
 	[NSS_TS_CLK_SRC] = &nss_ts_clk_src.clkr,
 	[GCC_ANOC_PCIE0_1LANE_M_CLK] = &gcc_anoc_pcie0_1lane_m_clk.clkr,
-- 
2.45.1


^ permalink raw reply related	[flat|nested] 31+ messages in thread

* [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574
  2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
                   ` (3 preceding siblings ...)
  2025-12-19  4:34 ` [PATCH 5/9] clk: qcom: gcc-ipq9574: add wcss remoteproc clocks Alexandru Gagniuc
@ 2025-12-19  4:34 ` Alexandru Gagniuc
  2025-12-19 13:20   ` Konrad Dybcio
  2025-12-19  4:34 ` [PATCH 7/9] remoteproc: qcom_q6v5_wcss: support m3 firmware Alexandru Gagniuc
                   ` (4 subsequent siblings)
  9 siblings, 1 reply; 31+ messages in thread
From: Alexandru Gagniuc @ 2025-12-19  4:34 UTC (permalink / raw)
  To: andersson, mathieu.poirier, krzk+dt, Philipp Zabel
  Cc: Alexandru Gagniuc, linux-arm-msm, linux-remoteproc, linux-kernel

Q6 based firmware loading is also present on IPQ9574, when coupled
with a wifi-6 device, such as QCN5024. Populate driver data for
IPQ9574 with values from the downstream 5.4 kerrnel.

Add the new sequences for the WCSS reset and stop. The downstream
5.4 kernel calls these "Q6V7", so keep the name. This is still worth
using with the "q6v5" driver because all other parts of the driver
can be seamlessly reused.

The IPQ9574 uses two sets of clocks. the first, dubbed "q6_clocks"
must be enabled before the Q6 is started by writing the Q6SS_RST_EVB
register. The second set of clocks, "clks" should only be enabled
after the Q6 is placed out of reset. Otherwise, the host CPU core that
tries to start the remoteproc will hang.

The downstream kernel had a funny comment, "Pray god and wait for
reset to complete", which I decided to keep for entertainment value.

Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
---
 drivers/remoteproc/qcom_q6v5_wcss.c | 241 +++++++++++++++++++++++++++-
 1 file changed, 234 insertions(+), 7 deletions(-)

diff --git a/drivers/remoteproc/qcom_q6v5_wcss.c b/drivers/remoteproc/qcom_q6v5_wcss.c
index c27200159a88a..b62e97c92d058 100644
--- a/drivers/remoteproc/qcom_q6v5_wcss.c
+++ b/drivers/remoteproc/qcom_q6v5_wcss.c
@@ -31,8 +31,13 @@
 #define Q6SS_MEM_PWR_CTL		0x0B0
 #define Q6SS_STRAP_ACC			0x110
 #define Q6SS_CGC_OVERRIDE		0x034
+#define Q6SS_BOOT_CORE_START		0x400
+#define Q6SS_BOOT_CMD                   0x404
+#define Q6SS_BOOT_STATUS		0x408
 #define Q6SS_BCR_REG			0x6000
 
+#define Q6SS_TIMEOUT_US         1000
+
 /* AXI Halt Register Offsets */
 #define AXI_HALTREQ_REG			0x0
 #define AXI_HALTACK_REG			0x4
@@ -67,6 +72,7 @@
 #define HALT_CHECK_MAX_LOOPS		200
 #define Q6SS_XO_CBCR		GENMASK(5, 3)
 #define Q6SS_SLEEP_CBCR		GENMASK(5, 2)
+#define Q6SS_CORE_CBCR		BIT(5)
 
 /* Q6SS config/status registers */
 #define TCSR_GLOBAL_CFG0	0x0
@@ -77,9 +83,11 @@
 #define Q6SS_RST_EVB		0x10
 
 #define BHS_EN_REST_ACK		BIT(0)
+#define WCSS_HM_RET		BIT(1)
 #define SSCAON_ENABLE		BIT(13)
 #define SSCAON_BUS_EN		BIT(15)
 #define SSCAON_BUS_MUX_MASK	GENMASK(18, 16)
+#define SSCAON_MASK             GENMASK(17, 15)
 
 #define MEM_BANKS		19
 #define TCSR_WCSS_CLK_MASK	0x1F
@@ -88,6 +96,7 @@
 #define MAX_HALT_REG		4
 enum {
 	WCSS_IPQ8074,
+	WCSS_IPQ9574,
 	WCSS_QCS404,
 };
 
@@ -128,6 +137,12 @@ struct q6v5_wcss {
 	struct clk *qdsp6ss_xo_cbcr;
 	struct clk *qdsp6ss_core_gfmux;
 	struct clk *lcc_bcr_sleep;
+	struct clk_bulk_data *clks;
+	/* clocks that must be started before the Q6 is booted */
+	struct clk_bulk_data *q6_clks;
+	int num_clks;
+	int num_q6_clks;
+
 	struct regulator *cx_supply;
 	struct qcom_sysmon *sysmon;
 
@@ -236,6 +251,87 @@ static int q6v5_wcss_reset(struct q6v5_wcss *wcss)
 	return 0;
 }
 
+static int q6v7_wcss_reset(struct q6v5_wcss *wcss, struct rproc *rproc)
+{
+	int ret;
+	u32 val;
+
+	/*1. Set TCSR GLOBAL CFG1*/
+	ret = regmap_update_bits(wcss->halt_map,
+				 wcss->halt_nc + TCSR_GLOBAL_CFG1,
+				 0xff00, 0x1100);
+	if (ret) {
+		dev_err(wcss->dev, "TCSE_GLOBAL_CFG1 failed\n");
+		return ret;
+	}
+
+	/* Enable Q6 clocks */
+	ret = clk_bulk_prepare_enable(wcss->num_q6_clks, wcss->q6_clks);
+	if (ret) {
+		dev_err(wcss->dev, "failed to enable clocks, err=%d\n", ret);
+		return ret;
+	};
+
+	/* Write bootaddr to EVB so that Q6WCSS will jump there after reset */
+	writel(rproc->bootaddr >> 4, wcss->reg_base + Q6SS_RST_EVB);
+
+	/*2. Deassert AON Reset */
+	ret = reset_control_deassert(wcss->wcss_aon_reset);
+	if (ret) {
+		dev_err(wcss->dev, "wcss_aon_reset failed\n");
+		clk_bulk_disable_unprepare(wcss->num_clks, wcss->clks);
+		return ret;
+	}
+
+	/*8. Set mpm configs*/
+	/*set CFG[18:15]=1*/
+	val = readl(wcss->rmb_base + SSCAON_CONFIG);
+	val &= ~SSCAON_MASK;
+	val |= SSCAON_BUS_EN;
+	writel(val, wcss->rmb_base + SSCAON_CONFIG);
+
+	/*9. Wait for SSCAON_STATUS */
+	ret = readl_poll_timeout(wcss->rmb_base + SSCAON_STATUS,
+				 val, (val & 0xffff) == 0x10, 1000,
+				 Q6SS_TIMEOUT_US * 1000);
+	if (ret) {
+		dev_err(wcss->dev, " Boot Error, SSCAON=0x%08X\n", val);
+		return ret;
+	}
+
+	/*3. BHS require xo cbcr to be enabled */
+	val = readl(wcss->reg_base + Q6SS_XO_CBCR);
+	val |= 0x1;
+	writel(val, wcss->reg_base + Q6SS_XO_CBCR);
+
+	/*4. Enable core cbcr*/
+	val = readl(wcss->reg_base + Q6SS_CORE_CBCR);
+	val |= 0x1;
+	writel(val, wcss->reg_base + Q6SS_CORE_CBCR);
+
+	/*5. Enable sleep cbcr*/
+	val = readl(wcss->reg_base + Q6SS_SLEEP_CBCR);
+	val |= 0x1;
+	writel(val, wcss->reg_base + Q6SS_SLEEP_CBCR);
+
+	/*6. Boot core start */
+	writel(0x1, wcss->reg_base + Q6SS_BOOT_CORE_START);
+	writel(0x1, wcss->reg_base + Q6SS_BOOT_CMD);
+
+	/*7. Pray god and wait for reset to complete*/
+	ret = readl_poll_timeout(wcss->reg_base + Q6SS_BOOT_STATUS, val,
+				 (val & 0x01), 20000, 1000);
+
+	/* Enable non-Q6 clocks */
+	ret = clk_bulk_prepare_enable(wcss->num_clks, wcss->clks);
+	if (ret) {
+		dev_err(wcss->dev, "failed to enable clocks, err=%d\n", ret);
+		return ret;
+	};
+
+	return 0;
+}
+
 static int q6v5_wcss_start(struct rproc *rproc)
 {
 	struct q6v5_wcss *wcss = rproc->priv;
@@ -270,10 +366,20 @@ static int q6v5_wcss_start(struct rproc *rproc)
 	if (ret)
 		goto wcss_q6_reset;
 
-	/* Write bootaddr to EVB so that Q6WCSS will jump there after reset */
-	writel(rproc->bootaddr >> 4, wcss->reg_base + Q6SS_RST_EVB);
+	switch (wcss->version) {
+	case WCSS_QCS404:
+	case WCSS_IPQ8074:
+		/* Write bootaddr to EVB so that Q6WCSS will jump there after
+		 * reset.
+		 */
+		writel(rproc->bootaddr >> 4, wcss->reg_base + Q6SS_RST_EVB);
+		ret = q6v5_wcss_reset(wcss);
+		break;
+	case WCSS_IPQ9574:
+		ret = q6v7_wcss_reset(wcss, rproc);
+		break;
+	}
 
-	ret = q6v5_wcss_reset(wcss);
 	if (ret)
 		goto wcss_q6_reset;
 
@@ -638,6 +744,41 @@ static int q6v5_wcss_powerdown(struct q6v5_wcss *wcss)
 	return 0;
 }
 
+static int q6v7_wcss_powerdown(struct q6v5_wcss *wcss)
+{
+	uint32_t val;
+	int ret;
+
+	q6v5_wcss_halt_axi_port(wcss, wcss->halt_map, wcss->halt_wcss);
+
+	val = readl(wcss->rmb_base + SSCAON_CONFIG);
+	val &= ~SSCAON_MASK;
+	val |= SSCAON_BUS_EN;
+	writel(val, wcss->rmb_base + SSCAON_CONFIG);
+
+	val |= WCSS_HM_RET;
+	writel(val, wcss->rmb_base + SSCAON_CONFIG);
+
+	ret = readl_poll_timeout(wcss->rmb_base + SSCAON_STATUS,
+				 val, (val & 0xffff) == 0x400, 1000,
+				 HALT_CHECK_MAX_LOOPS);
+	if (ret) {
+		dev_err(wcss->dev,
+			"can't get SSCAON_STATUS rc:%d)\n", ret);
+		return ret;
+	}
+
+	usleep_range(2000, 4000);
+
+	reset_control_assert(wcss->wcss_aon_reset);
+
+	val = readl(wcss->rmb_base + SSCAON_CONFIG);
+	val &= ~WCSS_HM_RET;
+	writel(val, wcss->rmb_base + SSCAON_CONFIG);
+
+	return 0;
+}
+
 static int q6v5_q6_powerdown(struct q6v5_wcss *wcss)
 {
 	int ret;
@@ -705,6 +846,25 @@ static int q6v5_q6_powerdown(struct q6v5_wcss *wcss)
 	return 0;
 }
 
+static void q6v7_q6_powerdown(struct q6v5_wcss *wcss)
+{
+	uint32_t val;
+
+	q6v5_wcss_halt_axi_port(wcss, wcss->halt_map, wcss->halt_q6);
+
+	/* Disable Q6 Core clock -- we don't know what bit 0 means */
+	val = readl(wcss->reg_base + Q6SS_GFMUX_CTL_REG);
+	val &= ~BIT(0);
+	writel(val, wcss->reg_base + Q6SS_GFMUX_CTL_REG);
+
+	clk_bulk_disable_unprepare(wcss->num_clks, wcss->clks);
+	clk_bulk_disable_unprepare(wcss->num_q6_clks, wcss->q6_clks);
+
+	reset_control_assert(wcss->wcss_q6_reset);
+	usleep_range(1000, 2000);
+	reset_control_assert(wcss->wcss_reset);
+}
+
 static int q6v5_wcss_stop(struct rproc *rproc)
 {
 	struct q6v5_wcss *wcss = rproc->priv;
@@ -719,11 +879,21 @@ static int q6v5_wcss_stop(struct rproc *rproc)
 		}
 	}
 
-	if (wcss->version == WCSS_QCS404) {
+	switch (wcss->version) {
+	case WCSS_QCS404:
 		ret = q6v5_qcs404_wcss_shutdown(wcss);
 		if (ret)
 			return ret;
-	} else {
+		break;
+	case WCSS_IPQ9574:
+		ret = q6v7_wcss_powerdown(wcss);
+		if (ret)
+			return ret;
+
+		q6v7_q6_powerdown(wcss);
+
+		break;
+	default:
 		ret = q6v5_wcss_powerdown(wcss);
 		if (ret)
 			return ret;
@@ -732,6 +902,7 @@ static int q6v5_wcss_stop(struct rproc *rproc)
 		ret = q6v5_q6_powerdown(wcss);
 		if (ret)
 			return ret;
+		break;
 	}
 
 	qcom_q6v5_unprepare(&wcss->q6v5);
@@ -838,7 +1009,9 @@ static int q6v5_wcss_init_mmio(struct q6v5_wcss *wcss,
 	if (!wcss->reg_base)
 		return -ENOMEM;
 
-	if (wcss->version == WCSS_IPQ8074) {
+	switch (wcss->version) {
+	case WCSS_IPQ8074:
+	case WCSS_IPQ9574:
 		wcss->rmb_base = devm_platform_ioremap_resource_byname(pdev, "rmb");
 		if (IS_ERR(wcss->rmb_base))
 			return PTR_ERR(wcss->rmb_base);
@@ -965,6 +1138,43 @@ static int q6v5_wcss_init_regulator(struct q6v5_wcss *wcss)
 	return 0;
 }
 
+static int ipq9574_init_clocks(struct q6v5_wcss *wcss)
+{
+	static const char *const q6_clks[] = {
+		"anoc_wcss_axi_m", "q6_ahb", "q6_ahb_s", "q6_axim", "q6ss_boot",
+		"mem_noc_q6_axi", "sys_noc_wcss_ahb", "wcss_acmt", "wcss_ecahb",
+		"wcss_q6_tbu" };
+	static const char *const clks[] = {
+		"q6_axim2", "wcss_ahb_s", "wcss_axi_m" };
+	int i, ret;
+
+	wcss->num_clks = ARRAY_SIZE(clks);
+	wcss->num_q6_clks = ARRAY_SIZE(q6_clks);
+
+	wcss->q6_clks = devm_kcalloc(wcss->dev, wcss->num_q6_clks,
+				     sizeof(*wcss->q6_clks), GFP_KERNEL);
+	if (!wcss->q6_clks)
+		return -ENOMEM;
+
+	wcss->clks = devm_kcalloc(wcss->dev, wcss->num_clks,
+				  sizeof(*wcss->clks), GFP_KERNEL);
+	if (!wcss->clks)
+		return -ENOMEM;
+
+	for (i = 0; i < wcss->num_q6_clks; i++)
+		wcss->q6_clks[i].id = q6_clks[i];
+
+	for (i = 0; i < wcss->num_clks; i++)
+		wcss->clks[i].id = clks[i];
+
+	ret = devm_clk_bulk_get(wcss->dev, wcss->num_q6_clks, wcss->q6_clks);
+	if (ret < 0)
+		return ret;
+
+	return devm_clk_bulk_get(wcss->dev, wcss->num_clks, wcss->clks);
+}
+
+
 static int q6v5_wcss_probe(struct platform_device *pdev)
 {
 	const struct wcss_data *desc;
@@ -997,7 +1207,8 @@ static int q6v5_wcss_probe(struct platform_device *pdev)
 	if (ret)
 		return ret;
 
-	if (wcss->version == WCSS_QCS404) {
+	switch (wcss->version) {
+	case WCSS_QCS404:
 		ret = q6v5_wcss_init_clock(wcss);
 		if (ret)
 			return ret;
@@ -1005,6 +1216,11 @@ static int q6v5_wcss_probe(struct platform_device *pdev)
 		ret = q6v5_wcss_init_regulator(wcss);
 		if (ret)
 			return ret;
+		break;
+	case WCSS_IPQ9574:
+		ret = ipq9574_init_clocks(wcss);
+		if (ret)
+			return ret;
 	}
 
 	ret = q6v5_wcss_init_reset(wcss, desc);
@@ -1067,6 +1283,16 @@ static const struct wcss_data wcss_ipq8074_res_init = {
 	.requires_force_stop = true,
 };
 
+static const struct wcss_data wcss_ipq9574_res_init = {
+	.firmware_name = "IPQ9574/q6_fw.mdt",
+	.version = WCSS_IPQ9574,
+	.crash_reason_smem = WCSS_CRASH_REASON,
+	.aon_reset_required = true,
+	.ssr_name = "q6wcss",
+	.ops = &q6v5_wcss_ipq8074_ops,
+	.requires_force_stop = true,
+};
+
 static const struct wcss_data wcss_qcs404_res_init = {
 	.crash_reason_smem = WCSS_CRASH_REASON,
 	.firmware_name = "wcnss.mdt",
@@ -1082,6 +1308,7 @@ static const struct wcss_data wcss_qcs404_res_init = {
 
 static const struct of_device_id q6v5_wcss_of_match[] = {
 	{ .compatible = "qcom,ipq8074-wcss-pil", .data = &wcss_ipq8074_res_init },
+	{ .compatible = "qcom,ipq9574-wcss-pil", .data = &wcss_ipq9574_res_init },
 	{ .compatible = "qcom,qcs404-wcss-pil", .data = &wcss_qcs404_res_init },
 	{ },
 };
-- 
2.45.1


^ permalink raw reply related	[flat|nested] 31+ messages in thread

* [PATCH 7/9] remoteproc: qcom_q6v5_wcss: support m3 firmware
  2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
                   ` (4 preceding siblings ...)
  2025-12-19  4:34 ` [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574 Alexandru Gagniuc
@ 2025-12-19  4:34 ` Alexandru Gagniuc
  2025-12-19 13:29   ` Konrad Dybcio
  2025-12-19  4:34 ` [PATCH 8/9] remoteproc: qcom_q6v5_wcss: drop unused clocks from q6v5 struct Alexandru Gagniuc
                   ` (3 subsequent siblings)
  9 siblings, 1 reply; 31+ messages in thread
From: Alexandru Gagniuc @ 2025-12-19  4:34 UTC (permalink / raw)
  To: andersson, mathieu.poirier, krzk+dt
  Cc: Alexandru Gagniuc, linux-arm-msm, linux-remoteproc, linux-kernel

IPQ8074, IPQ6018, and IPQ9574 support an m3 firmware image in addtion
to the q6 firmware. The firmware releases from qcom provide both q6
and m3 firmware for these SoCs. Support loading the m3 firmware image.

Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
---
 drivers/remoteproc/qcom_q6v5_wcss.c | 44 +++++++++++++++++++++++++----
 1 file changed, 39 insertions(+), 5 deletions(-)

diff --git a/drivers/remoteproc/qcom_q6v5_wcss.c b/drivers/remoteproc/qcom_q6v5_wcss.c
index b62e97c92d058..265010c5c82cb 100644
--- a/drivers/remoteproc/qcom_q6v5_wcss.c
+++ b/drivers/remoteproc/qcom_q6v5_wcss.c
@@ -101,7 +101,8 @@ enum {
 };
 
 struct wcss_data {
-	const char *firmware_name;
+	const char *q6_firmware_name;
+	const char *m3_firmware_name;
 	unsigned int crash_reason_smem;
 	u32 version;
 	bool aon_reset_required;
@@ -161,6 +162,7 @@ struct q6v5_wcss {
 	unsigned int crash_reason_smem;
 	u32 version;
 	bool requires_force_stop;
+	const char *m3_firmware_name;
 
 	struct qcom_rproc_glink glink_subdev;
 	struct qcom_rproc_pdm pdm_subdev;
@@ -922,11 +924,40 @@ static void *q6v5_wcss_da_to_va(struct rproc *rproc, u64 da, size_t len, bool *i
 	return wcss->mem_region + offset;
 }
 
+static int q6v5_wcss_load_aux(struct q6v5_wcss *wcss, const char *fw_name)
+{
+	const struct firmware *extra_fw;
+	int ret;
+
+	dev_info(wcss->dev, "loading additional firmware image %s\n", fw_name);
+
+	ret = request_firmware(&extra_fw, fw_name, wcss->dev);
+	if (ret)
+		return 0;
+
+	ret = qcom_mdt_load_no_init(wcss->dev, extra_fw, fw_name,
+				    wcss->mem_region, wcss->mem_phys,
+				    wcss->mem_size, &wcss->mem_reloc);
+
+	release_firmware(extra_fw);
+
+	if (ret)
+		dev_err(wcss->dev, "can't load %s\n", fw_name);
+
+	return ret;
+}
+
 static int q6v5_wcss_load(struct rproc *rproc, const struct firmware *fw)
 {
 	struct q6v5_wcss *wcss = rproc->priv;
 	int ret;
 
+	if (wcss->m3_firmware_name) {
+		ret = q6v5_wcss_load_aux(wcss, wcss->m3_firmware_name);
+		if (ret)
+			return ret;
+	}
+
 	ret = qcom_mdt_load_no_init(wcss->dev, fw, rproc->firmware,
 				    wcss->mem_region, wcss->mem_phys,
 				    wcss->mem_size, &wcss->mem_reloc);
@@ -1187,7 +1218,7 @@ static int q6v5_wcss_probe(struct platform_device *pdev)
 		return -EINVAL;
 
 	rproc = devm_rproc_alloc(&pdev->dev, pdev->name, desc->ops,
-				 desc->firmware_name, sizeof(*wcss));
+				 desc->q6_firmware_name, sizeof(*wcss));
 	if (!rproc) {
 		dev_err(&pdev->dev, "failed to allocate rproc\n");
 		return -ENOMEM;
@@ -1198,6 +1229,7 @@ static int q6v5_wcss_probe(struct platform_device *pdev)
 
 	wcss->version = desc->version;
 	wcss->requires_force_stop = desc->requires_force_stop;
+	wcss->m3_firmware_name = desc->m3_firmware_name;
 
 	ret = q6v5_wcss_init_mmio(wcss, pdev);
 	if (ret)
@@ -1275,7 +1307,8 @@ static void q6v5_wcss_remove(struct platform_device *pdev)
 }
 
 static const struct wcss_data wcss_ipq8074_res_init = {
-	.firmware_name = "IPQ8074/q6_fw.mdt",
+	.q6_firmware_name = "IPQ8074/q6_fw.mdt",
+	.m3_firmware_name = "IPQ8074/m3_fw.mdt",
 	.crash_reason_smem = WCSS_CRASH_REASON,
 	.aon_reset_required = true,
 	.wcss_q6_reset_required = true,
@@ -1284,7 +1317,8 @@ static const struct wcss_data wcss_ipq8074_res_init = {
 };
 
 static const struct wcss_data wcss_ipq9574_res_init = {
-	.firmware_name = "IPQ9574/q6_fw.mdt",
+	.q6_firmware_name = "IPQ9574/q6_fw.mdt",
+	.m3_firmware_name = "IPQ9574/m3_fw.mdt",
 	.version = WCSS_IPQ9574,
 	.crash_reason_smem = WCSS_CRASH_REASON,
 	.aon_reset_required = true,
@@ -1295,7 +1329,7 @@ static const struct wcss_data wcss_ipq9574_res_init = {
 
 static const struct wcss_data wcss_qcs404_res_init = {
 	.crash_reason_smem = WCSS_CRASH_REASON,
-	.firmware_name = "wcnss.mdt",
+	.q6_firmware_name = "wcnss.mdt",
 	.version = WCSS_QCS404,
 	.aon_reset_required = false,
 	.wcss_q6_reset_required = false,
-- 
2.45.1


^ permalink raw reply related	[flat|nested] 31+ messages in thread

* [PATCH 8/9] remoteproc: qcom_q6v5_wcss: drop unused clocks from q6v5 struct
  2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
                   ` (5 preceding siblings ...)
  2025-12-19  4:34 ` [PATCH 7/9] remoteproc: qcom_q6v5_wcss: support m3 firmware Alexandru Gagniuc
@ 2025-12-19  4:34 ` Alexandru Gagniuc
  2025-12-19 13:31   ` Konrad Dybcio
  2025-12-19  4:34 ` [PATCH 9/9] remoteproc: qcom_q6v5_wcss: use bulk clk API for q6 clocks in QCS404 Alexandru Gagniuc
                   ` (2 subsequent siblings)
  9 siblings, 1 reply; 31+ messages in thread
From: Alexandru Gagniuc @ 2025-12-19  4:34 UTC (permalink / raw)
  To: andersson, mathieu.poirier, krzk+dt, Gokul Sriram Palanisamy,
	Govind Singh
  Cc: Alexandru Gagniuc, linux-arm-msm, linux-remoteproc, linux-kernel

Three of the clocks from struct q6v5_wcss are not populated, and are
not used. Remove them.

Fixes: 0af65b9b915e ("remoteproc: qcom: wcss: Add non pas wcss Q6 support for QCS404")

Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
---
 drivers/remoteproc/qcom_q6v5_wcss.c | 3 ---
 1 file changed, 3 deletions(-)

diff --git a/drivers/remoteproc/qcom_q6v5_wcss.c b/drivers/remoteproc/qcom_q6v5_wcss.c
index 265010c5c82cb..bcfd79b12fde9 100644
--- a/drivers/remoteproc/qcom_q6v5_wcss.c
+++ b/drivers/remoteproc/qcom_q6v5_wcss.c
@@ -133,10 +133,7 @@ struct q6v5_wcss {
 	struct clk *ahbs_cbcr;
 	struct clk *tcm_slave_cbcr;
 	struct clk *qdsp6ss_abhm_cbcr;
-	struct clk *qdsp6ss_sleep_cbcr;
 	struct clk *qdsp6ss_axim_cbcr;
-	struct clk *qdsp6ss_xo_cbcr;
-	struct clk *qdsp6ss_core_gfmux;
 	struct clk *lcc_bcr_sleep;
 	struct clk_bulk_data *clks;
 	/* clocks that must be started before the Q6 is booted */
-- 
2.45.1


^ permalink raw reply related	[flat|nested] 31+ messages in thread

* [PATCH 9/9] remoteproc: qcom_q6v5_wcss: use bulk clk API for q6 clocks in QCS404
  2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
                   ` (6 preceding siblings ...)
  2025-12-19  4:34 ` [PATCH 8/9] remoteproc: qcom_q6v5_wcss: drop unused clocks from q6v5 struct Alexandru Gagniuc
@ 2025-12-19  4:34 ` Alexandru Gagniuc
  2025-12-19 14:52 ` [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Krzysztof Kozlowski
  2025-12-19 16:49 ` Rob Herring
  9 siblings, 0 replies; 31+ messages in thread
From: Alexandru Gagniuc @ 2025-12-19  4:34 UTC (permalink / raw)
  To: andersson, mathieu.poirier, krzk+dt
  Cc: Alexandru Gagniuc, linux-arm-msm, linux-remoteproc, linux-kernel

Five of the clocks on QCS404 are consistently enabled and disabled
together. Use the bulk clock API to get and enable them. They are
enabled after the Q6 reset is deasserted, implying they are required
by the Q6. Store them in q6_clks.

Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
---
 drivers/remoteproc/qcom_q6v5_wcss.c | 99 ++++++++---------------------
 1 file changed, 28 insertions(+), 71 deletions(-)

diff --git a/drivers/remoteproc/qcom_q6v5_wcss.c b/drivers/remoteproc/qcom_q6v5_wcss.c
index bcfd79b12fde9..d510769519966 100644
--- a/drivers/remoteproc/qcom_q6v5_wcss.c
+++ b/drivers/remoteproc/qcom_q6v5_wcss.c
@@ -126,14 +126,9 @@ struct q6v5_wcss {
 	u32 halt_nc;
 
 	struct clk *xo;
-	struct clk *ahbfabric_cbcr_clk;
 	struct clk *gcc_abhs_cbcr;
 	struct clk *gcc_axim_cbcr;
-	struct clk *lcc_csr_cbcr;
 	struct clk *ahbs_cbcr;
-	struct clk *tcm_slave_cbcr;
-	struct clk *qdsp6ss_abhm_cbcr;
-	struct clk *qdsp6ss_axim_cbcr;
 	struct clk *lcc_bcr_sleep;
 	struct clk_bulk_data *clks;
 	/* clocks that must be started before the Q6 is booted */
@@ -416,35 +411,16 @@ static int q6v5_wcss_qcs404_power_on(struct q6v5_wcss *wcss)
 	/* Remove reset to the WCNSS QDSP6SS */
 	reset_control_deassert(wcss->wcss_q6_bcr_reset);
 
-	/* Enable Q6SSTOP_AHBFABRIC_CBCR clock */
-	ret = clk_prepare_enable(wcss->ahbfabric_cbcr_clk);
-	if (ret)
+	ret = clk_bulk_prepare_enable(wcss->num_q6_clks, wcss->q6_clks);
+	if (ret) {
+		dev_err(wcss->dev, "failed to enable q6 clocks, err=%d\n", ret);
 		goto disable_gcc_abhs_cbcr_clk;
-
-	/* Enable the LCCCSR CBC clock, Q6SSTOP_Q6SSTOP_LCC_CSR_CBCR clock */
-	ret = clk_prepare_enable(wcss->lcc_csr_cbcr);
-	if (ret)
-		goto disable_ahbfabric_cbcr_clk;
+	};
 
 	/* Enable the Q6AHBS CBC, Q6SSTOP_Q6SS_AHBS_CBCR clock */
 	ret = clk_prepare_enable(wcss->ahbs_cbcr);
 	if (ret)
-		goto disable_csr_cbcr_clk;
-
-	/* Enable the TCM slave CBC, Q6SSTOP_Q6SS_TCM_SLAVE_CBCR clock */
-	ret = clk_prepare_enable(wcss->tcm_slave_cbcr);
-	if (ret)
-		goto disable_ahbs_cbcr_clk;
-
-	/* Enable the Q6SS AHB master CBC, Q6SSTOP_Q6SS_AHBM_CBCR clock */
-	ret = clk_prepare_enable(wcss->qdsp6ss_abhm_cbcr);
-	if (ret)
-		goto disable_tcm_slave_cbcr_clk;
-
-	/* Enable the Q6SS AXI master CBC, Q6SSTOP_Q6SS_AXIM_CBCR clock */
-	ret = clk_prepare_enable(wcss->qdsp6ss_axim_cbcr);
-	if (ret)
-		goto disable_abhm_cbcr_clk;
+		goto disable_q6_clks;
 
 	/* Enable the Q6SS XO CBC */
 	val = readl(wcss->reg_base + Q6SS_XO_CBCR);
@@ -527,17 +503,9 @@ static int q6v5_wcss_qcs404_power_on(struct q6v5_wcss *wcss)
 	val = readl(wcss->reg_base + Q6SS_XO_CBCR);
 	val &= ~Q6SS_CLK_ENABLE;
 	writel(val, wcss->reg_base + Q6SS_XO_CBCR);
-	clk_disable_unprepare(wcss->qdsp6ss_axim_cbcr);
-disable_abhm_cbcr_clk:
-	clk_disable_unprepare(wcss->qdsp6ss_abhm_cbcr);
-disable_tcm_slave_cbcr_clk:
-	clk_disable_unprepare(wcss->tcm_slave_cbcr);
-disable_ahbs_cbcr_clk:
 	clk_disable_unprepare(wcss->ahbs_cbcr);
-disable_csr_cbcr_clk:
-	clk_disable_unprepare(wcss->lcc_csr_cbcr);
-disable_ahbfabric_cbcr_clk:
-	clk_disable_unprepare(wcss->ahbfabric_cbcr_clk);
+disable_q6_clks:
+	clk_bulk_disable_unprepare(wcss->num_q6_clks, wcss->q6_clks);
 disable_gcc_abhs_cbcr_clk:
 	clk_disable_unprepare(wcss->gcc_abhs_cbcr);
 
@@ -655,11 +623,7 @@ static int q6v5_qcs404_wcss_shutdown(struct q6v5_wcss *wcss)
 	val &= ~Q6SS_BHS_ON;
 	writel(val, wcss->reg_base + Q6SS_PWR_CTL_REG);
 
-	clk_disable_unprepare(wcss->ahbfabric_cbcr_clk);
-	clk_disable_unprepare(wcss->lcc_csr_cbcr);
-	clk_disable_unprepare(wcss->tcm_slave_cbcr);
-	clk_disable_unprepare(wcss->qdsp6ss_abhm_cbcr);
-	clk_disable_unprepare(wcss->qdsp6ss_axim_cbcr);
+	clk_bulk_disable_unprepare(wcss->num_q6_clks, wcss->q6_clks);
 
 	val = readl(wcss->reg_base + Q6SS_SLEEP_CBCR);
 	val &= ~BIT(0);
@@ -1099,6 +1063,20 @@ static int q6v5_alloc_memory_region(struct q6v5_wcss *wcss)
 
 static int q6v5_wcss_init_clock(struct q6v5_wcss *wcss)
 {
+	static const char *const q6_clks[] = {
+		"lcc_ahbfabric_cbc", "tcsr_lcc_cbc", "lcc_tcm_slave_cbc",
+		"lcc_abhm_cbc", "lcc_axim_cbc" };
+	int ret, i;
+
+	wcss->num_q6_clks = ARRAY_SIZE(q6_clks);
+	wcss->q6_clks = devm_kcalloc(wcss->dev, wcss->num_q6_clks,
+				       sizeof(*wcss->q6_clks), GFP_KERNEL);
+	if (!wcss->q6_clks)
+		return -ENOMEM;
+
+	for (i = 0; i < wcss->num_q6_clks; i++)
+		wcss->q6_clks[i].id = q6_clks[i];
+
 	wcss->xo = devm_clk_get(wcss->dev, "xo");
 	if (IS_ERR(wcss->xo))
 		return dev_err_probe(wcss->dev, PTR_ERR(wcss->xo),
@@ -1114,44 +1092,23 @@ static int q6v5_wcss_init_clock(struct q6v5_wcss *wcss)
 		return dev_err_probe(wcss->dev, PTR_ERR(wcss->gcc_axim_cbcr),
 				     "failed to get gcc axim clock\n");
 
-	wcss->ahbfabric_cbcr_clk = devm_clk_get(wcss->dev,
-						"lcc_ahbfabric_cbc");
-	if (IS_ERR(wcss->ahbfabric_cbcr_clk))
-		return dev_err_probe(wcss->dev, PTR_ERR(wcss->ahbfabric_cbcr_clk),
-				     "failed to get ahbfabric clock\n");
-
-	wcss->lcc_csr_cbcr = devm_clk_get(wcss->dev, "tcsr_lcc_cbc");
-	if (IS_ERR(wcss->lcc_csr_cbcr))
-		return dev_err_probe(wcss->dev, PTR_ERR(wcss->lcc_csr_cbcr),
-				     "failed to get csr cbcr clk\n");
-
 	wcss->ahbs_cbcr = devm_clk_get(wcss->dev,
 				       "lcc_abhs_cbc");
 	if (IS_ERR(wcss->ahbs_cbcr))
 		return dev_err_probe(wcss->dev, PTR_ERR(wcss->ahbs_cbcr),
 				     "failed to get ahbs_cbcr clk\n");
 
-	wcss->tcm_slave_cbcr = devm_clk_get(wcss->dev,
-					    "lcc_tcm_slave_cbc");
-	if (IS_ERR(wcss->tcm_slave_cbcr))
-		return dev_err_probe(wcss->dev, PTR_ERR(wcss->tcm_slave_cbcr),
-				     "failed to get tcm cbcr clk\n");
-
-	wcss->qdsp6ss_abhm_cbcr = devm_clk_get(wcss->dev, "lcc_abhm_cbc");
-	if (IS_ERR(wcss->qdsp6ss_abhm_cbcr))
-		return dev_err_probe(wcss->dev, PTR_ERR(wcss->qdsp6ss_abhm_cbcr),
-				     "failed to get abhm cbcr clk\n");
-
-	wcss->qdsp6ss_axim_cbcr = devm_clk_get(wcss->dev, "lcc_axim_cbc");
-	if (IS_ERR(wcss->qdsp6ss_axim_cbcr))
-		return dev_err_probe(wcss->dev, PTR_ERR(wcss->qdsp6ss_axim_cbcr),
-				     "failed to get axim cbcr clk\n");
-
 	wcss->lcc_bcr_sleep = devm_clk_get(wcss->dev, "lcc_bcr_sleep");
 	if (IS_ERR(wcss->lcc_bcr_sleep))
 		return dev_err_probe(wcss->dev, PTR_ERR(wcss->lcc_bcr_sleep),
 				     "failed to get bcr cbcr clk\n");
 
+	ret = devm_clk_bulk_get(wcss->dev, wcss->num_q6_clks, wcss->q6_clks);
+	if (ret < 0) {
+		return dev_err_probe(wcss->dev, ret,
+				     "failed to bulk get q6 clocks\n");
+	}
+
 	return 0;
 }
 
-- 
2.45.1


^ permalink raw reply related	[flat|nested] 31+ messages in thread

* Re: [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader
  2025-12-19  4:34 ` [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader Alexandru Gagniuc
@ 2025-12-19  5:37   ` Rob Herring (Arm)
  2025-12-19 14:44   ` Rob Herring
  2025-12-20  8:56   ` Krzysztof Kozlowski
  2 siblings, 0 replies; 31+ messages in thread
From: Rob Herring (Arm) @ 2025-12-19  5:37 UTC (permalink / raw)
  To: Alexandru Gagniuc
  Cc: krzk+dt, linux-kernel, mathieu.poirier, linux-arm-msm, andersson,
	devicetree, Conor Dooley, linux-remoteproc


On Thu, 18 Dec 2025 22:34:10 -0600, Alexandru Gagniuc wrote:
> Document the IPQ9574 native (non-PAS) WCSS image loader. It is similar
> to IPQ8074 WCSS, but requires several new clocks. These clocks must be
> enabled by the host in non-PAS mode, and are not optional. Add an
> example that uses the "qcom,ipq9574-wcss-pil" binding.
> 
> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> ---
>  .../remoteproc/qcom,ipq8074-wcss-pil.yaml     | 115 +++++++++++++++++-
>  1 file changed, 113 insertions(+), 2 deletions(-)
> 

My bot found errors running 'make dt_binding_check' on your patch:

yamllint warnings/errors:

dtschema/dtc warnings/errors:
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:49.28-51 Unexpected 'GCC_ANOC_WCSS_AXI_M_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:50.28-42 Unexpected 'GCC_Q6_AHB_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:51.28-44 Unexpected 'GCC_Q6_AHB_S_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:52.28-43 Unexpected 'GCC_Q6_AXIM_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:53.28-45 Unexpected 'GCC_Q6SS_BOOT_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:54.28-50 Unexpected 'GCC_MEM_NOC_Q6_AXI_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:55.28-52 Unexpected 'GCC_SYS_NOC_WCSS_AHB_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:56.28-45 Unexpected 'GCC_WCSS_ACMT_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:57.28-46 Unexpected 'GCC_WCSS_ECAHB_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:58.28-47 Unexpected 'GCC_WCSS_Q6_TBU_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:59.28-46 Unexpected 'GCC_WCSS_AHB_S_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:60.28-44 Unexpected 'GCC_Q6_AXIM2_CLK'
Lexical error: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dts:61.28-46 Unexpected 'GCC_WCSS_AXI_M_CLK'
FATAL ERROR: Syntax error parsing input tree
make[2]: *** [scripts/Makefile.dtbs:141: Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.example.dtb] Error 1
make[2]: *** Waiting for unfinished jobs....
make[1]: *** [/builds/robherring/dt-review-ci/linux/Makefile:1559: dt_binding_check] Error 2
make: *** [Makefile:248: __sub-make] Error 2

doc reference errors (make refcheckdocs):

See https://patchwork.kernel.org/project/devicetree/patch/20251219043425.888585-2-mr.nuke.me@gmail.com

The base for the series is generally the latest rc1. A different dependency
should be noted in *this* patch.

If you already ran 'make dt_binding_check' and didn't see the above
error(s), then make sure 'yamllint' is installed and dt-schema is up to
date:

pip3 install dtschema --upgrade

Please check and re-submit after running the above command yourself. Note
that DT_SCHEMA_FILES can be set to your schema file to speed up checking
your schema. However, it must be unset to test all examples with your schema.


^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574
  2025-12-19  4:34 ` [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574 Alexandru Gagniuc
@ 2025-12-19 13:20   ` Konrad Dybcio
  2025-12-23 20:21     ` Alex G.
  0 siblings, 1 reply; 31+ messages in thread
From: Konrad Dybcio @ 2025-12-19 13:20 UTC (permalink / raw)
  To: Alexandru Gagniuc, andersson, mathieu.poirier, krzk+dt,
	Philipp Zabel
  Cc: linux-arm-msm, linux-remoteproc, linux-kernel

On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
> Q6 based firmware loading is also present on IPQ9574, when coupled
> with a wifi-6 device, such as QCN5024. Populate driver data for
> IPQ9574 with values from the downstream 5.4 kerrnel.
> 
> Add the new sequences for the WCSS reset and stop. The downstream
> 5.4 kernel calls these "Q6V7", so keep the name. This is still worth
> using with the "q6v5" driver because all other parts of the driver
> can be seamlessly reused.
> 
> The IPQ9574 uses two sets of clocks. the first, dubbed "q6_clocks"
> must be enabled before the Q6 is started by writing the Q6SS_RST_EVB
> register. The second set of clocks, "clks" should only be enabled
> after the Q6 is placed out of reset. Otherwise, the host CPU core that
> tries to start the remoteproc will hang.
> 
> The downstream kernel had a funny comment, "Pray god and wait for
> reset to complete", which I decided to keep for entertainment value.
> 
> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> ---

[...]

> @@ -128,6 +137,12 @@ struct q6v5_wcss {
>  	struct clk *qdsp6ss_xo_cbcr;
>  	struct clk *qdsp6ss_core_gfmux;
>  	struct clk *lcc_bcr_sleep;
> +	struct clk_bulk_data *clks;
> +	/* clocks that must be started before the Q6 is booted */
> +	struct clk_bulk_data *q6_clks;

"pre_boot_clks" or something along those lines?

In general i'm not super stoked to see another platform where manual and
through-TZ bringup of remoteprocs is supposed to be supported in parallel..

Are you sure your firmware doesn't allow you to just do a simple
qcom_scm_pas_auth_and_reset() like in the multipd series?


> +	int num_clks;
> +	int num_q6_clks;
> +
>  	struct regulator *cx_supply;
>  	struct qcom_sysmon *sysmon;
>  
> @@ -236,6 +251,87 @@ static int q6v5_wcss_reset(struct q6v5_wcss *wcss)
>  	return 0;
>  }
>  
> +static int q6v7_wcss_reset(struct q6v5_wcss *wcss, struct rproc *rproc)
> +{
> +	int ret;
> +	u32 val;
> +
> +	/*1. Set TCSR GLOBAL CFG1*/

Please add a space between the comment markers and the contents

> +	ret = regmap_update_bits(wcss->halt_map,
> +				 wcss->halt_nc + TCSR_GLOBAL_CFG1,
> +				 0xff00, 0x1100);

GENMASK(15, 8), BIT(8) | BIT(12)

> +	if (ret) {
> +		dev_err(wcss->dev, "TCSE_GLOBAL_CFG1 failed\n");

I don't think we should count on regmap to ever fail

> +		return ret;
> +	}
> +
> +	/* Enable Q6 clocks */

Right, this naming gets even more confusing


> +	ret = clk_bulk_prepare_enable(wcss->num_q6_clks, wcss->q6_clks);
> +	if (ret) {
> +		dev_err(wcss->dev, "failed to enable clocks, err=%d\n", ret);
> +		return ret;
> +	};
> +
> +	/* Write bootaddr to EVB so that Q6WCSS will jump there after reset */

That's what a boot address is generally for, no? ;)

> +	writel(rproc->bootaddr >> 4, wcss->reg_base + Q6SS_RST_EVB);
> +
> +	/*2. Deassert AON Reset */
> +	ret = reset_control_deassert(wcss->wcss_aon_reset);
> +	if (ret) {
> +		dev_err(wcss->dev, "wcss_aon_reset failed\n");
> +		clk_bulk_disable_unprepare(wcss->num_clks, wcss->clks);
> +		return ret;
> +	}
> +
> +	/*8. Set mpm configs*/

"MPM"

Why are the indices of your comments not in numerical order?

> +	/*set CFG[18:15]=1*/
> +	val = readl(wcss->rmb_base + SSCAON_CONFIG);
> +	val &= ~SSCAON_MASK;
> +	val |= SSCAON_BUS_EN;
> +	writel(val, wcss->rmb_base + SSCAON_CONFIG);
> +
> +	/*9. Wait for SSCAON_STATUS */
> +	ret = readl_poll_timeout(wcss->rmb_base + SSCAON_STATUS,
> +				 val, (val & 0xffff) == 0x10, 1000,
> +				 Q6SS_TIMEOUT_US * 1000);
> +	if (ret) {
> +		dev_err(wcss->dev, " Boot Error, SSCAON=0x%08X\n", val);
> +		return ret;

You left the clocks on in this path

> +	}
> +
> +	/*3. BHS require xo cbcr to be enabled */
> +	val = readl(wcss->reg_base + Q6SS_XO_CBCR);
> +	val |= 0x1;

That's BIT(0)

In qcom_q6v5_mss.c you'll notice this is defined as Q6SS_CBCR_CLKEN

If you dig a little deeper, you'll also notice a similar name in
drivers/clk/qcom/clk-branch.[ch].. I suppose they just reused the same
kind of HW on the remoteproc side

> +	writel(val, wcss->reg_base + Q6SS_XO_CBCR);
> +
> +	/*4. Enable core cbcr*/
> +	val = readl(wcss->reg_base + Q6SS_CORE_CBCR);
> +	val |= 0x1;
> +	writel(val, wcss->reg_base + Q6SS_CORE_CBCR);
> +
> +	/*5. Enable sleep cbcr*/
> +	val = readl(wcss->reg_base + Q6SS_SLEEP_CBCR);
> +	val |= 0x1;
> +	writel(val, wcss->reg_base + Q6SS_SLEEP_CBCR);
> +
> +	/*6. Boot core start */
> +	writel(0x1, wcss->reg_base + Q6SS_BOOT_CORE_START);
> +	writel(0x1, wcss->reg_base + Q6SS_BOOT_CMD);
> +
> +	/*7. Pray god and wait for reset to complete*/

"ora et labora" - you've done your work, so I'd assume we can
expect success now

> +	ret = readl_poll_timeout(wcss->reg_base + Q6SS_BOOT_STATUS, val,
> +				 (val & 0x01), 20000, 1000);

The timeout is smaller than the retry delay value, this will only spin
once

0x01 is also BIT(0)

But since you never check whether that timeout has actually been
reached, I assume you really stand by the comment!

(you need this hunk):
if (ret) {
	dev_err(wcss->dev, "WCSS boot timed out\n");
	// cleanup
	return -ETIMEDOUT;
}

> +
> +	/* Enable non-Q6 clocks */
> +	ret = clk_bulk_prepare_enable(wcss->num_clks, wcss->clks);
> +	if (ret) {
> +		dev_err(wcss->dev, "failed to enable clocks, err=%d\n", ret);

the previous set of clocks will be left enabled in this case too

> +		return ret;
> +	};
> +
> +	return 0;

If you return ret here, you can drop the return in the above scope

> +}
> +
>  static int q6v5_wcss_start(struct rproc *rproc)
>  {
>  	struct q6v5_wcss *wcss = rproc->priv;
> @@ -270,10 +366,20 @@ static int q6v5_wcss_start(struct rproc *rproc)
>  	if (ret)
>  		goto wcss_q6_reset;
>  
> -	/* Write bootaddr to EVB so that Q6WCSS will jump there after reset */
> -	writel(rproc->bootaddr >> 4, wcss->reg_base + Q6SS_RST_EVB);
> +	switch (wcss->version) {
> +	case WCSS_QCS404:
> +	case WCSS_IPQ8074:
> +		/* Write bootaddr to EVB so that Q6WCSS will jump there after
> +		 * reset.
> +		 */

/* foo */?

[...]

> +static void q6v7_q6_powerdown(struct q6v5_wcss *wcss)
> +{
> +	uint32_t val;

"u32"

> +
> +	q6v5_wcss_halt_axi_port(wcss, wcss->halt_map, wcss->halt_q6);
> +
> +	/* Disable Q6 Core clock -- we don't know what bit 0 means */

I would assume clearing it muxes the clocksource to XO

[...]

> +static int ipq9574_init_clocks(struct q6v5_wcss *wcss)
> +{
> +	static const char *const q6_clks[] = {
> +		"anoc_wcss_axi_m", "q6_ahb", "q6_ahb_s", "q6_axim", "q6ss_boot",
> +		"mem_noc_q6_axi", "sys_noc_wcss_ahb", "wcss_acmt", "wcss_ecahb",
> +		"wcss_q6_tbu" };
> +	static const char *const clks[] = {
> +		"q6_axim2", "wcss_ahb_s", "wcss_axi_m" };

static local variables that we point to? eeeeeeh

> +	int i, ret;
> +
> +	wcss->num_clks = ARRAY_SIZE(clks);
> +	wcss->num_q6_clks = ARRAY_SIZE(q6_clks);
> +
> +	wcss->q6_clks = devm_kcalloc(wcss->dev, wcss->num_q6_clks,
> +				     sizeof(*wcss->q6_clks), GFP_KERNEL);
> +	if (!wcss->q6_clks)
> +		return -ENOMEM;
> +
> +	wcss->clks = devm_kcalloc(wcss->dev, wcss->num_clks,
> +				  sizeof(*wcss->clks), GFP_KERNEL);
> +	if (!wcss->clks)
> +		return -ENOMEM;
> +
> +	for (i = 0; i < wcss->num_q6_clks; i++)
> +		wcss->q6_clks[i].id = q6_clks[i];
> +
> +	for (i = 0; i < wcss->num_clks; i++)
> +		wcss->clks[i].id = clks[i];
> +
> +	ret = devm_clk_bulk_get(wcss->dev, wcss->num_q6_clks, wcss->q6_clks);
> +	if (ret < 0)
> +		return ret;
> +
> +	return devm_clk_bulk_get(wcss->dev, wcss->num_clks, wcss->clks);
> +}
> +
> +

double \n

Konrad

^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 7/9] remoteproc: qcom_q6v5_wcss: support m3 firmware
  2025-12-19  4:34 ` [PATCH 7/9] remoteproc: qcom_q6v5_wcss: support m3 firmware Alexandru Gagniuc
@ 2025-12-19 13:29   ` Konrad Dybcio
  2025-12-23 20:35     ` Alex G.
  0 siblings, 1 reply; 31+ messages in thread
From: Konrad Dybcio @ 2025-12-19 13:29 UTC (permalink / raw)
  To: Alexandru Gagniuc, andersson, mathieu.poirier, krzk+dt
  Cc: linux-arm-msm, linux-remoteproc, linux-kernel

On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
> IPQ8074, IPQ6018, and IPQ9574 support an m3 firmware image in addtion
> to the q6 firmware. The firmware releases from qcom provide both q6
> and m3 firmware for these SoCs. Support loading the m3 firmware image.
> 
> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> ---
>  drivers/remoteproc/qcom_q6v5_wcss.c | 44 +++++++++++++++++++++++++----
>  1 file changed, 39 insertions(+), 5 deletions(-)
> 
> diff --git a/drivers/remoteproc/qcom_q6v5_wcss.c b/drivers/remoteproc/qcom_q6v5_wcss.c
> index b62e97c92d058..265010c5c82cb 100644
> --- a/drivers/remoteproc/qcom_q6v5_wcss.c
> +++ b/drivers/remoteproc/qcom_q6v5_wcss.c
> @@ -101,7 +101,8 @@ enum {
>  };
>  
>  struct wcss_data {
> -	const char *firmware_name;
> +	const char *q6_firmware_name;
> +	const char *m3_firmware_name;
>  	unsigned int crash_reason_smem;
>  	u32 version;
>  	bool aon_reset_required;
> @@ -161,6 +162,7 @@ struct q6v5_wcss {
>  	unsigned int crash_reason_smem;
>  	u32 version;
>  	bool requires_force_stop;
> +	const char *m3_firmware_name;
>  
>  	struct qcom_rproc_glink glink_subdev;
>  	struct qcom_rproc_pdm pdm_subdev;
> @@ -922,11 +924,40 @@ static void *q6v5_wcss_da_to_va(struct rproc *rproc, u64 da, size_t len, bool *i
>  	return wcss->mem_region + offset;
>  }
>  
> +static int q6v5_wcss_load_aux(struct q6v5_wcss *wcss, const char *fw_name)
> +{
> +	const struct firmware *extra_fw;
> +	int ret;
> +
> +	dev_info(wcss->dev, "loading additional firmware image %s\n", fw_name);

I don't think this log line is useful beyond development

> +
> +	ret = request_firmware(&extra_fw, fw_name, wcss->dev);
> +	if (ret)
> +		return 0;

return ret, perhaps? Unless you want to say that "it's fine if the M3 image
is missing, particularly not to impose any new requirements on existing
setups". But you haven't spelt that out explicitly.

You also haven't provided an explanation as to why the firmware should be
loaded. Is it necessary for some functionality? Is it that case on the
newly-supported IPQ9574?

Konrad

^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 8/9] remoteproc: qcom_q6v5_wcss: drop unused clocks from q6v5 struct
  2025-12-19  4:34 ` [PATCH 8/9] remoteproc: qcom_q6v5_wcss: drop unused clocks from q6v5 struct Alexandru Gagniuc
@ 2025-12-19 13:31   ` Konrad Dybcio
  0 siblings, 0 replies; 31+ messages in thread
From: Konrad Dybcio @ 2025-12-19 13:31 UTC (permalink / raw)
  To: Alexandru Gagniuc, andersson, mathieu.poirier, krzk+dt,
	Gokul Sriram Palanisamy, Govind Singh
  Cc: linux-arm-msm, linux-remoteproc, linux-kernel

On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
> Three of the clocks from struct q6v5_wcss are not populated, and are
> not used. Remove them.
> 
> Fixes: 0af65b9b915e ("remoteproc: qcom: wcss: Add non pas wcss Q6 support for QCS404")
> 
> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> ---

It's worth noting they are handled by the driver through register accesses
to the Q6 regspace

This patch can be moved to #1 so that Bjorn can pick it up independently

Konrad

^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 4/9] arm64: dts: qcom: ipq9574: add wcss remoteproc nodes
  2025-12-19  4:34 ` [PATCH 4/9] arm64: dts: qcom: ipq9574: add wcss remoteproc nodes Alexandru Gagniuc
@ 2025-12-19 13:43   ` Konrad Dybcio
  0 siblings, 0 replies; 31+ messages in thread
From: Konrad Dybcio @ 2025-12-19 13:43 UTC (permalink / raw)
  To: Alexandru Gagniuc, andersson, mathieu.poirier, krzk+dt,
	Konrad Dybcio, Rob Herring, Conor Dooley
  Cc: linux-arm-msm, devicetree, linux-kernel

On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
> The WCSS remoteproc is typically used by ath11k to load wifi firmware
> to the Hexagon q6 procesor. Add the nodes required to bring up this
> processor.
> 
> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> ---

[...]

> +		q6v5_wcss: remoteproc@cd00000 {
> +			compatible = "qcom,ipq9574-wcss-pil";
> +			reg = <0x0cd00000 0x4040>,
> +			      <0x004ab000 0x20>;
> +			reg-names = "qdsp6",
> +				    "rmb";

Hmm.. this "rmb" region is really:

0x0 PS_HOLD (write here to reset the chip, if the TZ lets you..)
..
0x8 SSCAON_CONFIG (essentially a syscon which you write to from your driver)
0xc SSCAON_STATUS (same)

But we've been describing things this way for years.. I don't know if it's
worth changing, especially since the rproc driver really assumes this to
be the case

Konrad

^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader
  2025-12-19  4:34 ` [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader Alexandru Gagniuc
  2025-12-19  5:37   ` Rob Herring (Arm)
@ 2025-12-19 14:44   ` Rob Herring
  2025-12-20  8:54     ` Krzysztof Kozlowski
  2025-12-20  8:56   ` Krzysztof Kozlowski
  2 siblings, 1 reply; 31+ messages in thread
From: Rob Herring @ 2025-12-19 14:44 UTC (permalink / raw)
  To: Alexandru Gagniuc
  Cc: andersson, mathieu.poirier, krzk+dt, Conor Dooley, linux-arm-msm,
	linux-remoteproc, devicetree, linux-kernel

On Thu, Dec 18, 2025 at 10:34:10PM -0600, Alexandru Gagniuc wrote:
> Document the IPQ9574 native (non-PAS) WCSS image loader. It is similar
> to IPQ8074 WCSS, but requires several new clocks. These clocks must be
> enabled by the host in non-PAS mode, and are not optional. Add an
> example that uses the "qcom,ipq9574-wcss-pil" binding.

Is the new example really much different and unique. If not, drop it 
(especially since it wasn't even tested).

Rob

^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema
  2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
                   ` (7 preceding siblings ...)
  2025-12-19  4:34 ` [PATCH 9/9] remoteproc: qcom_q6v5_wcss: use bulk clk API for q6 clocks in QCS404 Alexandru Gagniuc
@ 2025-12-19 14:52 ` Krzysztof Kozlowski
  2025-12-20 18:40   ` Alex G.
  2025-12-19 16:49 ` Rob Herring
  9 siblings, 1 reply; 31+ messages in thread
From: Krzysztof Kozlowski @ 2025-12-19 14:52 UTC (permalink / raw)
  To: Alexandru Gagniuc, andersson, mathieu.poirier, krzk+dt,
	Rob Herring, Conor Dooley
  Cc: linux-arm-msm, linux-remoteproc, devicetree, linux-kernel

On 19/12/2025 05:34, Alexandru Gagniuc wrote:
> Convert the QCS404 and IPQ WCSS Peripheral Image Loader bindings to DT
> schema. The text bindngs incorrectly implied that IPQ8074 needs only
> one qcom,smem-states entry. This is only true for QCS404. IPQ8074
> requires both "stop" and "shutdown".
> 
> The example is to be added in a subsequent commit that adds the
> IPQ9574 binding.
> 
> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>

This is not v1, but v2. Look - what is this "dt-bindings: remoteproc:
qcom,ipq8074-wcss-pil: convert to DT schema" in my inbox?

And what is this:

> 
> ---
> Changes since RFC
>  - rename binding from ipq9574 to ipq8074
>  - use a real person instead of placeholder as maintainer
>  - drop redundant minItems and descriptions
>  - merge if: clauses as suggested by Krzysztof
>  - various other fixes suggested by Krzysztof

So not v1?

And now run b4 diff and find differences.

If this is anyhow weird (although how counting from 0 or -1 or -2 if you
have 3 RFCs can be natural?), then just use b4 which would solve all
these problems.

You also miss cover letter, which would be easily solved with b4.

You are not making it easier for reviewers.

> 
> I used my name as a placeholder for the "maintainer" field. Krzysztof
> mentioned to get the "SOC maintainer" using get_maintainer. I don't
> know how to do that, and I don't see anyone listed for QCS404,
> IPQ8074, or IPQ9574. The bindings apply to any of those SOCs.

So you run get_maintainer.pl script on the soc DTSI file and you got
zero results? I claim that's impossible... but just in case please post
here the commands.

Anyway listing yourself is fine.

Trying to see what happened here:
b4 diff '<20251219043425.888585-4-mr.nuke.me@gmail.com>'
Grabbing thread from
lore.kernel.org/all/20251219043425.888585-4-mr.nuke.me@gmail.com/t.mbox.gz
---
Analyzing 15 messages in the thread
Could not find lower series to compare against.

so this patch will wait.


Best regards,
Krzysztof

^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema
  2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
                   ` (8 preceding siblings ...)
  2025-12-19 14:52 ` [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Krzysztof Kozlowski
@ 2025-12-19 16:49 ` Rob Herring
  9 siblings, 0 replies; 31+ messages in thread
From: Rob Herring @ 2025-12-19 16:49 UTC (permalink / raw)
  To: Alexandru Gagniuc
  Cc: krzk+dt, devicetree, mathieu.poirier, linux-remoteproc,
	Conor Dooley, linux-kernel, andersson, linux-arm-msm


On Thu, 18 Dec 2025 22:34:09 -0600, Alexandru Gagniuc wrote:
> Convert the QCS404 and IPQ WCSS Peripheral Image Loader bindings to DT
> schema. The text bindngs incorrectly implied that IPQ8074 needs only
> one qcom,smem-states entry. This is only true for QCS404. IPQ8074
> requires both "stop" and "shutdown".
> 
> The example is to be added in a subsequent commit that adds the
> IPQ9574 binding.
> 
> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> 
> ---
> Changes since RFC
>  - rename binding from ipq9574 to ipq8074
>  - use a real person instead of placeholder as maintainer
>  - drop redundant minItems and descriptions
>  - merge if: clauses as suggested by Krzysztof
>  - various other fixes suggested by Krzysztof
> 
> I used my name as a placeholder for the "maintainer" field. Krzysztof
> mentioned to get the "SOC maintainer" using get_maintainer. I don't
> know how to do that, and I don't see anyone listed for QCS404,
> IPQ8074, or IPQ9574. The bindings apply to any of those SOCs.
> ---
>  .../remoteproc/qcom,ipq8074-wcss-pil.yaml     | 156 ++++++++++++++++++
>  .../bindings/remoteproc/qcom,q6v5.txt         | 102 ------------
>  2 files changed, 156 insertions(+), 102 deletions(-)
>  create mode 100644 Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml
>  delete mode 100644 Documentation/devicetree/bindings/remoteproc/qcom,q6v5.txt
> 


My bot found new DTB warnings on the .dts files added or changed in this
series.

Some warnings may be from an existing SoC .dtsi. Or perhaps the warnings
are fixed by another series. Ultimately, it is up to the platform
maintainer whether these warnings are acceptable or not. No need to reply
unless the platform maintainer has comments.

If you already ran DT checks and didn't see these error(s), then
make sure dt-schema is up to date:

  pip3 install dtschema --upgrade


This patch series was applied (using b4) to base:
 Base: attempting to guess base-commit...
 Base: tags/v6.19-rc1-9-g98675bc92a9e (exact match)
 Base: tags/v6.19-rc1-9-g98675bc92a9e (use --merge-base to override)

If this is not the correct base, please add 'base-commit' tag
(or use b4 which does this automatically)

New warnings running 'make CHECK_DTBS=y for arch/arm64/boot/dts/qcom/' for 20251219043425.888585-1-mr.nuke.me@gmail.com:

arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: smp2p-wcss (qcom,smp2p): master-kernel: 'qcom,smp2p-feature-ssr-ack' does not match any of the regexes: '^pinctrl-[0-9]+$'
	from schema $id: http://devicetree.org/schemas/soc/qcom/qcom,smp2p.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:1: 'wcss_ahb_s' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:2: 'wcss_ecahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:3: 'wcss_acmt' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:4: 'wcss_axi_m' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:5: 'q6_axim' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:6: 'q6_axim2' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:7: 'q6_ahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:8: 'q6_ahb_s' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:9: 'q6ss_boot' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:10: 'mem_noc_q6_axi' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:11: 'wcss_q6_tbu' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp454.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:12: 'sys_noc_wcss_ahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: smp2p-wcss (qcom,smp2p): master-kernel: 'qcom,smp2p-feature-ssr-ack' does not match any of the regexes: '^pinctrl-[0-9]+$'
	from schema $id: http://devicetree.org/schemas/soc/qcom/qcom,smp2p.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:1: 'wcss_ahb_s' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:2: 'wcss_ecahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:3: 'wcss_acmt' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:4: 'wcss_axi_m' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:5: 'q6_axim' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:6: 'q6_axim2' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:7: 'q6_ahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:8: 'q6_ahb_s' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:9: 'q6ss_boot' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:10: 'mem_noc_q6_axi' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:11: 'wcss_q6_tbu' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp433.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:12: 'sys_noc_wcss_ahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: smp2p-wcss (qcom,smp2p): master-kernel: 'qcom,smp2p-feature-ssr-ack' does not match any of the regexes: '^pinctrl-[0-9]+$'
	from schema $id: http://devicetree.org/schemas/soc/qcom/qcom,smp2p.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:1: 'wcss_ahb_s' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:2: 'wcss_ecahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:3: 'wcss_acmt' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:4: 'wcss_axi_m' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:5: 'q6_axim' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:6: 'q6_axim2' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:7: 'q6_ahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:8: 'q6_ahb_s' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:9: 'q6ss_boot' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:10: 'mem_noc_q6_axi' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:11: 'wcss_q6_tbu' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp453.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:12: 'sys_noc_wcss_ahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: smp2p-wcss (qcom,smp2p): master-kernel: 'qcom,smp2p-feature-ssr-ack' does not match any of the regexes: '^pinctrl-[0-9]+$'
	from schema $id: http://devicetree.org/schemas/soc/qcom/qcom,smp2p.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:1: 'wcss_ahb_s' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:2: 'wcss_ecahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:3: 'wcss_acmt' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:4: 'wcss_axi_m' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:5: 'q6_axim' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:6: 'q6_axim2' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:7: 'q6_ahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:8: 'q6_ahb_s' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:9: 'q6ss_boot' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:10: 'mem_noc_q6_axi' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:11: 'wcss_q6_tbu' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp449.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:12: 'sys_noc_wcss_ahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: smp2p-wcss (qcom,smp2p): master-kernel: 'qcom,smp2p-feature-ssr-ack' does not match any of the regexes: '^pinctrl-[0-9]+$'
	from schema $id: http://devicetree.org/schemas/soc/qcom/qcom,smp2p.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:1: 'wcss_ahb_s' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:2: 'wcss_ecahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:3: 'wcss_acmt' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:4: 'wcss_axi_m' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:5: 'q6_axim' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:6: 'q6_axim2' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:7: 'q6_ahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:8: 'q6_ahb_s' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:9: 'q6ss_boot' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:10: 'mem_noc_q6_axi' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:11: 'wcss_q6_tbu' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml
arch/arm64/boot/dts/qcom/ipq9574-rdp418.dtb: remoteproc@cd00000 (qcom,ipq9574-wcss-pil): clock-names:12: 'sys_noc_wcss_ahb' was expected
	from schema $id: http://devicetree.org/schemas/remoteproc/qcom,ipq8074-wcss-pil.yaml






^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader
  2025-12-19 14:44   ` Rob Herring
@ 2025-12-20  8:54     ` Krzysztof Kozlowski
  2025-12-23 19:45       ` Alex G.
  0 siblings, 1 reply; 31+ messages in thread
From: Krzysztof Kozlowski @ 2025-12-20  8:54 UTC (permalink / raw)
  To: Rob Herring
  Cc: Alexandru Gagniuc, andersson, mathieu.poirier, krzk+dt,
	Conor Dooley, linux-arm-msm, linux-remoteproc, devicetree,
	linux-kernel

On Fri, Dec 19, 2025 at 08:44:33AM -0600, Rob Herring wrote:
> On Thu, Dec 18, 2025 at 10:34:10PM -0600, Alexandru Gagniuc wrote:
> > Document the IPQ9574 native (non-PAS) WCSS image loader. It is similar
> > to IPQ8074 WCSS, but requires several new clocks. These clocks must be
> > enabled by the host in non-PAS mode, and are not optional. Add an
> > example that uses the "qcom,ipq9574-wcss-pil" binding.
> 
> Is the new example really much different and unique. If not, drop it 
> (especially since it wasn't even tested).

There is simply no example for existing devices, so this is fine. It
could be mentioned here WHY it is being added, which would solve two
people's questions (yours and mine earlier). If only people knew and
said WHY they are doing something.

Best regards,
Krzysztof


^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader
  2025-12-19  4:34 ` [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader Alexandru Gagniuc
  2025-12-19  5:37   ` Rob Herring (Arm)
  2025-12-19 14:44   ` Rob Herring
@ 2025-12-20  8:56   ` Krzysztof Kozlowski
  2 siblings, 0 replies; 31+ messages in thread
From: Krzysztof Kozlowski @ 2025-12-20  8:56 UTC (permalink / raw)
  To: Alexandru Gagniuc
  Cc: andersson, mathieu.poirier, krzk+dt, Rob Herring, Conor Dooley,
	linux-arm-msm, linux-remoteproc, devicetree, linux-kernel

On Thu, Dec 18, 2025 at 10:34:10PM -0600, Alexandru Gagniuc wrote:
> Document the IPQ9574 native (non-PAS) WCSS image loader. It is similar
> to IPQ8074 WCSS, but requires several new clocks. These clocks must be
> enabled by the host in non-PAS mode, and are not optional. Add an
> example that uses the "qcom,ipq9574-wcss-pil" binding.
> 
> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> ---
>  .../remoteproc/qcom,ipq8074-wcss-pil.yaml     | 115 +++++++++++++++++-
>  1 file changed, 113 insertions(+), 2 deletions(-)
> 
> diff --git a/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml b/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml
> index dea46cb9f93fe..a665b704a835f 100644
> --- a/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml
> +++ b/Documentation/devicetree/bindings/remoteproc/qcom,ipq8074-wcss-pil.yaml
> @@ -18,6 +18,7 @@ properties:
>    compatible:
>      enum:
>        - qcom,ipq8074-wcss-pil
> +      - qcom,ipq9574-wcss-pil
>        - qcom,qcs404-wcss-pil
>  
>    reg:
> @@ -49,10 +50,10 @@ properties:
>        - const: wcss_q6_reset
>  
>    clocks:
> -    maxItems: 10

Either you miss minItems or you are changing existing devices without
any explanation.

> +    maxItems: 13
>  
>    clock-names:
> -    maxItems: 10
> +    maxItems: 13
>  
>    cx-supply:
>      description:
> @@ -107,6 +108,7 @@ allOf:
>            contains:
>              enum:
>                - qcom,ipq8074-wcss-pil
> +              - qcom,ipq9574-wcss-pil
>      then:
>        properties:
>          qcom,smem-states:
> @@ -117,9 +119,47 @@ allOf:
>            items:
>              - const: shutdown
>              - const: stop

So why all devices have now 13 clocks?

> +
> +  - if:
> +      properties:
> +        compatible:
> +          contains:
> +            enum:
> +              - qcom,ipq8074-wcss-pil

Just keep the if:then: per device, don't mix it up.

> +    then:
> +      properties:
>          clock-names: false
>          clocks: false

Best regards,
Krzysztof


^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema
  2025-12-19 14:52 ` [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Krzysztof Kozlowski
@ 2025-12-20 18:40   ` Alex G.
  0 siblings, 0 replies; 31+ messages in thread
From: Alex G. @ 2025-12-20 18:40 UTC (permalink / raw)
  To: andersson, mathieu.poirier, krzk+dt, Rob Herring, Conor Dooley,
	Krzysztof Kozlowski
  Cc: linux-arm-msm, linux-remoteproc, devicetree, linux-kernel

On Friday, December 19, 2025 8:52:51 AM CST Krzysztof Kozlowski wrote:
> On 19/12/2025 05:34, Alexandru Gagniuc wrote:
> > Convert the QCS404 and IPQ WCSS Peripheral Image Loader bindings to DT
> > schema. The text bindngs incorrectly implied that IPQ8074 needs only
> > one qcom,smem-states entry. This is only true for QCS404. IPQ8074
> > requires both "stop" and "shutdown".
> > 
> > The example is to be added in a subsequent commit that adds the
> > IPQ9574 binding.
> > 
> > Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> 
> > I used my name as a placeholder for the "maintainer" field. Krzysztof
> > mentioned to get the "SOC maintainer" using get_maintainer. I don't
> > know how to do that, and I don't see anyone listed for QCS404,
> > IPQ8074, or IPQ9574. The bindings apply to any of those SOCs.
> 
> the soc DTSI file 

Thank you Krzysztof! That's exactly what I needed to know

Alex





^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader
  2025-12-20  8:54     ` Krzysztof Kozlowski
@ 2025-12-23 19:45       ` Alex G.
  0 siblings, 0 replies; 31+ messages in thread
From: Alex G. @ 2025-12-23 19:45 UTC (permalink / raw)
  To: Rob Herring, Krzysztof Kozlowski
  Cc: andersson, mathieu.poirier, krzk+dt, Conor Dooley, linux-arm-msm,
	linux-remoteproc, devicetree, linux-kernel

On Saturday, December 20, 2025 2:54:02 AM CST Krzysztof Kozlowski wrote:
> On Fri, Dec 19, 2025 at 08:44:33AM -0600, Rob Herring wrote:
> > On Thu, Dec 18, 2025 at 10:34:10PM -0600, Alexandru Gagniuc wrote:
> > > Document the IPQ9574 native (non-PAS) WCSS image loader. It is similar
> > > to IPQ8074 WCSS, but requires several new clocks. These clocks must be
> > > enabled by the host in non-PAS mode, and are not optional. Add an
> > > example that uses the "qcom,ipq9574-wcss-pil" binding.

Hi Rob and Krzysztof,

> > Is the new example really much different and unique. If not, drop it
> > (especially since it wasn't even tested).
> 
> There is simply no example for existing devices, so this is fine. It
> could be mentioned here WHY it is being added, which would solve two
> people's questions (yours and mine earlier). If only people knew and
> said WHY they are doing something.

TIL, I need to put the third patch ("dt-bindings: clock: gcc-ipq9574: add wcss 
remoteproc clocks") before this one to resolve dtb check issues with the 
example. I'll also add a blurb to the commit message to explain WHY.

Alex




^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574
  2025-12-19 13:20   ` Konrad Dybcio
@ 2025-12-23 20:21     ` Alex G.
  2025-12-24  9:44       ` Vignesh Viswanathan
  2025-12-29 12:35       ` Konrad Dybcio
  0 siblings, 2 replies; 31+ messages in thread
From: Alex G. @ 2025-12-23 20:21 UTC (permalink / raw)
  To: andersson, mathieu.poirier, Konrad Dybcio, linux-kernel
  Cc: krzk+dt, Philipp Zabel, linux-arm-msm, linux-remoteproc

On Friday, December 19, 2025 7:20:04 AM CST Konrad Dybcio wrote:
> On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
> > Q6 based firmware loading is also present on IPQ9574, when coupled
> > with a wifi-6 device, such as QCN5024. Populate driver data for
> > IPQ9574 with values from the downstream 5.4 kerrnel.
> > 
> > Add the new sequences for the WCSS reset and stop. The downstream
> > 5.4 kernel calls these "Q6V7", so keep the name. This is still worth
> > using with the "q6v5" driver because all other parts of the driver
> > can be seamlessly reused.
> > 
> > The IPQ9574 uses two sets of clocks. the first, dubbed "q6_clocks"
> > must be enabled before the Q6 is started by writing the Q6SS_RST_EVB
> > register. The second set of clocks, "clks" should only be enabled
> > after the Q6 is placed out of reset. Otherwise, the host CPU core that
> > tries to start the remoteproc will hang.
> > 
> > The downstream kernel had a funny comment, "Pray god and wait for
> > reset to complete", which I decided to keep for entertainment value.
> > 
> > Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> > ---
> 
> [...]
> 
> > @@ -128,6 +137,12 @@ struct q6v5_wcss {
> > 
> >  	struct clk *qdsp6ss_xo_cbcr;
> >  	struct clk *qdsp6ss_core_gfmux;
> >  	struct clk *lcc_bcr_sleep;
> > 
> > +	struct clk_bulk_data *clks;
> > +	/* clocks that must be started before the Q6 is booted */
> > +	struct clk_bulk_data *q6_clks;
> 
> "pre_boot_clks" or something along those lines?

I like "pre_boot_clocks".

> In general i'm not super stoked to see another platform where manual and
> through-TZ bringup of remoteprocs is supposed to be supported in parallel..
> 
> Are you sure your firmware doesn't allow you to just do a simple
> qcom_scm_pas_auth_and_reset() like in the multipd series?

I am approaching this from the perspective of an aftermarket OS, like OpenWRT. 
I don't know if the firmware will do the right thing. I can mitigate this for 
OS-loaded firmware, like ath11k 16/m3 firmware, because I can test the driver 
and firmware together. I can't do that for bootloader-loaded firmware, so I try 
to depend on it as little as possible. I hope that native remoterproc loading 
for IPQ9574 will be allowed.

> > +	int num_clks;
> > +	int num_q6_clks;
> > +
> > 
> >  	struct regulator *cx_supply;
> >  	struct qcom_sysmon *sysmon;
> > 
> > @@ -236,6 +251,87 @@ static int q6v5_wcss_reset(struct q6v5_wcss *wcss)
> > 
> >  	return 0;
> >  
> >  }
> > 
> > +static int q6v7_wcss_reset(struct q6v5_wcss *wcss, struct rproc *rproc)
> > +{
> > +	int ret;
> > +	u32 val;
> > +
> > +	/*1. Set TCSR GLOBAL CFG1*/
> 
> Please add a space between the comment markers and the contents
> 
> > +	ret = regmap_update_bits(wcss->halt_map,
> > +				 wcss->halt_nc + 
TCSR_GLOBAL_CFG1,
> > +				 0xff00, 0x1100);
> 
> GENMASK(15, 8), BIT(8) | BIT(12)
 
I find GENMASK() and or'ed BIT()s harder to read than plain hex constants. 
Maybe we should use macros, but what should be the names of these two 
constants?

> > +	if (ret) {
> > +		dev_err(wcss->dev, "TCSE_GLOBAL_CFG1 failed\n");
> 
> I don't think we should count on regmap to ever fail

I was following q6v5_wcss_start(), which also handles regmap failures. Do you 
want me to ignore regmap return codes in the code that is added, at the cost 
of some  inconsistency??

> > +		return ret;
> > +	}
> > +
> > +	/* Enable Q6 clocks */
> 
> Right, this naming gets even more confusing

I'll name it "pre_boot_clocks" and drop the comment in the interest of self-
documenting code.

> > +	ret = clk_bulk_prepare_enable(wcss->num_q6_clks, wcss->q6_clks);
> > +	if (ret) {
> > +		dev_err(wcss->dev, "failed to enable clocks, err=%d\n", 
ret);
> > +		return ret;
> > +	};
> > +
> > +	/* Write bootaddr to EVB so that Q6WCSS will jump there after 
reset */
> 
> That's what a boot address is generally for, no? ;)

I used the same comment from q6v5_wcss_start(). I will shorten the comment.

> > +	writel(rproc->bootaddr >> 4, wcss->reg_base + Q6SS_RST_EVB);
> > +
> > +	/*2. Deassert AON Reset */
> > +	ret = reset_control_deassert(wcss->wcss_aon_reset);
> > +	if (ret) {
> > +		dev_err(wcss->dev, "wcss_aon_reset failed\n");
> > +		clk_bulk_disable_unprepare(wcss->num_clks, wcss->clks);
> > +		return ret;
> > +	}
> > +
> > +	/*8. Set mpm configs*/
> 
> "MPM"
> 
> Why are the indices of your comments not in numerical order?
 
I started with the spaghetti sequence from the downstream kernel. I unravelled 
it, and was so happy the code worked, that I forgot to check the numbering. 
I'll remove the numbers, as they don't add much value..

> > +	/*set CFG[18:15]=1*/
> > +	val = readl(wcss->rmb_base + SSCAON_CONFIG);
> > +	val &= ~SSCAON_MASK;
> > +	val |= SSCAON_BUS_EN;
> > +	writel(val, wcss->rmb_base + SSCAON_CONFIG);
> > +
> > +	/*9. Wait for SSCAON_STATUS */
> > +	ret = readl_poll_timeout(wcss->rmb_base + SSCAON_STATUS,
> > +				 val, (val & 0xffff) == 0x10, 1000,
> > +				 Q6SS_TIMEOUT_US * 1000);
> > +	if (ret) {
> > +		dev_err(wcss->dev, " Boot Error, SSCAON=0x%08X\n", 
val);
> > +		return ret;
> 
> You left the clocks on in this path

Good catch! I will use "goto" centralized exiting to turn off resources on 
failure.

> > +	}
> > +
> > +	/*3. BHS require xo cbcr to be enabled */
> > +	val = readl(wcss->reg_base + Q6SS_XO_CBCR);
> > +	val |= 0x1;
> 
> That's BIT(0)
> 
> In qcom_q6v5_mss.c you'll notice this is defined as Q6SS_CBCR_CLKEN
> 
> If you dig a little deeper, you'll also notice a similar name in
> drivers/clk/qcom/clk-branch.[ch].. I suppose they just reused the same
> kind of HW on the remoteproc side

I'll use the macro name as suggested. Thank you!

> > +	writel(val, wcss->reg_base + Q6SS_XO_CBCR);
> > +
> > +	/*4. Enable core cbcr*/
> > +	val = readl(wcss->reg_base + Q6SS_CORE_CBCR);
> > +	val |= 0x1;
> > +	writel(val, wcss->reg_base + Q6SS_CORE_CBCR);
> > +
> > +	/*5. Enable sleep cbcr*/
> > +	val = readl(wcss->reg_base + Q6SS_SLEEP_CBCR);
> > +	val |= 0x1;
> > +	writel(val, wcss->reg_base + Q6SS_SLEEP_CBCR);
> > +
> > +	/*6. Boot core start */
> > +	writel(0x1, wcss->reg_base + Q6SS_BOOT_CORE_START);
> > +	writel(0x1, wcss->reg_base + Q6SS_BOOT_CMD);
> > +
> > +	/*7. Pray god and wait for reset to complete*/
> 
> "ora et labora" - you've done your work, so I'd assume we can
> expect success now
> 
> > +	ret = readl_poll_timeout(wcss->reg_base + Q6SS_BOOT_STATUS, val,
> > +				 (val & 0x01), 20000, 1000);
> 
> The timeout is smaller than the retry delay value, this will only spin
> once
> 
> 0x01 is also BIT(0)
> 
> But since you never check whether that timeout has actually been
> reached, I assume you really stand by the comment!
> 
> (you need this hunk):
> if (ret) {
> 	dev_err(wcss->dev, "WCSS boot timed out\n");
> 	// cleanup
> 	return -ETIMEDOUT;
> }

Good catches! Yes, I definitely meant 20 millisecond timeout (not 1 ms). I will 
also add the error checking.

> > +
> > +	/* Enable non-Q6 clocks */
> > +	ret = clk_bulk_prepare_enable(wcss->num_clks, wcss->clks);
> > +	if (ret) {
> > +		dev_err(wcss->dev, "failed to enable clocks, err=%d\n", 
ret);
> 
> the previous set of clocks will be left enabled in this case too
> 
> > +		return ret;
> > +	};
> > +
> > +	return 0;
> 
> If you return ret here, you can drop the return in the above scope

This part will get changed a bit by the centralized exiting. It will be a 
"goto" (on error) followed by "return 0" (on success).

> > +}
> > +
> > 
> >  static int q6v5_wcss_start(struct rproc *rproc)
> >  {
> >  
> >  	struct q6v5_wcss *wcss = rproc->priv;
> > 
> > @@ -270,10 +366,20 @@ static int q6v5_wcss_start(struct rproc *rproc)
> > 
> >  	if (ret)
> >  	
> >  		goto wcss_q6_reset;
> > 
> > -	/* Write bootaddr to EVB so that Q6WCSS will jump there after 
reset */
> > -	writel(rproc->bootaddr >> 4, wcss->reg_base + Q6SS_RST_EVB);
> > +	switch (wcss->version) {
> > +	case WCSS_QCS404:
> > +	case WCSS_IPQ8074:
> > +		/* Write bootaddr to EVB so that Q6WCSS will jump there 
after
> > +		 * reset.
> > +		 */
> 
> /* foo */?

I was trying to keep it at 80 characters, but since I will shorten this 
comment on the new code paths, I will shorten it here too.

> [...]
> 
> > +static void q6v7_q6_powerdown(struct q6v5_wcss *wcss)
> > +{
> > +	uint32_t val;
> 
> "u32"

Okay.

> > +
> > +	q6v5_wcss_halt_axi_port(wcss, wcss->halt_map, wcss->halt_q6);
> > +
> > +	/* Disable Q6 Core clock -- we don't know what bit 0 means */
> 
> I would assume clearing it muxes the clocksource to XO
> 
> [...]
> 
> > +static int ipq9574_init_clocks(struct q6v5_wcss *wcss)
> > +{
> > +	static const char *const q6_clks[] = {
> > +		"anoc_wcss_axi_m", "q6_ahb", "q6_ahb_s", "q6_axim", 
"q6ss_boot",
> > +		"mem_noc_q6_axi", "sys_noc_wcss_ahb", "wcss_acmt", 
"wcss_ecahb",
> > +		"wcss_q6_tbu" };
> > +	static const char *const clks[] = {
> > +		"q6_axim2", "wcss_ahb_s", "wcss_axi_m" };
> 
> static local variables that we point to? eeeeeeh

I wanted "const char *clks[]" originally. I changed it to this in order to 
appease checkpatch. Should I use my original "const char * []" instead?

[...]

Alex




^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 7/9] remoteproc: qcom_q6v5_wcss: support m3 firmware
  2025-12-19 13:29   ` Konrad Dybcio
@ 2025-12-23 20:35     ` Alex G.
  2025-12-29 12:37       ` Konrad Dybcio
  0 siblings, 1 reply; 31+ messages in thread
From: Alex G. @ 2025-12-23 20:35 UTC (permalink / raw)
  To: andersson, Konrad Dybcio
  Cc: mathieu.poirier, krzk+dt, linux-arm-msm, linux-remoteproc,
	linux-kernel

On Friday, December 19, 2025 7:29:07 AM CST Konrad Dybcio wrote:
> On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
> > IPQ8074, IPQ6018, and IPQ9574 support an m3 firmware image in addtion
> > to the q6 firmware. The firmware releases from qcom provide both q6
> > and m3 firmware for these SoCs. Support loading the m3 firmware image.
> > 
> > Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> > ---
> > 
> >  drivers/remoteproc/qcom_q6v5_wcss.c | 44 +++++++++++++++++++++++++----
> >  1 file changed, 39 insertions(+), 5 deletions(-)
> > 
> > diff --git a/drivers/remoteproc/qcom_q6v5_wcss.c
> > b/drivers/remoteproc/qcom_q6v5_wcss.c index b62e97c92d058..265010c5c82cb
> > 100644
> > --- a/drivers/remoteproc/qcom_q6v5_wcss.c
> > +++ b/drivers/remoteproc/qcom_q6v5_wcss.c
> > @@ -101,7 +101,8 @@ enum {
> > 
> >  };
> >  
> >  struct wcss_data {
> > 
> > -	const char *firmware_name;
> > +	const char *q6_firmware_name;
> > +	const char *m3_firmware_name;
> > 
> >  	unsigned int crash_reason_smem;
> >  	u32 version;
> >  	bool aon_reset_required;
> > 
> > @@ -161,6 +162,7 @@ struct q6v5_wcss {
> > 
> >  	unsigned int crash_reason_smem;
> >  	u32 version;
> >  	bool requires_force_stop;
> > 
> > +	const char *m3_firmware_name;
> > 
> >  	struct qcom_rproc_glink glink_subdev;
> >  	struct qcom_rproc_pdm pdm_subdev;
> > 
> > @@ -922,11 +924,40 @@ static void *q6v5_wcss_da_to_va(struct rproc *rproc,
> > u64 da, size_t len, bool *i> 
> >  	return wcss->mem_region + offset;
> >  
> >  }
> > 
> > +static int q6v5_wcss_load_aux(struct q6v5_wcss *wcss, const char
> > *fw_name)
> > +{
> > +	const struct firmware *extra_fw;
> > +	int ret;
> > +
> > +	dev_info(wcss->dev, "loading additional firmware image %s\n", 
fw_name);
> 
> I don't think this log line is useful beyond development

Remoteproc driver prints the main (q6) fimrware name, so I thought it would be 
prudent to print the names of any additional firmwares:

    remoteproc remoteproc0: Booting fw image IPQ9574/q6_fw.mdt, size 8140

> > +
> > +	ret = request_firmware(&extra_fw, fw_name, wcss->dev);
> > +	if (ret)
> > +		return 0;
> 
> return ret, perhaps? Unless you want to say that "it's fine if the M3 image
> is missing, particularly not to impose any new requirements on existing
> setups". But you haven't spelt that out explicitly.

I intended to not abort when aux firmware is missing. Maybe the better way to 
handle this is to check for "-ENOENT" in the caller instead of return 0 here.

> You also haven't provided an explanation as to why the firmware should be
> loaded. Is it necessary for some functionality? Is it that case on the
> newly-supported IPQ9574?

I don't have a good answer. I reasoned that since the qcom provides it [1], 
the M3 firmware would need to be loaded. I haven't done much testing without 
it.

Alex

[1] https://github.com/quic/upstream-wifi-fw.git


> Konrad





^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574
  2025-12-23 20:21     ` Alex G.
@ 2025-12-24  9:44       ` Vignesh Viswanathan
  2025-12-24 17:36         ` Alex G.
  2025-12-29 12:35       ` Konrad Dybcio
  1 sibling, 1 reply; 31+ messages in thread
From: Vignesh Viswanathan @ 2025-12-24  9:44 UTC (permalink / raw)
  To: Alex G., andersson, mathieu.poirier, Konrad Dybcio, linux-kernel
  Cc: krzk+dt, Philipp Zabel, linux-arm-msm, linux-remoteproc



On 12/24/2025 1:51 AM, Alex G. wrote:
> On Friday, December 19, 2025 7:20:04 AM CST Konrad Dybcio wrote:
>> On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
>>> Q6 based firmware loading is also present on IPQ9574, when coupled
>>> with a wifi-6 device, such as QCN5024. Populate driver data for
>>> IPQ9574 with values from the downstream 5.4 kerrnel.
>>>
>>> Add the new sequences for the WCSS reset and stop. The downstream
>>> 5.4 kernel calls these "Q6V7", so keep the name. This is still worth
>>> using with the "q6v5" driver because all other parts of the driver
>>> can be seamlessly reused.
>>>
>>> The IPQ9574 uses two sets of clocks. the first, dubbed "q6_clocks"
>>> must be enabled before the Q6 is started by writing the Q6SS_RST_EVB
>>> register. The second set of clocks, "clks" should only be enabled
>>> after the Q6 is placed out of reset. Otherwise, the host CPU core that
>>> tries to start the remoteproc will hang.
>>>
>>> The downstream kernel had a funny comment, "Pray god and wait for
>>> reset to complete", which I decided to keep for entertainment value.
>>>
>>> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
>>> ---
>>
>> [...]
>>
>>> @@ -128,6 +137,12 @@ struct q6v5_wcss {
>>>
>>>  	struct clk *qdsp6ss_xo_cbcr;
>>>  	struct clk *qdsp6ss_core_gfmux;
>>>  	struct clk *lcc_bcr_sleep;
>>>
>>> +	struct clk_bulk_data *clks;
>>> +	/* clocks that must be started before the Q6 is booted */
>>> +	struct clk_bulk_data *q6_clks;
>>
>> "pre_boot_clks" or something along those lines?
> 
> I like "pre_boot_clocks".
> 
>> In general i'm not super stoked to see another platform where manual and
>> through-TZ bringup of remoteprocs is supposed to be supported in parallel..
>>
>> Are you sure your firmware doesn't allow you to just do a simple
>> qcom_scm_pas_auth_and_reset() like in the multipd series?
> 
> I am approaching this from the perspective of an aftermarket OS, like OpenWRT. 
> I don't know if the firmware will do the right thing. I can mitigate this for 
> OS-loaded firmware, like ath11k 16/m3 firmware, because I can test the driver 
> and firmware together. I can't do that for bootloader-loaded firmware, so I try 
> to depend on it as little as possible. I hope that native remoterproc loading 
> for IPQ9574 will be allowed.

Hi Alex,

Does this rproc start sequence work on IPQ9574 without using the 
qcom_scm_pas_auth_and_reset ?

Thanks,
Vignesh

> 
>>> +	int num_clks;
>>> +	int num_q6_clks;
>>> +
>>>
>>>  	struct regulator *cx_supply;
>>>  	struct qcom_sysmon *sysmon;
>>>
>>> @@ -236,6 +251,87 @@ static int q6v5_wcss_reset(struct q6v5_wcss *wcss)
>>>
>>>  	return 0;
>>>  
>>>  }
>>>
>>> +static int q6v7_wcss_reset(struct q6v5_wcss *wcss, struct rproc *rproc)
>>> +{
>>> +	int ret;
>>> +	u32 val;
>>> +
>>> +	/*1. Set TCSR GLOBAL CFG1*/
>>
>> Please add a space between the comment markers and the contents
>>
>>> +	ret = regmap_update_bits(wcss->halt_map,
>>> +				 wcss->halt_nc + 
> TCSR_GLOBAL_CFG1,
>>> +				 0xff00, 0x1100);
>>
>> GENMASK(15, 8), BIT(8) | BIT(12)
>  
> I find GENMASK() and or'ed BIT()s harder to read than plain hex constants. 
> Maybe we should use macros, but what should be the names of these two 
> constants?
> 
>>> +	if (ret) {
>>> +		dev_err(wcss->dev, "TCSE_GLOBAL_CFG1 failed\n");
>>
>> I don't think we should count on regmap to ever fail
> 
> I was following q6v5_wcss_start(), which also handles regmap failures. Do you 
> want me to ignore regmap return codes in the code that is added, at the cost 
> of some  inconsistency??
> 
>>> +		return ret;
>>> +	}
>>> +
>>> +	/* Enable Q6 clocks */
>>
>> Right, this naming gets even more confusing
> 
> I'll name it "pre_boot_clocks" and drop the comment in the interest of self-
> documenting code.
> 
>>> +	ret = clk_bulk_prepare_enable(wcss->num_q6_clks, wcss->q6_clks);
>>> +	if (ret) {
>>> +		dev_err(wcss->dev, "failed to enable clocks, err=%d\n", 
> ret);
>>> +		return ret;
>>> +	};
>>> +
>>> +	/* Write bootaddr to EVB so that Q6WCSS will jump there after 
> reset */
>>
>> That's what a boot address is generally for, no? ;)
> 
> I used the same comment from q6v5_wcss_start(). I will shorten the comment.
> 
>>> +	writel(rproc->bootaddr >> 4, wcss->reg_base + Q6SS_RST_EVB);
>>> +
>>> +	/*2. Deassert AON Reset */
>>> +	ret = reset_control_deassert(wcss->wcss_aon_reset);
>>> +	if (ret) {
>>> +		dev_err(wcss->dev, "wcss_aon_reset failed\n");
>>> +		clk_bulk_disable_unprepare(wcss->num_clks, wcss->clks);
>>> +		return ret;
>>> +	}
>>> +
>>> +	/*8. Set mpm configs*/
>>
>> "MPM"
>>
>> Why are the indices of your comments not in numerical order?
>  
> I started with the spaghetti sequence from the downstream kernel. I unravelled 
> it, and was so happy the code worked, that I forgot to check the numbering. 
> I'll remove the numbers, as they don't add much value..
> 
>>> +	/*set CFG[18:15]=1*/
>>> +	val = readl(wcss->rmb_base + SSCAON_CONFIG);
>>> +	val &= ~SSCAON_MASK;
>>> +	val |= SSCAON_BUS_EN;
>>> +	writel(val, wcss->rmb_base + SSCAON_CONFIG);
>>> +
>>> +	/*9. Wait for SSCAON_STATUS */
>>> +	ret = readl_poll_timeout(wcss->rmb_base + SSCAON_STATUS,
>>> +				 val, (val & 0xffff) == 0x10, 1000,
>>> +				 Q6SS_TIMEOUT_US * 1000);
>>> +	if (ret) {
>>> +		dev_err(wcss->dev, " Boot Error, SSCAON=0x%08X\n", 
> val);
>>> +		return ret;
>>
>> You left the clocks on in this path
> 
> Good catch! I will use "goto" centralized exiting to turn off resources on 
> failure.
> 
>>> +	}
>>> +
>>> +	/*3. BHS require xo cbcr to be enabled */
>>> +	val = readl(wcss->reg_base + Q6SS_XO_CBCR);
>>> +	val |= 0x1;
>>
>> That's BIT(0)
>>
>> In qcom_q6v5_mss.c you'll notice this is defined as Q6SS_CBCR_CLKEN
>>
>> If you dig a little deeper, you'll also notice a similar name in
>> drivers/clk/qcom/clk-branch.[ch].. I suppose they just reused the same
>> kind of HW on the remoteproc side
> 
> I'll use the macro name as suggested. Thank you!
> 
>>> +	writel(val, wcss->reg_base + Q6SS_XO_CBCR);
>>> +
>>> +	/*4. Enable core cbcr*/
>>> +	val = readl(wcss->reg_base + Q6SS_CORE_CBCR);
>>> +	val |= 0x1;
>>> +	writel(val, wcss->reg_base + Q6SS_CORE_CBCR);
>>> +
>>> +	/*5. Enable sleep cbcr*/
>>> +	val = readl(wcss->reg_base + Q6SS_SLEEP_CBCR);
>>> +	val |= 0x1;
>>> +	writel(val, wcss->reg_base + Q6SS_SLEEP_CBCR);
>>> +
>>> +	/*6. Boot core start */
>>> +	writel(0x1, wcss->reg_base + Q6SS_BOOT_CORE_START);
>>> +	writel(0x1, wcss->reg_base + Q6SS_BOOT_CMD);
>>> +
>>> +	/*7. Pray god and wait for reset to complete*/
>>
>> "ora et labora" - you've done your work, so I'd assume we can
>> expect success now
>>
>>> +	ret = readl_poll_timeout(wcss->reg_base + Q6SS_BOOT_STATUS, val,
>>> +				 (val & 0x01), 20000, 1000);
>>
>> The timeout is smaller than the retry delay value, this will only spin
>> once
>>
>> 0x01 is also BIT(0)
>>
>> But since you never check whether that timeout has actually been
>> reached, I assume you really stand by the comment!
>>
>> (you need this hunk):
>> if (ret) {
>> 	dev_err(wcss->dev, "WCSS boot timed out\n");
>> 	// cleanup
>> 	return -ETIMEDOUT;
>> }
> 
> Good catches! Yes, I definitely meant 20 millisecond timeout (not 1 ms). I will 
> also add the error checking.
> 
>>> +
>>> +	/* Enable non-Q6 clocks */
>>> +	ret = clk_bulk_prepare_enable(wcss->num_clks, wcss->clks);
>>> +	if (ret) {
>>> +		dev_err(wcss->dev, "failed to enable clocks, err=%d\n", 
> ret);
>>
>> the previous set of clocks will be left enabled in this case too
>>
>>> +		return ret;
>>> +	};
>>> +
>>> +	return 0;
>>
>> If you return ret here, you can drop the return in the above scope
> 
> This part will get changed a bit by the centralized exiting. It will be a 
> "goto" (on error) followed by "return 0" (on success).
> 
>>> +}
>>> +
>>>
>>>  static int q6v5_wcss_start(struct rproc *rproc)
>>>  {
>>>  
>>>  	struct q6v5_wcss *wcss = rproc->priv;
>>>
>>> @@ -270,10 +366,20 @@ static int q6v5_wcss_start(struct rproc *rproc)
>>>
>>>  	if (ret)
>>>  	
>>>  		goto wcss_q6_reset;
>>>
>>> -	/* Write bootaddr to EVB so that Q6WCSS will jump there after 
> reset */
>>> -	writel(rproc->bootaddr >> 4, wcss->reg_base + Q6SS_RST_EVB);
>>> +	switch (wcss->version) {
>>> +	case WCSS_QCS404:
>>> +	case WCSS_IPQ8074:
>>> +		/* Write bootaddr to EVB so that Q6WCSS will jump there 
> after
>>> +		 * reset.
>>> +		 */
>>
>> /* foo */?
> 
> I was trying to keep it at 80 characters, but since I will shorten this 
> comment on the new code paths, I will shorten it here too.
> 
>> [...]
>>
>>> +static void q6v7_q6_powerdown(struct q6v5_wcss *wcss)
>>> +{
>>> +	uint32_t val;
>>
>> "u32"
> 
> Okay.
> 
>>> +
>>> +	q6v5_wcss_halt_axi_port(wcss, wcss->halt_map, wcss->halt_q6);
>>> +
>>> +	/* Disable Q6 Core clock -- we don't know what bit 0 means */
>>
>> I would assume clearing it muxes the clocksource to XO
>>
>> [...]
>>
>>> +static int ipq9574_init_clocks(struct q6v5_wcss *wcss)
>>> +{
>>> +	static const char *const q6_clks[] = {
>>> +		"anoc_wcss_axi_m", "q6_ahb", "q6_ahb_s", "q6_axim", 
> "q6ss_boot",
>>> +		"mem_noc_q6_axi", "sys_noc_wcss_ahb", "wcss_acmt", 
> "wcss_ecahb",
>>> +		"wcss_q6_tbu" };
>>> +	static const char *const clks[] = {
>>> +		"q6_axim2", "wcss_ahb_s", "wcss_axi_m" };
>>
>> static local variables that we point to? eeeeeeh
> 
> I wanted "const char *clks[]" originally. I changed it to this in order to 
> appease checkpatch. Should I use my original "const char * []" instead?
> 
> [...]
> 
> Alex
> 
> 
> 
> 


^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574
  2025-12-24  9:44       ` Vignesh Viswanathan
@ 2025-12-24 17:36         ` Alex G.
  0 siblings, 0 replies; 31+ messages in thread
From: Alex G. @ 2025-12-24 17:36 UTC (permalink / raw)
  To: andersson, mathieu.poirier, Konrad Dybcio, linux-kernel,
	Vignesh Viswanathan
  Cc: krzk+dt, Philipp Zabel, linux-arm-msm, linux-remoteproc

On Wednesday, December 24, 2025 3:44:56 AM CST Vignesh Viswanathan wrote:
> On 12/24/2025 1:51 AM, Alex G. wrote:
> > On Friday, December 19, 2025 7:20:04 AM CST Konrad Dybcio wrote:
> >> On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
> >>> Q6 based firmware loading is also present on IPQ9574, when coupled
> >>> with a wifi-6 device, such as QCN5024. Populate driver data for
> >>> IPQ9574 with values from the downstream 5.4 kerrnel.
> >>> 
> >>> Add the new sequences for the WCSS reset and stop. The downstream
> >>> 5.4 kernel calls these "Q6V7", so keep the name. This is still worth
> >>> using with the "q6v5" driver because all other parts of the driver
> >>> can be seamlessly reused.
> >>> 
> >>> The IPQ9574 uses two sets of clocks. the first, dubbed "q6_clocks"
> >>> must be enabled before the Q6 is started by writing the Q6SS_RST_EVB
> >>> register. The second set of clocks, "clks" should only be enabled
> >>> after the Q6 is placed out of reset. Otherwise, the host CPU core that
> >>> tries to start the remoteproc will hang.
> >>> 
> >>> The downstream kernel had a funny comment, "Pray god and wait for
> >>> reset to complete", which I decided to keep for entertainment value.
> >>> 
> >>> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
> >>> ---
> >> 
> >> [...]
> >> 
> >>> @@ -128,6 +137,12 @@ struct q6v5_wcss {
> >>> 
> >>>  	struct clk *qdsp6ss_xo_cbcr;
> >>>  	struct clk *qdsp6ss_core_gfmux;
> >>>  	struct clk *lcc_bcr_sleep;
> >>> 
> >>> +	struct clk_bulk_data *clks;
> >>> +	/* clocks that must be started before the Q6 is booted */
> >>> +	struct clk_bulk_data *q6_clks;
> >> 
> >> "pre_boot_clks" or something along those lines?
> > 
> > I like "pre_boot_clocks".
> > 
> >> In general i'm not super stoked to see another platform where manual and
> >> through-TZ bringup of remoteprocs is supposed to be supported in
> >> parallel..
> >> 
> >> Are you sure your firmware doesn't allow you to just do a simple
> >> qcom_scm_pas_auth_and_reset() like in the multipd series?
> > 
> > I am approaching this from the perspective of an aftermarket OS, like
> > OpenWRT. I don't know if the firmware will do the right thing. I can
> > mitigate this for OS-loaded firmware, like ath11k 16/m3 firmware, because
> > I can test the driver and firmware together. I can't do that for
> > bootloader-loaded firmware, so I try to depend on it as little as
> > possible. I hope that native remoterproc loading for IPQ9574 will be
> > allowed.

Hi Vignesh,

> Does this rproc start sequence work on IPQ9574 without using the
> qcom_scm_pas_auth_and_reset ?

Yes, it works as presented in this series, without 
qcom_scm_pas_auth_and_reset().

Alex





^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574
  2025-12-23 20:21     ` Alex G.
  2025-12-24  9:44       ` Vignesh Viswanathan
@ 2025-12-29 12:35       ` Konrad Dybcio
  2026-01-05 16:09         ` mr.nuke.me
  1 sibling, 1 reply; 31+ messages in thread
From: Konrad Dybcio @ 2025-12-29 12:35 UTC (permalink / raw)
  To: Alex G., andersson, mathieu.poirier, linux-kernel
  Cc: krzk+dt, Philipp Zabel, linux-arm-msm, linux-remoteproc

On 12/23/25 9:21 PM, Alex G. wrote:
> On Friday, December 19, 2025 7:20:04 AM CST Konrad Dybcio wrote:
>> On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
>>> Q6 based firmware loading is also present on IPQ9574, when coupled
>>> with a wifi-6 device, such as QCN5024. Populate driver data for
>>> IPQ9574 with values from the downstream 5.4 kerrnel.
>>>
>>> Add the new sequences for the WCSS reset and stop. The downstream
>>> 5.4 kernel calls these "Q6V7", so keep the name. This is still worth
>>> using with the "q6v5" driver because all other parts of the driver
>>> can be seamlessly reused.
>>>
>>> The IPQ9574 uses two sets of clocks. the first, dubbed "q6_clocks"
>>> must be enabled before the Q6 is started by writing the Q6SS_RST_EVB
>>> register. The second set of clocks, "clks" should only be enabled
>>> after the Q6 is placed out of reset. Otherwise, the host CPU core that
>>> tries to start the remoteproc will hang.
>>>
>>> The downstream kernel had a funny comment, "Pray god and wait for
>>> reset to complete", which I decided to keep for entertainment value.
>>>
>>> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
>>> ---
>>
>> [...]
>>
>>> @@ -128,6 +137,12 @@ struct q6v5_wcss {
>>>
>>>  	struct clk *qdsp6ss_xo_cbcr;
>>>  	struct clk *qdsp6ss_core_gfmux;
>>>  	struct clk *lcc_bcr_sleep;
>>>
>>> +	struct clk_bulk_data *clks;
>>> +	/* clocks that must be started before the Q6 is booted */
>>> +	struct clk_bulk_data *q6_clks;
>>
>> "pre_boot_clks" or something along those lines?
> 
> I like "pre_boot_clocks".
> 
>> In general i'm not super stoked to see another platform where manual and
>> through-TZ bringup of remoteprocs is supposed to be supported in parallel..
>>
>> Are you sure your firmware doesn't allow you to just do a simple
>> qcom_scm_pas_auth_and_reset() like in the multipd series?
> 
> I am approaching this from the perspective of an aftermarket OS, like OpenWRT. 
> I don't know if the firmware will do the right thing. I can mitigate this for 
> OS-loaded firmware, like ath11k 16/m3 firmware, because I can test the driver 
> and firmware together. I can't do that for bootloader-loaded firmware, so I try 
> to depend on it as little as possible. I hope that native remoterproc loading 
> for IPQ9574 will be allowed.

These are two parallel questions. I didn't even know that the bootloader
preloaded firmware on these platforms (are you sure that's the case?)

qcom_scm_pas_auth_and_reset() is usually preceded by qcom_mdt_pas_init() +
qcom_mdt_load_no_init() where *you* supply the loadable firmware for the
remote processor.

The init sequence provided by this interface will be at worst identical to
what you're proposing here (except abstracted out), and at best containing
some fixes and/or workarounds that may be necessary. Please try using PAS
and see if that works.

Konrad

^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 7/9] remoteproc: qcom_q6v5_wcss: support m3 firmware
  2025-12-23 20:35     ` Alex G.
@ 2025-12-29 12:37       ` Konrad Dybcio
  2026-01-05 15:23         ` mr.nuke.me
  0 siblings, 1 reply; 31+ messages in thread
From: Konrad Dybcio @ 2025-12-29 12:37 UTC (permalink / raw)
  To: Alex G., andersson
  Cc: mathieu.poirier, krzk+dt, linux-arm-msm, linux-remoteproc,
	linux-kernel

On 12/23/25 9:35 PM, Alex G. wrote:
> On Friday, December 19, 2025 7:29:07 AM CST Konrad Dybcio wrote:
>> On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
>>> IPQ8074, IPQ6018, and IPQ9574 support an m3 firmware image in addtion
>>> to the q6 firmware. The firmware releases from qcom provide both q6
>>> and m3 firmware for these SoCs. Support loading the m3 firmware image.
>>>
>>> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
>>> ---

[...]

>>> +static int q6v5_wcss_load_aux(struct q6v5_wcss *wcss, const char
>>> *fw_name)
>>> +{
>>> +	const struct firmware *extra_fw;
>>> +	int ret;
>>> +
>>> +	dev_info(wcss->dev, "loading additional firmware image %s\n", 
> fw_name);

Your email client is messing up the reply context - if it happens to
be Thunderbird, set:

mailnews.wraplength = 0
mailnews.send_plaintext_flowed = false

in the config

>>
>> I don't think this log line is useful beyond development
> 
> Remoteproc driver prints the main (q6) fimrware name, so I thought it would be 
> prudent to print the names of any additional firmwares:
> 
>     remoteproc remoteproc0: Booting fw image IPQ9574/q6_fw.mdt, size 8140
> 
>>> +
>>> +	ret = request_firmware(&extra_fw, fw_name, wcss->dev);
>>> +	if (ret)
>>> +		return 0;
>>
>> return ret, perhaps? Unless you want to say that "it's fine if the M3 image
>> is missing, particularly not to impose any new requirements on existing
>> setups". But you haven't spelt that out explicitly.
> 
> I intended to not abort when aux firmware is missing. Maybe the better way to 
> handle this is to check for "-ENOENT" in the caller instead of return 0 here.
> 
>> You also haven't provided an explanation as to why the firmware should be
>> loaded. Is it necessary for some functionality? Is it that case on the
>> newly-supported IPQ9574?
> 
> I don't have a good answer. I reasoned that since the qcom provides it [1], 
> the M3 firmware would need to be loaded. I haven't done much testing without 
> it.

Well, could you please try?

IIRC it was strictly necessary for ATH1xk-on-PCIe so I'm assuming it's going
to be a necessity here as well 

Konrad

^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 7/9] remoteproc: qcom_q6v5_wcss: support m3 firmware
  2025-12-29 12:37       ` Konrad Dybcio
@ 2026-01-05 15:23         ` mr.nuke.me
  2026-01-05 18:00           ` Vignesh Viswanathan
  0 siblings, 1 reply; 31+ messages in thread
From: mr.nuke.me @ 2026-01-05 15:23 UTC (permalink / raw)
  To: Konrad Dybcio, andersson
  Cc: mathieu.poirier, krzk+dt, linux-arm-msm, linux-remoteproc,
	linux-kernel



On 12/29/25 6:37 AM, Konrad Dybcio wrote:
> On 12/23/25 9:35 PM, Alex G. wrote:
>> On Friday, December 19, 2025 7:29:07 AM CST Konrad Dybcio wrote:
>>> On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
>>>> IPQ8074, IPQ6018, and IPQ9574 support an m3 firmware image in addtion
>>>> to the q6 firmware. The firmware releases from qcom provide both q6
>>>> and m3 firmware for these SoCs. Support loading the m3 firmware image.
>>>>
>>>> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
>>>> ---
> 
> [...]
> 
>>>> +static int q6v5_wcss_load_aux(struct q6v5_wcss *wcss, const char
>>>> *fw_name)
>>>> +{
>>>> +	const struct firmware *extra_fw;
>>>> +	int ret;
>>>> +
>>>> +	dev_info(wcss->dev, "loading additional firmware image %s\n",
>> fw_name);
> 
> Your email client is messing up the reply context - if it happens to
> be Thunderbird, set:
> 
> mailnews.wraplength = 0
> mailnews.send_plaintext_flowed = false
> 
> in the config

Oops.
>>>
>>> I don't think this log line is useful beyond development
>>
>> Remoteproc driver prints the main (q6) fimrware name, so I thought it would be
>> prudent to print the names of any additional firmwares:
>>
>>      remoteproc remoteproc0: Booting fw image IPQ9574/q6_fw.mdt, size 8140
>>
>>>> +
>>>> +	ret = request_firmware(&extra_fw, fw_name, wcss->dev);
>>>> +	if (ret)
>>>> +		return 0;
>>>
>>> return ret, perhaps? Unless you want to say that "it's fine if the M3 image
>>> is missing, particularly not to impose any new requirements on existing
>>> setups". But you haven't spelt that out explicitly.
>>
>> I intended to not abort when aux firmware is missing. Maybe the better way to
>> handle this is to check for "-ENOENT" in the caller instead of return 0 here.
>>
>>> You also haven't provided an explanation as to why the firmware should be
>>> loaded. Is it necessary for some functionality? Is it that case on the
>>> newly-supported IPQ9574?
>>
>> I don't have a good answer. I reasoned that since the qcom provides it [1],
>> the M3 firmware would need to be loaded. I haven't done much testing without
>> it.
> 
> Well, could you please try?
> 
> IIRC it was strictly necessary for ATH1xk-on-PCIe so I'm assuming it's going
> to be a necessity here as well

I tried this without the M3 firmware, and I don't see a measurable 
difference in normal operation. I only tested AP mode briefly. How can I 
know for sure if the M3 firmware is needed or not?

Alex

^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574
  2025-12-29 12:35       ` Konrad Dybcio
@ 2026-01-05 16:09         ` mr.nuke.me
  2026-01-05 17:57           ` Vignesh Viswanathan
  0 siblings, 1 reply; 31+ messages in thread
From: mr.nuke.me @ 2026-01-05 16:09 UTC (permalink / raw)
  To: Konrad Dybcio, andersson, mathieu.poirier, linux-kernel
  Cc: krzk+dt, Philipp Zabel, linux-arm-msm, linux-remoteproc



On 12/29/25 6:35 AM, Konrad Dybcio wrote:
> On 12/23/25 9:21 PM, Alex G. wrote:
>> On Friday, December 19, 2025 7:20:04 AM CST Konrad Dybcio wrote:
>>> On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
>>>> Q6 based firmware loading is also present on IPQ9574, when coupled
>>>> with a wifi-6 device, such as QCN5024. Populate driver data for
>>>> IPQ9574 with values from the downstream 5.4 kerrnel.
>>>>
>>>> Add the new sequences for the WCSS reset and stop. The downstream
>>>> 5.4 kernel calls these "Q6V7", so keep the name. This is still worth
>>>> using with the "q6v5" driver because all other parts of the driver
>>>> can be seamlessly reused.
>>>>
>>>> The IPQ9574 uses two sets of clocks. the first, dubbed "q6_clocks"
>>>> must be enabled before the Q6 is started by writing the Q6SS_RST_EVB
>>>> register. The second set of clocks, "clks" should only be enabled
>>>> after the Q6 is placed out of reset. Otherwise, the host CPU core that
>>>> tries to start the remoteproc will hang.
>>>>
>>>> The downstream kernel had a funny comment, "Pray god and wait for
>>>> reset to complete", which I decided to keep for entertainment value.
>>>>
>>>> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
>>>> ---
>>>
>>> [...]
>>>
>>>> @@ -128,6 +137,12 @@ struct q6v5_wcss {
>>>>
>>>>   	struct clk *qdsp6ss_xo_cbcr;
>>>>   	struct clk *qdsp6ss_core_gfmux;
>>>>   	struct clk *lcc_bcr_sleep;
>>>>
>>>> +	struct clk_bulk_data *clks;
>>>> +	/* clocks that must be started before the Q6 is booted */
>>>> +	struct clk_bulk_data *q6_clks;
>>>
>>> "pre_boot_clks" or something along those lines?
>>
>> I like "pre_boot_clocks".
>>
>>> In general i'm not super stoked to see another platform where manual and
>>> through-TZ bringup of remoteprocs is supposed to be supported in parallel..
>>>
>>> Are you sure your firmware doesn't allow you to just do a simple
>>> qcom_scm_pas_auth_and_reset() like in the multipd series?
>>
>> I am approaching this from the perspective of an aftermarket OS, like OpenWRT.
>> I don't know if the firmware will do the right thing. I can mitigate this for
>> OS-loaded firmware, like ath11k 16/m3 firmware, because I can test the driver
>> and firmware together. I can't do that for bootloader-loaded firmware, so I try
>> to depend on it as little as possible. I hope that native remoterproc loading
>> for IPQ9574 will be allowed.
> 
> These are two parallel questions. I didn't even know that the bootloader
> preloaded firmware on these platforms (are you sure that's the case?)
> 
> qcom_scm_pas_auth_and_reset() is usually preceded by qcom_mdt_pas_init() +
> qcom_mdt_load_no_init() where *you* supply the loadable firmware for the
> remote processor.

What I mean is that the init sequence is implemented in the trustzone 
firmware which is loaded at boot time. Irrespective of what Q6 and M3 
firmware I supply, if trustzone doesn't cooperate, I can't start the 
remoteproc. I don't have that problem when the init sequence is 
implemented in the kernel.

> The init sequence provided by this interface will be at worst identical to
> what you're proposing here (except abstracted out), and at best containing
> some fixes and/or workarounds that may be necessary.

I think this portrays the TZ path as somehow superior. That's not how 
things work in my use casee.

The bootloader/FW versions depends on when and who made the device. So 
while the newest TZ from upstream may have the latest fixes, I have no 
guarantee that they will be present on a given device at runtime. The 
best solution I found to get consistent behavior across devices is to do 
these sequences from the kernel. Is there something incomplete in my 
init sequence that I can fix?

  > Please try using PAS and see if that works.

I found the v6 of the multipd series [1]. It needed some minor 
adjustments to compile. I went as far as loading the Q6 firmware and 
starting the remoteproc without error. I did not test any further.

Alex

[1] 
https://patchwork.kernel.org/project/linux-remoteproc/patch/20231110091939.3025413-1-quic_mmanikan@quicinc.com/


^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574
  2026-01-05 16:09         ` mr.nuke.me
@ 2026-01-05 17:57           ` Vignesh Viswanathan
  0 siblings, 0 replies; 31+ messages in thread
From: Vignesh Viswanathan @ 2026-01-05 17:57 UTC (permalink / raw)
  To: mr.nuke.me, Konrad Dybcio, andersson, mathieu.poirier,
	linux-kernel
  Cc: krzk+dt, Philipp Zabel, linux-arm-msm, linux-remoteproc



On 1/5/2026 9:39 PM, mr.nuke.me@gmail.com wrote:
> 
> 
> On 12/29/25 6:35 AM, Konrad Dybcio wrote:
>> On 12/23/25 9:21 PM, Alex G. wrote:
>>> On Friday, December 19, 2025 7:20:04 AM CST Konrad Dybcio wrote:
>>>> On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
>>>>> Q6 based firmware loading is also present on IPQ9574, when coupled
>>>>> with a wifi-6 device, such as QCN5024. Populate driver data for
>>>>> IPQ9574 with values from the downstream 5.4 kerrnel.
>>>>>
>>>>> Add the new sequences for the WCSS reset and stop. The downstream
>>>>> 5.4 kernel calls these "Q6V7", so keep the name. This is still worth
>>>>> using with the "q6v5" driver because all other parts of the driver
>>>>> can be seamlessly reused.
>>>>>
>>>>> The IPQ9574 uses two sets of clocks. the first, dubbed "q6_clocks"
>>>>> must be enabled before the Q6 is started by writing the Q6SS_RST_EVB
>>>>> register. The second set of clocks, "clks" should only be enabled
>>>>> after the Q6 is placed out of reset. Otherwise, the host CPU core that
>>>>> tries to start the remoteproc will hang.
>>>>>
>>>>> The downstream kernel had a funny comment, "Pray god and wait for
>>>>> reset to complete", which I decided to keep for entertainment value.
>>>>>
>>>>> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
>>>>> ---
>>>>
>>>> [...]
>>>>
>>>>> @@ -128,6 +137,12 @@ struct q6v5_wcss {
>>>>>
>>>>>       struct clk *qdsp6ss_xo_cbcr;
>>>>>       struct clk *qdsp6ss_core_gfmux;
>>>>>       struct clk *lcc_bcr_sleep;
>>>>>
>>>>> +    struct clk_bulk_data *clks;
>>>>> +    /* clocks that must be started before the Q6 is booted */
>>>>> +    struct clk_bulk_data *q6_clks;
>>>>
>>>> "pre_boot_clks" or something along those lines?
>>>
>>> I like "pre_boot_clocks".
>>>
>>>> In general i'm not super stoked to see another platform where manual and
>>>> through-TZ bringup of remoteprocs is supposed to be supported in parallel..
>>>>
>>>> Are you sure your firmware doesn't allow you to just do a simple
>>>> qcom_scm_pas_auth_and_reset() like in the multipd series?
>>>
>>> I am approaching this from the perspective of an aftermarket OS, like OpenWRT.
>>> I don't know if the firmware will do the right thing. I can mitigate this for
>>> OS-loaded firmware, like ath11k 16/m3 firmware, because I can test the driver
>>> and firmware together. I can't do that for bootloader-loaded firmware, so I try
>>> to depend on it as little as possible. I hope that native remoterproc loading
>>> for IPQ9574 will be allowed.
>>
>> These are two parallel questions. I didn't even know that the bootloader
>> preloaded firmware on these platforms (are you sure that's the case?)
>>
>> qcom_scm_pas_auth_and_reset() is usually preceded by qcom_mdt_pas_init() +
>> qcom_mdt_load_no_init() where *you* supply the loadable firmware for the
>> remote processor.
> 
> What I mean is that the init sequence is implemented in the trustzone firmware which is loaded at boot time. Irrespective of what Q6 and M3 firmware I supply, if trustzone doesn't cooperate, I can't start the remoteproc. I don't have that problem when the init sequence is implemented in the kernel.
> 
>> The init sequence provided by this interface will be at worst identical to
>> what you're proposing here (except abstracted out), and at best containing
>> some fixes and/or workarounds that may be necessary.
> 
> I think this portrays the TZ path as somehow superior. That's not how things work in my use casee.

Adding my 2 cents here, in some platforms, the regions which you are accessing
as part of the init sequence might be access protected by Trustzone.
This might lead to the kernel bringup failing due to an access violation.

This was the motivation behind me asking if this worked in my previous email.
Using the TZ interface, as suggested by Konrad, should work in any case.

Thanks,
Vignesh

> 
> The bootloader/FW versions depends on when and who made the device. So while the newest TZ from upstream may have the latest fixes, I have no guarantee that they will be present on a given device at runtime. The best solution I found to get consistent behavior across devices is to do these sequences from the kernel. Is there something incomplete in my init sequence that I can fix?
> 
>  > Please try using PAS and see if that works.
> 
> I found the v6 of the multipd series [1]. It needed some minor adjustments to compile. I went as far as loading the Q6 firmware and starting the remoteproc without error. I did not test any further.
> 
> Alex
> 
> [1] https://patchwork.kernel.org/project/linux-remoteproc/patch/20231110091939.3025413-1-quic_mmanikan@quicinc.com/
> 
> 


^ permalink raw reply	[flat|nested] 31+ messages in thread

* Re: [PATCH 7/9] remoteproc: qcom_q6v5_wcss: support m3 firmware
  2026-01-05 15:23         ` mr.nuke.me
@ 2026-01-05 18:00           ` Vignesh Viswanathan
  0 siblings, 0 replies; 31+ messages in thread
From: Vignesh Viswanathan @ 2026-01-05 18:00 UTC (permalink / raw)
  To: mr.nuke.me, Konrad Dybcio, andersson, jeff.johnson
  Cc: mathieu.poirier, krzk+dt, linux-arm-msm, linux-remoteproc,
	linux-kernel



On 1/5/2026 8:53 PM, mr.nuke.me@gmail.com wrote:
> 
> 
> On 12/29/25 6:37 AM, Konrad Dybcio wrote:
>> On 12/23/25 9:35 PM, Alex G. wrote:
>>> On Friday, December 19, 2025 7:29:07 AM CST Konrad Dybcio wrote:
>>>> On 12/19/25 5:34 AM, Alexandru Gagniuc wrote:
>>>>> IPQ8074, IPQ6018, and IPQ9574 support an m3 firmware image in addtion
>>>>> to the q6 firmware. The firmware releases from qcom provide both q6
>>>>> and m3 firmware for these SoCs. Support loading the m3 firmware image.
>>>>>
>>>>> Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
>>>>> ---
>>
>> [...]
>>
>>>>> +static int q6v5_wcss_load_aux(struct q6v5_wcss *wcss, const char
>>>>> *fw_name)
>>>>> +{
>>>>> +    const struct firmware *extra_fw;
>>>>> +    int ret;
>>>>> +
>>>>> +    dev_info(wcss->dev, "loading additional firmware image %s\n",
>>> fw_name);
>>
>> Your email client is messing up the reply context - if it happens to
>> be Thunderbird, set:
>>
>> mailnews.wraplength = 0
>> mailnews.send_plaintext_flowed = false
>>
>> in the config
> 
> Oops.
>>>>
>>>> I don't think this log line is useful beyond development
>>>
>>> Remoteproc driver prints the main (q6) fimrware name, so I thought it would be
>>> prudent to print the names of any additional firmwares:
>>>
>>>      remoteproc remoteproc0: Booting fw image IPQ9574/q6_fw.mdt, size 8140
>>>
>>>>> +
>>>>> +    ret = request_firmware(&extra_fw, fw_name, wcss->dev);
>>>>> +    if (ret)
>>>>> +        return 0;
>>>>
>>>> return ret, perhaps? Unless you want to say that "it's fine if the M3 image
>>>> is missing, particularly not to impose any new requirements on existing
>>>> setups". But you haven't spelt that out explicitly.
>>>
>>> I intended to not abort when aux firmware is missing. Maybe the better way to
>>> handle this is to check for "-ENOENT" in the caller instead of return 0 here.
>>>
>>>> You also haven't provided an explanation as to why the firmware should be
>>>> loaded. Is it necessary for some functionality? Is it that case on the
>>>> newly-supported IPQ9574?
>>>
>>> I don't have a good answer. I reasoned that since the qcom provides it [1],
>>> the M3 firmware would need to be loaded. I haven't done much testing without
>>> it.
>>
>> Well, could you please try?
>>
>> IIRC it was strictly necessary for ATH1xk-on-PCIe so I'm assuming it's going
>> to be a necessity here as well
> 
> I tried this without the M3 firmware, and I don't see a measurable difference in normal operation. I only tested AP mode briefly. How can I know for sure if the M3 firmware is needed or not?

AFAIK, M3 Firmware is required for an underlying sub-processor which is used
by the Wi-Fi subsystem.

Hi Jeff,

Is there any upstream facing documentation on the need for M3 Firmware ?

Thanks,
Vignesh


> 
> Alex
> 


^ permalink raw reply	[flat|nested] 31+ messages in thread

end of thread, other threads:[~2026-01-05 18:00 UTC | newest]

Thread overview: 31+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-12-19  4:34 [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Alexandru Gagniuc
2025-12-19  4:34 ` [PATCH 2/9] dt-bindings: remoteproc: qcom: add IPQ9574 image loader Alexandru Gagniuc
2025-12-19  5:37   ` Rob Herring (Arm)
2025-12-19 14:44   ` Rob Herring
2025-12-20  8:54     ` Krzysztof Kozlowski
2025-12-23 19:45       ` Alex G.
2025-12-20  8:56   ` Krzysztof Kozlowski
2025-12-19  4:34 ` [PATCH 3/9] dt-bindings: clock: gcc-ipq9574: add wcss remoteproc clocks Alexandru Gagniuc
2025-12-19  4:34 ` [PATCH 4/9] arm64: dts: qcom: ipq9574: add wcss remoteproc nodes Alexandru Gagniuc
2025-12-19 13:43   ` Konrad Dybcio
2025-12-19  4:34 ` [PATCH 5/9] clk: qcom: gcc-ipq9574: add wcss remoteproc clocks Alexandru Gagniuc
2025-12-19  4:34 ` [PATCH 6/9] remoteproc: qcom_q6v5_wcss: support IPQ9574 Alexandru Gagniuc
2025-12-19 13:20   ` Konrad Dybcio
2025-12-23 20:21     ` Alex G.
2025-12-24  9:44       ` Vignesh Viswanathan
2025-12-24 17:36         ` Alex G.
2025-12-29 12:35       ` Konrad Dybcio
2026-01-05 16:09         ` mr.nuke.me
2026-01-05 17:57           ` Vignesh Viswanathan
2025-12-19  4:34 ` [PATCH 7/9] remoteproc: qcom_q6v5_wcss: support m3 firmware Alexandru Gagniuc
2025-12-19 13:29   ` Konrad Dybcio
2025-12-23 20:35     ` Alex G.
2025-12-29 12:37       ` Konrad Dybcio
2026-01-05 15:23         ` mr.nuke.me
2026-01-05 18:00           ` Vignesh Viswanathan
2025-12-19  4:34 ` [PATCH 8/9] remoteproc: qcom_q6v5_wcss: drop unused clocks from q6v5 struct Alexandru Gagniuc
2025-12-19 13:31   ` Konrad Dybcio
2025-12-19  4:34 ` [PATCH 9/9] remoteproc: qcom_q6v5_wcss: use bulk clk API for q6 clocks in QCS404 Alexandru Gagniuc
2025-12-19 14:52 ` [PATCH 1/9] dt-bindings: remoteproc: qcom,ipq8074-wcss-pil: convert to DT schema Krzysztof Kozlowski
2025-12-20 18:40   ` Alex G.
2025-12-19 16:49 ` Rob Herring

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).