aboutsummaryrefslogtreecommitdiffstats
path: root/recipes-kernel/linux/linux-yocto/generic-drivers
diff options
context:
space:
mode:
Diffstat (limited to 'recipes-kernel/linux/linux-yocto/generic-drivers')
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/0001-FROMLIST-dma-heap-Add-proper-kref-handling-on-dma-bu.patch145
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/0002-FROMLIST-dma-heap-Provide-accessors-so-that-in-kerne.patch180
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/icc/0001-interconnect-qcom-icc-rpm-Add-AB-IB-calculations-coe.patch97
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/icc/0002-interconnect-qcom-icc-rpm-Separate-out-clock-rate-ca.patch100
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/icc/0003-interconnect-qcom-icc-rpm-Let-nodes-drive-their-own-.patch99
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/icc/0004-interconnect-qcom-icc-rpm-Check-for-node-specific-ra.patch82
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/icc/0005-interconnect-qcom-qcm2290-Hook-up-MAS_APPS_PROC-s-bu.patch69
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/icc/0006-interconnect-qcom-qcm2290-Set-AB-coefficients.patch47
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/icc/0007-interconnect-qcom-qcm2290-Update-EBI-channel-configu.patch43
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/icc/0008-interconnect-qcom-sdm660-Set-AB-IB-coefficients.patch55
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/icc/0009-interconnect-qcom-msm8996-Set-AB-IB-coefficients.patch59
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0001_drm_msm_mdss_switch_mdss_to_use_devm_of_icc_get.patch64
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0002_drm_msm_mdss_rename_path_references_to_mdp_path.patch66
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0002_dt_bindings_display_msm_add_reg_bus_and_rotator_interconnects.patch287
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0003_drm_msm_mdss_inline_msm_mdss_icc_request_bw.patch69
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0004_drm_msm_mdss_handle_the_reg_bus_icc_path.patch238
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/mpm/0001-dt-bindings-interrupt-controller-mpm-Pass-MSG-RAM-sl.patch72
-rw-r--r--recipes-kernel/linux/linux-yocto/generic-drivers/mpm/0002-irqchip-irq-qcom-mpm-Support-passing-a-slice-of-SRAM.patch78
18 files changed, 1850 insertions, 0 deletions
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/0001-FROMLIST-dma-heap-Add-proper-kref-handling-on-dma-bu.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/0001-FROMLIST-dma-heap-Add-proper-kref-handling-on-dma-bu.patch
new file mode 100644
index 0000000..87fefa9
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/0001-FROMLIST-dma-heap-Add-proper-kref-handling-on-dma-bu.patch
@@ -0,0 +1,145 @@
+From dd2c03120004f3bfed8b4f6500c33957b1bae807 Mon Sep 17 00:00:00 2001
+From: John Stultz <jstultz@google.com>
+Date: Mon, 11 Sep 2023 10:30:31 +0800
+Subject: [PATCH 1/2] FROMLIST: dma-heap: Add proper kref handling on dma-buf
+ heaps
+
+Add proper refcounting on the dma_heap structure.
+While existing heaps are built-in, we may eventually
+have heaps loaded from modules, and we'll need to be
+able to properly handle the references to the heaps
+
+Also moves minor tracking into the heap structure so
+we can properly free things.
+
+[Yong: Just add comment for "minor" and "refcount"]
+Signed-off-by: John Stultz <jstultz@google.com>
+Signed-off-by: T.J. Mercier <tjmercier@google.com>
+Signed-off-by: Yong Wu <yong.wu@mediatek.com>
+Signed-off-by: Vijayanand Jitta <quic_vjitta@quicinc.com>
+Signed-off-by: Atul Dhudase <quic_adhudase@quicinc.com>
+Upstream-Status: Submitted [https://lore.kernel.org/lkml/20230911023038.30649-3-yong.wu@mediatek.com/]
+---
+ drivers/dma-buf/dma-heap.c | 38 ++++++++++++++++++++++++++++++++++----
+ include/linux/dma-heap.h | 6 ++++++
+ 2 files changed, 40 insertions(+), 4 deletions(-)
+
+diff --git a/drivers/dma-buf/dma-heap.c b/drivers/dma-buf/dma-heap.c
+index 84ae708fafe7..59328045975a 100644
+--- a/drivers/dma-buf/dma-heap.c
++++ b/drivers/dma-buf/dma-heap.c
+@@ -12,6 +12,7 @@
+ #include <linux/dma-buf.h>
+ #include <linux/err.h>
+ #include <linux/xarray.h>
++#include <linux/kref.h>
+ #include <linux/list.h>
+ #include <linux/slab.h>
+ #include <linux/nospec.h>
+@@ -31,6 +32,8 @@
+ * @heap_devt heap device node
+ * @list list head connecting to list of heaps
+ * @heap_cdev heap char device
++ * @minor: heap device node minor number
++ * @refcount: reference counter for this heap device
+ *
+ * Represents a heap of memory from which buffers can be made.
+ */
+@@ -41,6 +44,8 @@ struct dma_heap {
+ dev_t heap_devt;
+ struct list_head list;
+ struct cdev heap_cdev;
++ int minor;
++ struct kref refcount;
+ };
+
+ static LIST_HEAD(heap_list);
+@@ -220,7 +225,6 @@ struct dma_heap *dma_heap_add(const struct dma_heap_export_info *exp_info)
+ {
+ struct dma_heap *heap, *h, *err_ret;
+ struct device *dev_ret;
+- unsigned int minor;
+ int ret;
+
+ if (!exp_info->name || !strcmp(exp_info->name, "")) {
+@@ -237,12 +241,13 @@ struct dma_heap *dma_heap_add(const struct dma_heap_export_info *exp_info)
+ if (!heap)
+ return ERR_PTR(-ENOMEM);
+
++ kref_init(&heap->refcount);
+ heap->name = exp_info->name;
+ heap->ops = exp_info->ops;
+ heap->priv = exp_info->priv;
+
+ /* Find unused minor number */
+- ret = xa_alloc(&dma_heap_minors, &minor, heap,
++ ret = xa_alloc(&dma_heap_minors, &heap->minor, heap,
+ XA_LIMIT(0, NUM_HEAP_MINORS - 1), GFP_KERNEL);
+ if (ret < 0) {
+ pr_err("dma_heap: Unable to get minor number for heap\n");
+@@ -251,7 +256,7 @@ struct dma_heap *dma_heap_add(const struct dma_heap_export_info *exp_info)
+ }
+
+ /* Create device */
+- heap->heap_devt = MKDEV(MAJOR(dma_heap_devt), minor);
++ heap->heap_devt = MKDEV(MAJOR(dma_heap_devt), heap->minor);
+
+ cdev_init(&heap->heap_cdev, &dma_heap_fops);
+ ret = cdev_add(&heap->heap_cdev, heap->heap_devt, 1);
+@@ -295,12 +300,37 @@ struct dma_heap *dma_heap_add(const struct dma_heap_export_info *exp_info)
+ err2:
+ cdev_del(&heap->heap_cdev);
+ err1:
+- xa_erase(&dma_heap_minors, minor);
++ xa_erase(&dma_heap_minors, heap->minor);
+ err0:
+ kfree(heap);
+ return err_ret;
+ }
+
++static void dma_heap_release(struct kref *ref)
++{
++ struct dma_heap *heap = container_of(ref, struct dma_heap, refcount);
++
++ /* Note, we already holding the heap_list_lock here */
++ list_del(&heap->list);
++
++ device_destroy(dma_heap_class, heap->heap_devt);
++ cdev_del(&heap->heap_cdev);
++ xa_erase(&dma_heap_minors, heap->minor);
++
++ kfree(heap);
++}
++
++void dma_heap_put(struct dma_heap *h)
++{
++ /*
++ * Take the heap_list_lock now to avoid racing with code
++ * scanning the list and then taking a kref.
++ */
++ mutex_lock(&heap_list_lock);
++ kref_put(&h->refcount, dma_heap_release);
++ mutex_unlock(&heap_list_lock);
++}
++
+ static char *dma_heap_devnode(const struct device *dev, umode_t *mode)
+ {
+ return kasprintf(GFP_KERNEL, "dma_heap/%s", dev_name(dev));
+diff --git a/include/linux/dma-heap.h b/include/linux/dma-heap.h
+index 0c05561cad6e..f8c986dd9a8b 100644
+--- a/include/linux/dma-heap.h
++++ b/include/linux/dma-heap.h
+@@ -65,4 +65,10 @@ const char *dma_heap_get_name(struct dma_heap *heap);
+ */
+ struct dma_heap *dma_heap_add(const struct dma_heap_export_info *exp_info);
+
++/**
++ * dma_heap_put - drops a reference to a dmabuf heap, potentially freeing it
++ * @heap: the heap whose reference count to decrement
++ */
++void dma_heap_put(struct dma_heap *heap);
++
+ #endif /* _DMA_HEAPS_H */
+--
+2.25.1
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/0002-FROMLIST-dma-heap-Provide-accessors-so-that-in-kerne.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/0002-FROMLIST-dma-heap-Provide-accessors-so-that-in-kerne.patch
new file mode 100644
index 0000000..f65b7cb
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/0002-FROMLIST-dma-heap-Provide-accessors-so-that-in-kerne.patch
@@ -0,0 +1,180 @@
+From fd0d8a09c8d928459d37ae535825018bb0594357 Mon Sep 17 00:00:00 2001
+From: John Stultz <jstultz@google.com>
+Date: Mon, 11 Sep 2023 10:30:32 +0800
+Subject: [PATCH 2/2] FROMLIST: dma-heap: Provide accessors so that in-kernel
+ drivers can allocate dmabufs from specific heaps
+
+This allows drivers who don't want to create their own
+DMA-BUF exporter to be able to allocate DMA-BUFs directly
+from existing DMA-BUF Heaps.
+
+There is some concern that the premise of DMA-BUF heaps is
+that userland knows better about what type of heap memory
+is needed for a pipeline, so it would likely be best for
+drivers to import and fill DMA-BUFs allocated by userland
+instead of allocating one themselves, but this is still
+up for debate.
+
+[Yong: Fix the checkpatch alignment warning]
+Signed-off-by: John Stultz <jstultz@google.com>
+Signed-off-by: T.J. Mercier <tjmercier@google.com>
+Signed-off-by: Yong Wu <yong.wu@mediatek.com>
+Signed-off-by: Vijayanand Jitta <quic_vjitta@quicinc.com>
+Signed-off-by: Atul Dhudase <quic_adhudase@quicinc.com>
+Upstream-Status: Submitted [https://lore.kernel.org/lkml/20230911023038.30649-4-yong.wu@mediatek.com/]
+---
+ drivers/dma-buf/dma-heap.c | 60 ++++++++++++++++++++++++++++----------
+ include/linux/dma-heap.h | 25 ++++++++++++++++
+ 2 files changed, 69 insertions(+), 16 deletions(-)
+
+diff --git a/drivers/dma-buf/dma-heap.c b/drivers/dma-buf/dma-heap.c
+index 59328045975a..e17705427b23 100644
+--- a/drivers/dma-buf/dma-heap.c
++++ b/drivers/dma-buf/dma-heap.c
+@@ -54,12 +54,15 @@ static dev_t dma_heap_devt;
+ static struct class *dma_heap_class;
+ static DEFINE_XARRAY_ALLOC(dma_heap_minors);
+
+-static int dma_heap_buffer_alloc(struct dma_heap *heap, size_t len,
+- unsigned int fd_flags,
+- unsigned int heap_flags)
++struct dma_buf *dma_heap_buffer_alloc(struct dma_heap *heap, size_t len,
++ unsigned int fd_flags,
++ unsigned int heap_flags)
+ {
+- struct dma_buf *dmabuf;
+- int fd;
++ if (fd_flags & ~DMA_HEAP_VALID_FD_FLAGS)
++ return ERR_PTR(-EINVAL);
++
++ if (heap_flags & ~DMA_HEAP_VALID_HEAP_FLAGS)
++ return ERR_PTR(-EINVAL);
+
+ /*
+ * Allocations from all heaps have to begin
+@@ -67,9 +70,20 @@ static int dma_heap_buffer_alloc(struct dma_heap *heap, size_t len,
+ */
+ len = PAGE_ALIGN(len);
+ if (!len)
+- return -EINVAL;
++ return ERR_PTR(-EINVAL);
+
+- dmabuf = heap->ops->allocate(heap, len, fd_flags, heap_flags);
++ return heap->ops->allocate(heap, len, fd_flags, heap_flags);
++}
++EXPORT_SYMBOL_GPL(dma_heap_buffer_alloc);
++
++static int dma_heap_bufferfd_alloc(struct dma_heap *heap, size_t len,
++ unsigned int fd_flags,
++ unsigned int heap_flags)
++{
++ struct dma_buf *dmabuf;
++ int fd;
++
++ dmabuf = dma_heap_buffer_alloc(heap, len, fd_flags, heap_flags);
+ if (IS_ERR(dmabuf))
+ return PTR_ERR(dmabuf);
+
+@@ -107,15 +121,9 @@ static long dma_heap_ioctl_allocate(struct file *file, void *data)
+ if (heap_allocation->fd)
+ return -EINVAL;
+
+- if (heap_allocation->fd_flags & ~DMA_HEAP_VALID_FD_FLAGS)
+- return -EINVAL;
+-
+- if (heap_allocation->heap_flags & ~DMA_HEAP_VALID_HEAP_FLAGS)
+- return -EINVAL;
+-
+- fd = dma_heap_buffer_alloc(heap, heap_allocation->len,
+- heap_allocation->fd_flags,
+- heap_allocation->heap_flags);
++ fd = dma_heap_bufferfd_alloc(heap, heap_allocation->len,
++ heap_allocation->fd_flags,
++ heap_allocation->heap_flags);
+ if (fd < 0)
+ return fd;
+
+@@ -220,6 +228,7 @@ const char *dma_heap_get_name(struct dma_heap *heap)
+ {
+ return heap->name;
+ }
++EXPORT_SYMBOL_GPL(dma_heap_get_name);
+
+ struct dma_heap *dma_heap_add(const struct dma_heap_export_info *exp_info)
+ {
+@@ -305,6 +314,24 @@ struct dma_heap *dma_heap_add(const struct dma_heap_export_info *exp_info)
+ kfree(heap);
+ return err_ret;
+ }
++EXPORT_SYMBOL_GPL(dma_heap_add);
++
++struct dma_heap *dma_heap_find(const char *name)
++{
++ struct dma_heap *h;
++
++ mutex_lock(&heap_list_lock);
++ list_for_each_entry(h, &heap_list, list) {
++ if (!strcmp(h->name, name)) {
++ kref_get(&h->refcount);
++ mutex_unlock(&heap_list_lock);
++ return h;
++ }
++ }
++ mutex_unlock(&heap_list_lock);
++ return NULL;
++}
++EXPORT_SYMBOL_GPL(dma_heap_find);
+
+ static void dma_heap_release(struct kref *ref)
+ {
+@@ -330,6 +357,7 @@ void dma_heap_put(struct dma_heap *h)
+ kref_put(&h->refcount, dma_heap_release);
+ mutex_unlock(&heap_list_lock);
+ }
++EXPORT_SYMBOL_GPL(dma_heap_put);
+
+ static char *dma_heap_devnode(const struct device *dev, umode_t *mode)
+ {
+diff --git a/include/linux/dma-heap.h b/include/linux/dma-heap.h
+index f8c986dd9a8b..31f44d83f11b 100644
+--- a/include/linux/dma-heap.h
++++ b/include/linux/dma-heap.h
+@@ -65,10 +65,35 @@ const char *dma_heap_get_name(struct dma_heap *heap);
+ */
+ struct dma_heap *dma_heap_add(const struct dma_heap_export_info *exp_info);
+
++/**
++ * dma_heap_find - get the heap registered with the specified name
++ * @name: Name of the DMA-Heap to find
++ *
++ * Returns:
++ * The DMA-Heap with the provided name.
++ *
++ * NOTE: DMA-Heaps returned from this function MUST be released using
++ * dma_heap_put() when the user is done to enable the heap to be unloaded.
++ */
++struct dma_heap *dma_heap_find(const char *name);
++
+ /**
+ * dma_heap_put - drops a reference to a dmabuf heap, potentially freeing it
+ * @heap: the heap whose reference count to decrement
+ */
+ void dma_heap_put(struct dma_heap *heap);
+
++/**
++ * dma_heap_buffer_alloc - Allocate dma-buf from a dma_heap
++ * @heap: DMA-Heap to allocate from
++ * @len: size to allocate in bytes
++ * @fd_flags: flags to set on returned dma-buf fd
++ * @heap_flags: flags to pass to the dma heap
++ *
++ * This is for internal dma-buf allocations only. Free returned buffers with dma_buf_put().
++ */
++struct dma_buf *dma_heap_buffer_alloc(struct dma_heap *heap, size_t len,
++ unsigned int fd_flags,
++ unsigned int heap_flags);
++
+ #endif /* _DMA_HEAPS_H */
+--
+2.25.1
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0001-interconnect-qcom-icc-rpm-Add-AB-IB-calculations-coe.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0001-interconnect-qcom-icc-rpm-Add-AB-IB-calculations-coe.patch
new file mode 100644
index 0000000..6b8e76f
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0001-interconnect-qcom-icc-rpm-Add-AB-IB-calculations-coe.patch
@@ -0,0 +1,97 @@
+From dd014803f260b337daaabcde259daf70d5b26b5e Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Fri, 25 Aug 2023 17:38:23 +0200
+Subject: [PATCH 1/9] interconnect: qcom: icc-rpm: Add AB/IB calculations
+ coefficients
+
+Presumably due to the hardware being so complex, some nodes (or busses)
+have different (usually higher) requirements for bandwidth than what
+the usual calculations would suggest.
+
+Looking at the available downstream files, it seems like AB values are
+adjusted per-bus and IB values are adjusted per-node.
+With that in mind, introduce percentage-based coefficient struct members
+and use them in the calculations.
+
+One thing to note is that the IB coefficient is inverse (100/ib_percent)
+which feels a bit backwards, but it's necessary for precision..
+
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Link: https://lore.kernel.org/r/20230726-topic-icc_coeff-v4-1-c04b60caa467@linaro.org
+Signed-off-by: Georgi Djakov <djakov@kernel.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git dd014803f260]
+---
+ drivers/interconnect/qcom/icc-rpm.c | 18 +++++++++++++++---
+ drivers/interconnect/qcom/icc-rpm.h | 6 ++++++
+ 2 files changed, 21 insertions(+), 3 deletions(-)
+
+diff --git a/drivers/interconnect/qcom/icc-rpm.c b/drivers/interconnect/qcom/icc-rpm.c
+index 2c16917ba1fd..8b02aa8aa96a 100644
+--- a/drivers/interconnect/qcom/icc-rpm.c
++++ b/drivers/interconnect/qcom/icc-rpm.c
+@@ -298,7 +298,8 @@ static int qcom_icc_bw_aggregate(struct icc_node *node, u32 tag, u32 avg_bw,
+ */
+ static void qcom_icc_bus_aggregate(struct icc_provider *provider, u64 *agg_clk_rate)
+ {
+- u64 agg_avg_rate, agg_rate;
++ struct qcom_icc_provider *qp = to_qcom_provider(provider);
++ u64 agg_avg_rate, agg_peak_rate, agg_rate;
+ struct qcom_icc_node *qn;
+ struct icc_node *node;
+ int i;
+@@ -315,8 +316,19 @@ static void qcom_icc_bus_aggregate(struct icc_provider *provider, u64 *agg_clk_r
+ else
+ agg_avg_rate = qn->sum_avg[i];
+
+- agg_rate = max_t(u64, agg_avg_rate, qn->max_peak[i]);
+- do_div(agg_rate, qn->buswidth);
++ if (qp->ab_coeff) {
++ agg_avg_rate = agg_avg_rate * qp->ab_coeff;
++ agg_avg_rate = div_u64(agg_avg_rate, 100);
++ }
++
++ if (qp->ib_coeff) {
++ agg_peak_rate = qn->max_peak[i] * 100;
++ agg_peak_rate = div_u64(qn->max_peak[i], qp->ib_coeff);
++ } else {
++ agg_peak_rate = qn->max_peak[i];
++ }
++
++ agg_rate = max_t(u64, agg_avg_rate, agg_peak_rate);
+
+ agg_clk_rate[i] = max_t(u64, agg_clk_rate[i], agg_rate);
+ }
+diff --git a/drivers/interconnect/qcom/icc-rpm.h b/drivers/interconnect/qcom/icc-rpm.h
+index eed3451af3e6..5e7d6a4fd2f3 100644
+--- a/drivers/interconnect/qcom/icc-rpm.h
++++ b/drivers/interconnect/qcom/icc-rpm.h
+@@ -44,6 +44,8 @@ struct rpm_clk_resource {
+ * @type: the ICC provider type
+ * @regmap: regmap for QoS registers read/write access
+ * @qos_offset: offset to QoS registers
++ * @ab_coeff: a percentage-based coefficient for compensating the AB calculations
++ * @ib_coeff: an inverse-percentage-based coefficient for compensating the IB calculations
+ * @bus_clk_rate: bus clock rate in Hz
+ * @bus_clk_desc: a pointer to a rpm_clk_resource description of bus clocks
+ * @bus_clk: a pointer to a HLOS-owned bus clock
+@@ -57,6 +59,8 @@ struct qcom_icc_provider {
+ enum qcom_icc_type type;
+ struct regmap *regmap;
+ unsigned int qos_offset;
++ u16 ab_coeff;
++ u16 ib_coeff;
+ u32 bus_clk_rate[QCOM_SMD_RPM_STATE_NUM];
+ const struct rpm_clk_resource *bus_clk_desc;
+ struct clk *bus_clk;
+@@ -123,6 +127,8 @@ struct qcom_icc_desc {
+ enum qcom_icc_type type;
+ const struct regmap_config *regmap_cfg;
+ unsigned int qos_offset;
++ u16 ab_coeff;
++ u16 ib_coeff;
+ };
+
+ /* Valid for all bus types */
+--
+2.39.2
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0002-interconnect-qcom-icc-rpm-Separate-out-clock-rate-ca.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0002-interconnect-qcom-icc-rpm-Separate-out-clock-rate-ca.patch
new file mode 100644
index 0000000..be1d79f
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0002-interconnect-qcom-icc-rpm-Separate-out-clock-rate-ca.patch
@@ -0,0 +1,100 @@
+From db8fc1002c53bc17a3ca6fad2c524de42b77c146 Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Fri, 25 Aug 2023 17:38:24 +0200
+Subject: [PATCH 2/9] interconnect: qcom: icc-rpm: Separate out clock rate
+ calulcations
+
+In preparation for also setting per-node clock rates, separate out the
+logic that computes it.
+
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Link: https://lore.kernel.org/r/20230726-topic-icc_coeff-v4-2-c04b60caa467@linaro.org
+Signed-off-by: Georgi Djakov <djakov@kernel.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git db8fc1002c53]
+---
+ drivers/interconnect/qcom/icc-rpm.c | 53 ++++++++++++++++-------------
+ 1 file changed, 30 insertions(+), 23 deletions(-)
+
+diff --git a/drivers/interconnect/qcom/icc-rpm.c b/drivers/interconnect/qcom/icc-rpm.c
+index 8b02aa8aa96a..8c1bfd65d774 100644
+--- a/drivers/interconnect/qcom/icc-rpm.c
++++ b/drivers/interconnect/qcom/icc-rpm.c
+@@ -291,6 +291,32 @@ static int qcom_icc_bw_aggregate(struct icc_node *node, u32 tag, u32 avg_bw,
+ return 0;
+ }
+
++static u64 qcom_icc_calc_rate(struct qcom_icc_provider *qp, struct qcom_icc_node *qn, int ctx)
++{
++ u64 agg_avg_rate, agg_peak_rate, agg_rate;
++
++ if (qn->channels)
++ agg_avg_rate = div_u64(qn->sum_avg[ctx], qn->channels);
++ else
++ agg_avg_rate = qn->sum_avg[ctx];
++
++ if (qp->ab_coeff) {
++ agg_avg_rate = agg_avg_rate * qp->ab_coeff;
++ agg_avg_rate = div_u64(agg_avg_rate, 100);
++ }
++
++ if (qp->ib_coeff) {
++ agg_peak_rate = qn->max_peak[ctx] * 100;
++ agg_peak_rate = div_u64(qn->max_peak[ctx], qp->ib_coeff);
++ } else {
++ agg_peak_rate = qn->max_peak[ctx];
++ }
++
++ agg_rate = max_t(u64, agg_avg_rate, agg_peak_rate);
++
++ return div_u64(agg_rate, qn->buswidth);
++}
++
+ /**
+ * qcom_icc_bus_aggregate - calculate bus clock rates by traversing all nodes
+ * @provider: generic interconnect provider
+@@ -299,10 +325,9 @@ static int qcom_icc_bw_aggregate(struct icc_node *node, u32 tag, u32 avg_bw,
+ static void qcom_icc_bus_aggregate(struct icc_provider *provider, u64 *agg_clk_rate)
+ {
+ struct qcom_icc_provider *qp = to_qcom_provider(provider);
+- u64 agg_avg_rate, agg_peak_rate, agg_rate;
+ struct qcom_icc_node *qn;
+ struct icc_node *node;
+- int i;
++ int ctx;
+
+ /*
+ * Iterate nodes on the provider, aggregate bandwidth requests for
+@@ -310,27 +335,9 @@ static void qcom_icc_bus_aggregate(struct icc_provider *provider, u64 *agg_clk_r
+ */
+ list_for_each_entry(node, &provider->nodes, node_list) {
+ qn = node->data;
+- for (i = 0; i < QCOM_SMD_RPM_STATE_NUM; i++) {
+- if (qn->channels)
+- agg_avg_rate = div_u64(qn->sum_avg[i], qn->channels);
+- else
+- agg_avg_rate = qn->sum_avg[i];
+-
+- if (qp->ab_coeff) {
+- agg_avg_rate = agg_avg_rate * qp->ab_coeff;
+- agg_avg_rate = div_u64(agg_avg_rate, 100);
+- }
+-
+- if (qp->ib_coeff) {
+- agg_peak_rate = qn->max_peak[i] * 100;
+- agg_peak_rate = div_u64(qn->max_peak[i], qp->ib_coeff);
+- } else {
+- agg_peak_rate = qn->max_peak[i];
+- }
+-
+- agg_rate = max_t(u64, agg_avg_rate, agg_peak_rate);
+-
+- agg_clk_rate[i] = max_t(u64, agg_clk_rate[i], agg_rate);
++ for (ctx = 0; ctx < QCOM_SMD_RPM_STATE_NUM; ctx++) {
++ agg_clk_rate[ctx] = max_t(u64, agg_clk_rate[ctx],
++ qcom_icc_calc_rate(qp, qn, ctx));
+ }
+ }
+ }
+--
+2.39.2
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0003-interconnect-qcom-icc-rpm-Let-nodes-drive-their-own-.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0003-interconnect-qcom-icc-rpm-Let-nodes-drive-their-own-.patch
new file mode 100644
index 0000000..f71cf3d
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0003-interconnect-qcom-icc-rpm-Let-nodes-drive-their-own-.patch
@@ -0,0 +1,99 @@
+From 919791d82d3b878094e9edc39b0d9a4eafcc0860 Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Fri, 25 Aug 2023 17:38:25 +0200
+Subject: [PATCH 3/9] interconnect: qcom: icc-rpm: Let nodes drive their own
+ bus clock
+
+If this hardware couldn't get messier, some nodes are supposed to drive
+their own bus clock.. Presumably to connect to some intermediate
+interface between the node itself and the bus it's (supposed to be)
+connected to.
+
+Expand the node struct with the necessary data and hook up the
+allocations & calculations.
+
+Note that the node-specific AB/IB coefficients contribute (by design)
+to both the node-level and the bus-level aggregation.
+
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Link: https://lore.kernel.org/r/20230726-topic-icc_coeff-v4-3-c04b60caa467@linaro.org
+Signed-off-by: Georgi Djakov <djakov@kernel.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git 919791d82d3b]
+---
+ drivers/interconnect/qcom/icc-rpm.c | 27 +++++++++++++++++++++++++++
+ drivers/interconnect/qcom/icc-rpm.h | 4 ++++
+ 2 files changed, 31 insertions(+)
+
+diff --git a/drivers/interconnect/qcom/icc-rpm.c b/drivers/interconnect/qcom/icc-rpm.c
+index 8c1bfd65d774..1d3af4e9ead8 100644
+--- a/drivers/interconnect/qcom/icc-rpm.c
++++ b/drivers/interconnect/qcom/icc-rpm.c
+@@ -414,6 +414,33 @@ static int qcom_icc_set(struct icc_node *src, struct icc_node *dst)
+ qp->bus_clk_rate[QCOM_SMD_RPM_SLEEP_STATE] = sleep_rate;
+ }
+
++ /* Handle the node-specific clock */
++ if (!src_qn->bus_clk_desc)
++ return 0;
++
++ active_rate = qcom_icc_calc_rate(qp, src_qn, QCOM_SMD_RPM_ACTIVE_STATE);
++ sleep_rate = qcom_icc_calc_rate(qp, src_qn, QCOM_SMD_RPM_SLEEP_STATE);
++
++ if (active_rate != src_qn->bus_clk_rate[QCOM_SMD_RPM_ACTIVE_STATE]) {
++ ret = qcom_icc_rpm_set_bus_rate(src_qn->bus_clk_desc, QCOM_SMD_RPM_ACTIVE_STATE,
++ active_rate);
++ if (ret)
++ return ret;
++
++ /* Cache the rate after we've successfully committed it to RPM */
++ src_qn->bus_clk_rate[QCOM_SMD_RPM_ACTIVE_STATE] = active_rate;
++ }
++
++ if (sleep_rate != src_qn->bus_clk_rate[QCOM_SMD_RPM_SLEEP_STATE]) {
++ ret = qcom_icc_rpm_set_bus_rate(src_qn->bus_clk_desc, QCOM_SMD_RPM_SLEEP_STATE,
++ sleep_rate);
++ if (ret)
++ return ret;
++
++ /* Cache the rate after we've successfully committed it to RPM */
++ src_qn->bus_clk_rate[QCOM_SMD_RPM_SLEEP_STATE] = sleep_rate;
++ }
++
+ return 0;
+ }
+
+diff --git a/drivers/interconnect/qcom/icc-rpm.h b/drivers/interconnect/qcom/icc-rpm.h
+index 5e7d6a4fd2f3..725e0d4840e4 100644
+--- a/drivers/interconnect/qcom/icc-rpm.h
++++ b/drivers/interconnect/qcom/icc-rpm.h
+@@ -97,11 +97,13 @@ struct qcom_icc_qos {
+ * @num_links: the total number of @links
+ * @channels: number of channels at this node (e.g. DDR channels)
+ * @buswidth: width of the interconnect between a node and the bus (bytes)
++ * @bus_clk_desc: a pointer to a rpm_clk_resource description of bus clocks
+ * @sum_avg: current sum aggregate value of all avg bw requests
+ * @max_peak: current max aggregate value of all peak bw requests
+ * @mas_rpm_id: RPM id for devices that are bus masters
+ * @slv_rpm_id: RPM id for devices that are bus slaves
+ * @qos: NoC QoS setting parameters
++ * @bus_clk_rate: a pointer to an array containing bus clock rates in Hz
+ */
+ struct qcom_icc_node {
+ unsigned char *name;
+@@ -110,11 +112,13 @@ struct qcom_icc_node {
+ u16 num_links;
+ u16 channels;
+ u16 buswidth;
++ const struct rpm_clk_resource *bus_clk_desc;
+ u64 sum_avg[QCOM_SMD_RPM_STATE_NUM];
+ u64 max_peak[QCOM_SMD_RPM_STATE_NUM];
+ int mas_rpm_id;
+ int slv_rpm_id;
+ struct qcom_icc_qos qos;
++ u32 bus_clk_rate[QCOM_SMD_RPM_STATE_NUM];
+ };
+
+ struct qcom_icc_desc {
+--
+2.39.2
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0004-interconnect-qcom-icc-rpm-Check-for-node-specific-ra.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0004-interconnect-qcom-icc-rpm-Check-for-node-specific-ra.patch
new file mode 100644
index 0000000..faee1be
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0004-interconnect-qcom-icc-rpm-Check-for-node-specific-ra.patch
@@ -0,0 +1,82 @@
+From ba3f826639782587b70a684dae79d39f6d3c433e Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Fri, 25 Aug 2023 17:38:26 +0200
+Subject: [PATCH 4/9] interconnect: qcom: icc-rpm: Check for node-specific rate
+ coefficients
+
+Some nodes may have different coefficients than the general values for
+bus they're attached to. Check for that and use them if present. See
+[1], [2] for reference.
+
+[1] https://github.com/sonyxperiadev/kernel/commit/7456d9779af9ad6bb9c7ee6f33d5c5a8d3648e24
+[2] https://github.com/artem/android_kernel_sony_msm8996/commit/bf7a8985dcaf0eab5bc2562d2d6775e7e29c0f30
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Link: https://lore.kernel.org/r/20230726-topic-icc_coeff-v4-4-c04b60caa467@linaro.org
+Signed-off-by: Georgi Djakov <djakov@kernel.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git ba3f82663978]
+---
+ drivers/interconnect/qcom/icc-rpm.c | 14 ++++++++++----
+ drivers/interconnect/qcom/icc-rpm.h | 4 ++++
+ 2 files changed, 14 insertions(+), 4 deletions(-)
+
+diff --git a/drivers/interconnect/qcom/icc-rpm.c b/drivers/interconnect/qcom/icc-rpm.c
+index 1d3af4e9ead8..9c40314e03b5 100644
+--- a/drivers/interconnect/qcom/icc-rpm.c
++++ b/drivers/interconnect/qcom/icc-rpm.c
+@@ -300,14 +300,14 @@ static u64 qcom_icc_calc_rate(struct qcom_icc_provider *qp, struct qcom_icc_node
+ else
+ agg_avg_rate = qn->sum_avg[ctx];
+
+- if (qp->ab_coeff) {
+- agg_avg_rate = agg_avg_rate * qp->ab_coeff;
++ if (qn->ab_coeff) {
++ agg_avg_rate = agg_avg_rate * qn->ab_coeff;
+ agg_avg_rate = div_u64(agg_avg_rate, 100);
+ }
+
+- if (qp->ib_coeff) {
++ if (qn->ib_coeff) {
+ agg_peak_rate = qn->max_peak[ctx] * 100;
+- agg_peak_rate = div_u64(qn->max_peak[ctx], qp->ib_coeff);
++ agg_peak_rate = div_u64(qn->max_peak[ctx], qn->ib_coeff);
+ } else {
+ agg_peak_rate = qn->max_peak[ctx];
+ }
+@@ -563,6 +563,12 @@ int qnoc_probe(struct platform_device *pdev)
+ for (i = 0; i < num_nodes; i++) {
+ size_t j;
+
++ if (!qnodes[i]->ab_coeff)
++ qnodes[i]->ab_coeff = qp->ab_coeff;
++
++ if (!qnodes[i]->ib_coeff)
++ qnodes[i]->ib_coeff = qp->ib_coeff;
++
+ node = icc_node_create(qnodes[i]->id);
+ if (IS_ERR(node)) {
+ ret = PTR_ERR(node);
+diff --git a/drivers/interconnect/qcom/icc-rpm.h b/drivers/interconnect/qcom/icc-rpm.h
+index 725e0d4840e4..4abf99ce2690 100644
+--- a/drivers/interconnect/qcom/icc-rpm.h
++++ b/drivers/interconnect/qcom/icc-rpm.h
+@@ -103,6 +103,8 @@ struct qcom_icc_qos {
+ * @mas_rpm_id: RPM id for devices that are bus masters
+ * @slv_rpm_id: RPM id for devices that are bus slaves
+ * @qos: NoC QoS setting parameters
++ * @ab_coeff: a percentage-based coefficient for compensating the AB calculations
++ * @ib_coeff: an inverse-percentage-based coefficient for compensating the IB calculations
+ * @bus_clk_rate: a pointer to an array containing bus clock rates in Hz
+ */
+ struct qcom_icc_node {
+@@ -118,6 +120,8 @@ struct qcom_icc_node {
+ int mas_rpm_id;
+ int slv_rpm_id;
+ struct qcom_icc_qos qos;
++ u16 ab_coeff;
++ u16 ib_coeff;
+ u32 bus_clk_rate[QCOM_SMD_RPM_STATE_NUM];
+ };
+
+--
+2.39.2
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0005-interconnect-qcom-qcm2290-Hook-up-MAS_APPS_PROC-s-bu.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0005-interconnect-qcom-qcm2290-Hook-up-MAS_APPS_PROC-s-bu.patch
new file mode 100644
index 0000000..4a0bbb4
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0005-interconnect-qcom-qcm2290-Hook-up-MAS_APPS_PROC-s-bu.patch
@@ -0,0 +1,69 @@
+From fa35757ae0a5a88bd1b7df8578ee9dac9d147c64 Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Fri, 25 Aug 2023 17:38:27 +0200
+Subject: [PATCH 5/9] interconnect: qcom: qcm2290: Hook up MAS_APPS_PROC's bus
+ clock
+
+This single node has its own clock which seems to be responsible for
+transactions between CPUSS (CPU + some stuff) and the GNOC. See [1]
+for reference.
+
+Define it and hook it up.
+
+[1] https://android.googlesource.com/kernel/msm-extra/devicetree/+/02f8c342b23c20a5cf967df649814be37a08227c%5E%21/#F0
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Link: https://lore.kernel.org/r/20230726-topic-icc_coeff-v4-5-c04b60caa467@linaro.org
+Signed-off-by: Georgi Djakov <djakov@kernel.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git fa35757ae0a5]
+---
+ drivers/interconnect/qcom/icc-rpm-clocks.c | 6 ++++++
+ drivers/interconnect/qcom/icc-rpm.h | 1 +
+ drivers/interconnect/qcom/qcm2290.c | 3 +++
+ 3 files changed, 10 insertions(+)
+
+diff --git a/drivers/interconnect/qcom/icc-rpm-clocks.c b/drivers/interconnect/qcom/icc-rpm-clocks.c
+index 63c82a91bbc7..ac1677de7dfd 100644
+--- a/drivers/interconnect/qcom/icc-rpm-clocks.c
++++ b/drivers/interconnect/qcom/icc-rpm-clocks.c
+@@ -25,6 +25,12 @@ const struct rpm_clk_resource bimc_clk = {
+ };
+ EXPORT_SYMBOL_GPL(bimc_clk);
+
++const struct rpm_clk_resource mem_1_clk = {
++ .resource_type = QCOM_SMD_RPM_MEM_CLK,
++ .clock_id = 1,
++};
++EXPORT_SYMBOL_GPL(mem_1_clk);
++
+ const struct rpm_clk_resource bus_0_clk = {
+ .resource_type = QCOM_SMD_RPM_BUS_CLK,
+ .clock_id = 0,
+diff --git a/drivers/interconnect/qcom/icc-rpm.h b/drivers/interconnect/qcom/icc-rpm.h
+index 4abf99ce2690..a13768cfd231 100644
+--- a/drivers/interconnect/qcom/icc-rpm.h
++++ b/drivers/interconnect/qcom/icc-rpm.h
+@@ -152,6 +152,7 @@ extern const struct rpm_clk_resource bimc_clk;
+ extern const struct rpm_clk_resource bus_0_clk;
+ extern const struct rpm_clk_resource bus_1_clk;
+ extern const struct rpm_clk_resource bus_2_clk;
++extern const struct rpm_clk_resource mem_1_clk;
+ extern const struct rpm_clk_resource mmaxi_0_clk;
+ extern const struct rpm_clk_resource mmaxi_1_clk;
+ extern const struct rpm_clk_resource qup_clk;
+diff --git a/drivers/interconnect/qcom/qcm2290.c b/drivers/interconnect/qcom/qcm2290.c
+index 5bc4b7516608..026e4c82d6d4 100644
+--- a/drivers/interconnect/qcom/qcm2290.c
++++ b/drivers/interconnect/qcom/qcm2290.c
+@@ -112,6 +112,9 @@ static struct qcom_icc_node mas_appss_proc = {
+ .qos.qos_mode = NOC_QOS_MODE_FIXED,
+ .qos.prio_level = 0,
+ .qos.areq_prio = 0,
++ .bus_clk_desc = &mem_1_clk,
++ .ab_coeff = 159,
++ .ib_coeff = 96,
+ .mas_rpm_id = 0,
+ .slv_rpm_id = -1,
+ .num_links = ARRAY_SIZE(mas_appss_proc_links),
+--
+2.39.2
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0006-interconnect-qcom-qcm2290-Set-AB-coefficients.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0006-interconnect-qcom-qcm2290-Set-AB-coefficients.patch
new file mode 100644
index 0000000..3062f49
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0006-interconnect-qcom-qcm2290-Set-AB-coefficients.patch
@@ -0,0 +1,47 @@
+From 8657ed471196f4dc8e7917453a39363e0014840c Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Fri, 25 Aug 2023 17:38:28 +0200
+Subject: [PATCH 6/9] interconnect: qcom: qcm2290: Set AB coefficients
+
+Some buses need additional manual adjustments atop the usual
+calculations. Fill in the missing coefficients.
+
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Link: https://lore.kernel.org/r/20230726-topic-icc_coeff-v4-6-c04b60caa467@linaro.org
+Signed-off-by: Georgi Djakov <djakov@kernel.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git 8657ed471196]
+---
+ drivers/interconnect/qcom/qcm2290.c | 3 +++
+ 1 file changed, 3 insertions(+)
+
+diff --git a/drivers/interconnect/qcom/qcm2290.c b/drivers/interconnect/qcom/qcm2290.c
+index 026e4c82d6d4..7abc0c449220 100644
+--- a/drivers/interconnect/qcom/qcm2290.c
++++ b/drivers/interconnect/qcom/qcm2290.c
+@@ -1202,6 +1202,7 @@ static const struct qcom_icc_desc qcm2290_bimc = {
+ .keep_alive = true,
+ /* M_REG_BASE() in vendor msm_bus_bimc_adhoc driver */
+ .qos_offset = 0x8000,
++ .ab_coeff = 153,
+ };
+
+ static struct qcom_icc_node * const qcm2290_cnoc_nodes[] = {
+@@ -1332,6 +1333,7 @@ static const struct qcom_icc_desc qcm2290_mmnrt_virt = {
+ .regmap_cfg = &qcm2290_snoc_regmap_config,
+ .keep_alive = true,
+ .qos_offset = 0x15000,
++ .ab_coeff = 142,
+ };
+
+ static struct qcom_icc_node * const qcm2290_mmrt_virt_nodes[] = {
+@@ -1348,6 +1350,7 @@ static const struct qcom_icc_desc qcm2290_mmrt_virt = {
+ .regmap_cfg = &qcm2290_snoc_regmap_config,
+ .keep_alive = true,
+ .qos_offset = 0x15000,
++ .ab_coeff = 139,
+ };
+
+ static const struct of_device_id qcm2290_noc_of_match[] = {
+--
+2.39.2
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0007-interconnect-qcom-qcm2290-Update-EBI-channel-configu.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0007-interconnect-qcom-qcm2290-Update-EBI-channel-configu.patch
new file mode 100644
index 0000000..c6960d8
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0007-interconnect-qcom-qcm2290-Update-EBI-channel-configu.patch
@@ -0,0 +1,43 @@
+From 550064a85ba564cfb508a995f45e39a6ad0e26ed Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Fri, 25 Aug 2023 17:38:29 +0200
+Subject: [PATCH 7/9] interconnect: qcom: qcm2290: Update EBI channel
+ configuration
+
+QCM2290 can support two memory configurations: single-channel, 32-bit
+wide LPDDR3 @ up to 933MHz (bus clock) or dual-channel, 16-bit wide
+LPDDR4X @ up to 1804 MHz. The interconnect driver in its current form
+seems to gravitate towards the first one, however there are no LPDDR3-
+equipped boards upstream and we still don't have a great way to discern
+the DDR generations on the kernel side.
+
+To make DDR scaling possible on the only currently-supported 2290
+board, stick with the LPDDR4X config by default. The side effect on any
+potential LPDDR3 board would be that the requested bus clock rate is
+too high (but still capped to the firmware-configured FMAX).
+
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Link: https://lore.kernel.org/r/20230726-topic-icc_coeff-v4-7-c04b60caa467@linaro.org
+Signed-off-by: Georgi Djakov <djakov@kernel.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git 550064a85ba5]
+---
+ drivers/interconnect/qcom/qcm2290.c | 3 ++-
+ 1 file changed, 2 insertions(+), 1 deletion(-)
+
+diff --git a/drivers/interconnect/qcom/qcm2290.c b/drivers/interconnect/qcom/qcm2290.c
+index 7abc0c449220..b88cf9a022e0 100644
+--- a/drivers/interconnect/qcom/qcm2290.c
++++ b/drivers/interconnect/qcom/qcm2290.c
+@@ -678,7 +678,8 @@ static struct qcom_icc_node mas_gfx3d = {
+ static struct qcom_icc_node slv_ebi1 = {
+ .name = "slv_ebi1",
+ .id = QCM2290_SLAVE_EBI1,
+- .buswidth = 8,
++ .buswidth = 4,
++ .channels = 2,
+ .mas_rpm_id = -1,
+ .slv_rpm_id = 0,
+ };
+--
+2.39.2
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0008-interconnect-qcom-sdm660-Set-AB-IB-coefficients.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0008-interconnect-qcom-sdm660-Set-AB-IB-coefficients.patch
new file mode 100644
index 0000000..af67d8c
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0008-interconnect-qcom-sdm660-Set-AB-IB-coefficients.patch
@@ -0,0 +1,55 @@
+From a4a9251760185af9ca7ff1592a05a0eabfe0cd00 Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Fri, 25 Aug 2023 17:38:30 +0200
+Subject: [PATCH 8/9] interconnect: qcom: sdm660: Set AB/IB coefficients
+
+Some buses and nodes need additional manual adjustments atop the usual
+calculations. Fill in the missing coefficients.
+
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Link: https://lore.kernel.org/r/20230726-topic-icc_coeff-v4-8-c04b60caa467@linaro.org
+Signed-off-by: Georgi Djakov <djakov@kernel.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git a4a925176018]
+---
+ drivers/interconnect/qcom/sdm660.c | 4 ++++
+ 1 file changed, 4 insertions(+)
+
+diff --git a/drivers/interconnect/qcom/sdm660.c b/drivers/interconnect/qcom/sdm660.c
+index 36962f7bd7bb..7392bebba334 100644
+--- a/drivers/interconnect/qcom/sdm660.c
++++ b/drivers/interconnect/qcom/sdm660.c
+@@ -602,6 +602,7 @@ static struct qcom_icc_node mas_mdp_p0 = {
+ .name = "mas_mdp_p0",
+ .id = SDM660_MASTER_MDP_P0,
+ .buswidth = 16,
++ .ib_coeff = 50,
+ .mas_rpm_id = 8,
+ .slv_rpm_id = -1,
+ .qos.ap_owned = true,
+@@ -621,6 +622,7 @@ static struct qcom_icc_node mas_mdp_p1 = {
+ .name = "mas_mdp_p1",
+ .id = SDM660_MASTER_MDP_P1,
+ .buswidth = 16,
++ .ib_coeff = 50,
+ .mas_rpm_id = 61,
+ .slv_rpm_id = -1,
+ .qos.ap_owned = true,
+@@ -1540,6 +1542,7 @@ static const struct qcom_icc_desc sdm660_bimc = {
+ .num_nodes = ARRAY_SIZE(sdm660_bimc_nodes),
+ .bus_clk_desc = &bimc_clk,
+ .regmap_cfg = &sdm660_bimc_regmap_config,
++ .ab_coeff = 153,
+ };
+
+ static struct qcom_icc_node * const sdm660_cnoc_nodes[] = {
+@@ -1659,6 +1662,7 @@ static const struct qcom_icc_desc sdm660_mnoc = {
+ .intf_clocks = mm_intf_clocks,
+ .num_intf_clocks = ARRAY_SIZE(mm_intf_clocks),
+ .regmap_cfg = &sdm660_mnoc_regmap_config,
++ .ab_coeff = 153,
+ };
+
+ static struct qcom_icc_node * const sdm660_snoc_nodes[] = {
+--
+2.39.2
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0009-interconnect-qcom-msm8996-Set-AB-IB-coefficients.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0009-interconnect-qcom-msm8996-Set-AB-IB-coefficients.patch
new file mode 100644
index 0000000..ff49eb0
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/icc/0009-interconnect-qcom-msm8996-Set-AB-IB-coefficients.patch
@@ -0,0 +1,59 @@
+From 1255f23c219a74f2577c9ca5521abeb36db35d3b Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Fri, 25 Aug 2023 17:38:31 +0200
+Subject: [PATCH 9/9] interconnect: qcom: msm8996: Set AB/IB coefficients
+
+Some buses and nodes need additional manual adjustments atop the usual
+calculations. Fill in the missing coefficients.
+
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Link: https://lore.kernel.org/r/20230726-topic-icc_coeff-v4-9-c04b60caa467@linaro.org
+Signed-off-by: Georgi Djakov <djakov@kernel.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git 1255f23c219a]
+---
+ drivers/interconnect/qcom/msm8996.c | 8 ++++++--
+ 1 file changed, 6 insertions(+), 2 deletions(-)
+
+diff --git a/drivers/interconnect/qcom/msm8996.c b/drivers/interconnect/qcom/msm8996.c
+index 88683dfa468f..b73566c9b21f 100644
+--- a/drivers/interconnect/qcom/msm8996.c
++++ b/drivers/interconnect/qcom/msm8996.c
+@@ -448,6 +448,7 @@ static struct qcom_icc_node mas_mdp_p0 = {
+ .name = "mas_mdp_p0",
+ .id = MSM8996_MASTER_MDP_PORT0,
+ .buswidth = 32,
++ .ib_coeff = 25,
+ .mas_rpm_id = 8,
+ .slv_rpm_id = -1,
+ .qos.ap_owned = true,
+@@ -463,6 +464,7 @@ static struct qcom_icc_node mas_mdp_p1 = {
+ .name = "mas_mdp_p1",
+ .id = MSM8996_MASTER_MDP_PORT1,
+ .buswidth = 32,
++ .ib_coeff = 25,
+ .mas_rpm_id = 61,
+ .slv_rpm_id = -1,
+ .qos.ap_owned = true,
+@@ -1889,7 +1891,8 @@ static const struct qcom_icc_desc msm8996_bimc = {
+ .nodes = bimc_nodes,
+ .num_nodes = ARRAY_SIZE(bimc_nodes),
+ .bus_clk_desc = &bimc_clk,
+- .regmap_cfg = &msm8996_bimc_regmap_config
++ .regmap_cfg = &msm8996_bimc_regmap_config,
++ .ab_coeff = 154,
+ };
+
+ static struct qcom_icc_node * const cnoc_nodes[] = {
+@@ -2004,7 +2007,8 @@ static const struct qcom_icc_desc msm8996_mnoc = {
+ .bus_clk_desc = &mmaxi_0_clk,
+ .intf_clocks = mm_intf_clocks,
+ .num_intf_clocks = ARRAY_SIZE(mm_intf_clocks),
+- .regmap_cfg = &msm8996_mnoc_regmap_config
++ .regmap_cfg = &msm8996_mnoc_regmap_config,
++ .ab_coeff = 154,
+ };
+
+ static struct qcom_icc_node * const pnoc_nodes[] = {
+--
+2.39.2
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0001_drm_msm_mdss_switch_mdss_to_use_devm_of_icc_get.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0001_drm_msm_mdss_switch_mdss_to_use_devm_of_icc_get.patch
new file mode 100644
index 0000000..0620692
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0001_drm_msm_mdss_switch_mdss_to_use_devm_of_icc_get.patch
@@ -0,0 +1,64 @@
+From: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
+Subject: drm/msm/mdss: switch mdss to use devm_of_icc_get()
+Date: Sun, 03 Dec 2023 01:42:44 +0300
+
+Stop using hand-written reset function for ICC release, use
+devm_of_icc_get() instead.
+
+Reviewed-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Reviewed-by: Abhinav Kumar <quic_abhinavk@quicinc.com>
+Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
+Upstream-Status: Backport [https://gitlab.freedesktop.org/lumag/msm/-/commit/ded61d7dc5a0]
+---
+ drivers/gpu/drm/msm/msm_mdss.c | 16 ++--------------
+ 1 file changed, 2 insertions(+), 14 deletions(-)
+
+diff --git a/drivers/gpu/drm/msm/msm_mdss.c b/drivers/gpu/drm/msm/msm_mdss.c
+index 29bb38f0bb2c..53bc496ace99 100644
+--- a/drivers/gpu/drm/msm/msm_mdss.c
++++ b/drivers/gpu/drm/msm/msm_mdss.c
+@@ -50,14 +50,14 @@ static int msm_mdss_parse_data_bus_icc_path(struct device *dev,
+ struct icc_path *path0;
+ struct icc_path *path1;
+
+- path0 = of_icc_get(dev, "mdp0-mem");
++ path0 = devm_of_icc_get(dev, "mdp0-mem");
+ if (IS_ERR_OR_NULL(path0))
+ return PTR_ERR_OR_ZERO(path0);
+
+ msm_mdss->path[0] = path0;
+ msm_mdss->num_paths = 1;
+
+- path1 = of_icc_get(dev, "mdp1-mem");
++ path1 = devm_of_icc_get(dev, "mdp1-mem");
+ if (!IS_ERR_OR_NULL(path1)) {
+ msm_mdss->path[1] = path1;
+ msm_mdss->num_paths++;
+@@ -66,15 +66,6 @@ static int msm_mdss_parse_data_bus_icc_path(struct device *dev,
+ return 0;
+ }
+
+-static void msm_mdss_put_icc_path(void *data)
+-{
+- struct msm_mdss *msm_mdss = data;
+- int i;
+-
+- for (i = 0; i < msm_mdss->num_paths; i++)
+- icc_put(msm_mdss->path[i]);
+-}
+-
+ static void msm_mdss_icc_request_bw(struct msm_mdss *msm_mdss, unsigned long bw)
+ {
+ int i;
+@@ -391,9 +382,6 @@ static struct msm_mdss *msm_mdss_init(struct platform_device *pdev, bool is_mdp5
+ dev_dbg(&pdev->dev, "mapped mdss address space @%pK\n", msm_mdss->mmio);
+
+ ret = msm_mdss_parse_data_bus_icc_path(&pdev->dev, msm_mdss);
+- if (ret)
+- return ERR_PTR(ret);
+- ret = devm_add_action_or_reset(&pdev->dev, msm_mdss_put_icc_path, msm_mdss);
+ if (ret)
+ return ERR_PTR(ret);
+
+--
+2.39.2
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0002_drm_msm_mdss_rename_path_references_to_mdp_path.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0002_drm_msm_mdss_rename_path_references_to_mdp_path.patch
new file mode 100644
index 0000000..6416729
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0002_drm_msm_mdss_rename_path_references_to_mdp_path.patch
@@ -0,0 +1,66 @@
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Subject: drm/msm/mdss: Rename path references to mdp_path
+Date: Sun, 03 Dec 2023 01:42:45 +0300
+
+The DPU1 driver needs to handle all MDPn<->DDR paths, as well as
+CPU<->SLAVE_DISPLAY_CFG. The former ones share how their values are
+calculated, but the latter one has static predefines spanning all SoCs.
+
+In preparation for supporting the CPU<->SLAVE_DISPLAY_CFG path, rename
+the path-related struct members to include "mdp_".
+
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Reviewed-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
+Reviewed-by: Abhinav Kumar <quic_abhinavk@quicinc.com>
+Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
+Upstream-Status: Backport [https://gitlab.freedesktop.org/lumag/msm/-/commit/fabaf176322d]
+---
+ drivers/gpu/drm/msm/msm_mdss.c | 16 ++++++++--------
+ 1 file changed, 8 insertions(+), 8 deletions(-)
+
+diff --git a/drivers/gpu/drm/msm/msm_mdss.c b/drivers/gpu/drm/msm/msm_mdss.c
+index 53bc496ace99..e1b208fd072e 100644
+--- a/drivers/gpu/drm/msm/msm_mdss.c
++++ b/drivers/gpu/drm/msm/msm_mdss.c
+@@ -40,8 +40,8 @@ struct msm_mdss {
+ struct irq_domain *domain;
+ } irq_controller;
+ const struct msm_mdss_data *mdss_data;
+- struct icc_path *path[2];
+- u32 num_paths;
++ struct icc_path *mdp_path[2];
++ u32 num_mdp_paths;
+ };
+
+ static int msm_mdss_parse_data_bus_icc_path(struct device *dev,
+@@ -54,13 +54,13 @@ static int msm_mdss_parse_data_bus_icc_path(struct device *dev,
+ if (IS_ERR_OR_NULL(path0))
+ return PTR_ERR_OR_ZERO(path0);
+
+- msm_mdss->path[0] = path0;
+- msm_mdss->num_paths = 1;
++ msm_mdss->mdp_path[0] = path0;
++ msm_mdss->num_mdp_paths = 1;
+
+ path1 = devm_of_icc_get(dev, "mdp1-mem");
+ if (!IS_ERR_OR_NULL(path1)) {
+- msm_mdss->path[1] = path1;
+- msm_mdss->num_paths++;
++ msm_mdss->mdp_path[1] = path1;
++ msm_mdss->num_mdp_paths++;
+ }
+
+ return 0;
+@@ -70,8 +70,8 @@ static void msm_mdss_icc_request_bw(struct msm_mdss *msm_mdss, unsigned long bw)
+ {
+ int i;
+
+- for (i = 0; i < msm_mdss->num_paths; i++)
+- icc_set_bw(msm_mdss->path[i], 0, Bps_to_icc(bw));
++ for (i = 0; i < msm_mdss->num_mdp_paths; i++)
++ icc_set_bw(msm_mdss->mdp_path[i], 0, Bps_to_icc(bw));
+ }
+
+ static void msm_mdss_irq(struct irq_desc *desc)
+--
+2.39.2
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0002_dt_bindings_display_msm_add_reg_bus_and_rotator_interconnects.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0002_dt_bindings_display_msm_add_reg_bus_and_rotator_interconnects.patch
new file mode 100644
index 0000000..f2822ae
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0002_dt_bindings_display_msm_add_reg_bus_and_rotator_interconnects.patch
@@ -0,0 +1,287 @@
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Subject: dt-bindings: display: msm: Add reg bus and rotator interconnects
+Date: Wed, 29 Nov 2023 15:43:59 +0100
+
+Apart from the already handled data bus (MAS_MDP_Pn<->DDR), there are
+other connection paths:
+- a path that connects rotator block to the DDR.
+- a path that needs to be handled to ensure MDSS register access
+ functions properly, namely the "reg bus", a.k.a the CPU-MDSS CFG
+ interconnect.
+
+Describe these paths to allow using them in device trees and in the
+driver.
+
+Reviewed-by: Krzysztof Kozlowski <krzysztof.kozlowski@linaro.org>
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
+Upstream-Status: Backport [https://gitlab.freedesktop.org/lumag/msm/-/commit/a1ed5860efd3]
+---
+ .../devicetree/bindings/display/msm/mdss-common.yaml | 18 ++++++++++++++----
+ .../bindings/display/msm/qcom,qcm2290-mdss.yaml | 14 ++++++++++----
+ .../bindings/display/msm/qcom,sc7180-mdss.yaml | 14 ++++++++++----
+ .../bindings/display/msm/qcom,sc7280-mdss.yaml | 14 ++++++++++----
+ .../bindings/display/msm/qcom,sm6115-mdss.yaml | 10 ++++++++++
+ .../bindings/display/msm/qcom,sm6125-mdss.yaml | 8 ++++++--
+ .../bindings/display/msm/qcom,sm6350-mdss.yaml | 8 ++++++--
+ .../bindings/display/msm/qcom,sm6375-mdss.yaml | 8 ++++++--
+ .../bindings/display/msm/qcom,sm8450-mdss.yaml | 13 ++++++++-----
+ 9 files changed, 80 insertions(+), 27 deletions(-)
+
+diff --git a/Documentation/devicetree/bindings/display/msm/mdss-common.yaml b/Documentation/devicetree/bindings/display/msm/mdss-common.yaml
+index f69196e4cc76..c6305a6e0334 100644
+--- a/Documentation/devicetree/bindings/display/msm/mdss-common.yaml
++++ b/Documentation/devicetree/bindings/display/msm/mdss-common.yaml
+@@ -61,17 +61,27 @@ properties:
+
+ ranges: true
+
++ # This is not a perfect description, but it's impossible to discern and match
++ # the entries like we do with interconnect-names
+ interconnects:
+ minItems: 1
+ items:
+ - description: Interconnect path from mdp0 (or a single mdp) port to the data bus
+ - description: Interconnect path from mdp1 port to the data bus
++ - description: Interconnect path from CPU to the reg bus
+
+ interconnect-names:
+- minItems: 1
+- items:
+- - const: mdp0-mem
+- - const: mdp1-mem
++ oneOf:
++ - minItems: 1
++ items:
++ - const: mdp0-mem
++ - const: cpu-cfg
++
++ - minItems: 2
++ items:
++ - const: mdp0-mem
++ - const: mdp1-mem
++ - const: cpu-cfg
+
+ resets:
+ items:
+diff --git a/Documentation/devicetree/bindings/display/msm/qcom,qcm2290-mdss.yaml b/Documentation/devicetree/bindings/display/msm/qcom,qcm2290-mdss.yaml
+index d71a8e09a798..f0cdb5422688 100644
+--- a/Documentation/devicetree/bindings/display/msm/qcom,qcm2290-mdss.yaml
++++ b/Documentation/devicetree/bindings/display/msm/qcom,qcm2290-mdss.yaml
+@@ -36,10 +36,14 @@ properties:
+ maxItems: 2
+
+ interconnects:
+- maxItems: 1
++ items:
++ - description: Interconnect path from mdp0 port to the data bus
++ - description: Interconnect path from CPU to the reg bus
+
+ interconnect-names:
+- maxItems: 1
++ items:
++ - const: mdp0-mem
++ - const: cpu-cfg
+
+ patternProperties:
+ "^display-controller@[0-9a-f]+$":
+@@ -98,8 +102,10 @@ examples:
+ interrupt-controller;
+ #interrupt-cells = <1>;
+
+- interconnects = <&mmrt_virt MASTER_MDP0 &bimc SLAVE_EBI1>;
+- interconnect-names = "mdp0-mem";
++ interconnects = <&mmrt_virt MASTER_MDP0 &bimc SLAVE_EBI1>,
++ <&bimc MASTER_APPSS_PROC &config_noc SLAVE_DISPLAY_CFG>;
++ interconnect-names = "mdp0-mem",
++ "cpu-cfg";
+
+ iommus = <&apps_smmu 0x420 0x2>,
+ <&apps_smmu 0x421 0x0>;
+diff --git a/Documentation/devicetree/bindings/display/msm/qcom,sc7180-mdss.yaml b/Documentation/devicetree/bindings/display/msm/qcom,sc7180-mdss.yaml
+index 3432a2407caa..7a0555b15ddf 100644
+--- a/Documentation/devicetree/bindings/display/msm/qcom,sc7180-mdss.yaml
++++ b/Documentation/devicetree/bindings/display/msm/qcom,sc7180-mdss.yaml
+@@ -36,10 +36,14 @@ properties:
+ maxItems: 1
+
+ interconnects:
+- maxItems: 1
++ items:
++ - description: Interconnect path from mdp0 port to the data bus
++ - description: Interconnect path from CPU to the reg bus
+
+ interconnect-names:
+- maxItems: 1
++ items:
++ - const: mdp0-mem
++ - const: cpu-cfg
+
+ patternProperties:
+ "^display-controller@[0-9a-f]+$":
+@@ -106,8 +110,10 @@ examples:
+ interrupt-controller;
+ #interrupt-cells = <1>;
+
+- interconnects = <&mmss_noc MASTER_MDP0 &mc_virt SLAVE_EBI1>;
+- interconnect-names = "mdp0-mem";
++ interconnects = <&mmss_noc MASTER_MDP0 &mc_virt SLAVE_EBI1>,
++ <&gem_noc MASTER_APPSS_PROC &config_noc SLAVE_DISPLAY_CFG>;
++ interconnect-names = "mdp0-mem",
++ "cpu-cfg";
+
+ iommus = <&apps_smmu 0x800 0x2>;
+ ranges;
+diff --git a/Documentation/devicetree/bindings/display/msm/qcom,sc7280-mdss.yaml b/Documentation/devicetree/bindings/display/msm/qcom,sc7280-mdss.yaml
+index bbb727831fca..2947f27e0585 100644
+--- a/Documentation/devicetree/bindings/display/msm/qcom,sc7280-mdss.yaml
++++ b/Documentation/devicetree/bindings/display/msm/qcom,sc7280-mdss.yaml
+@@ -36,10 +36,14 @@ properties:
+ maxItems: 1
+
+ interconnects:
+- maxItems: 1
++ items:
++ - description: Interconnect path from mdp0 port to the data bus
++ - description: Interconnect path from CPU to the reg bus
+
+ interconnect-names:
+- maxItems: 1
++ items:
++ - const: mdp0-mem
++ - const: cpu-cfg
+
+ patternProperties:
+ "^display-controller@[0-9a-f]+$":
+@@ -118,8 +122,10 @@ examples:
+ interrupt-controller;
+ #interrupt-cells = <1>;
+
+- interconnects = <&mmss_noc MASTER_MDP0 &mc_virt SLAVE_EBI1>;
+- interconnect-names = "mdp0-mem";
++ interconnects = <&mmss_noc MASTER_MDP0 &mc_virt SLAVE_EBI1>,
++ <&gem_noc MASTER_APPSS_PROC &cnoc2 SLAVE_DISPLAY_CFG>;
++ interconnect-names = "mdp0-mem",
++ "cpu-cfg";
+
+ iommus = <&apps_smmu 0x900 0x402>;
+ ranges;
+diff --git a/Documentation/devicetree/bindings/display/msm/qcom,sm6115-mdss.yaml b/Documentation/devicetree/bindings/display/msm/qcom,sm6115-mdss.yaml
+index dde5c2acead5..309de1953c88 100644
+--- a/Documentation/devicetree/bindings/display/msm/qcom,sm6115-mdss.yaml
++++ b/Documentation/devicetree/bindings/display/msm/qcom,sm6115-mdss.yaml
+@@ -29,6 +29,16 @@ properties:
+ iommus:
+ maxItems: 2
+
++ interconnects:
++ items:
++ - description: Interconnect path from mdp0 port to the data bus
++ - description: Interconnect path from CPU to the reg bus
++
++ interconnect-names:
++ items:
++ - const: mdp0-mem
++ - const: cpu-cfg
++
+ patternProperties:
+ "^display-controller@[0-9a-f]+$":
+ type: object
+diff --git a/Documentation/devicetree/bindings/display/msm/qcom,sm6125-mdss.yaml b/Documentation/devicetree/bindings/display/msm/qcom,sm6125-mdss.yaml
+index 671c2c2aa896..3deb9dc81c9c 100644
+--- a/Documentation/devicetree/bindings/display/msm/qcom,sm6125-mdss.yaml
++++ b/Documentation/devicetree/bindings/display/msm/qcom,sm6125-mdss.yaml
+@@ -35,10 +35,14 @@ properties:
+ maxItems: 1
+
+ interconnects:
+- maxItems: 2
++ items:
++ - description: Interconnect path from mdp0 port to the data bus
++ - description: Interconnect path from CPU to the reg bus
+
+ interconnect-names:
+- maxItems: 2
++ items:
++ - const: mdp0-mem
++ - const: cpu-cfg
+
+ patternProperties:
+ "^display-controller@[0-9a-f]+$":
+diff --git a/Documentation/devicetree/bindings/display/msm/qcom,sm6350-mdss.yaml b/Documentation/devicetree/bindings/display/msm/qcom,sm6350-mdss.yaml
+index e1dcb453762e..c9ba1fae8042 100644
+--- a/Documentation/devicetree/bindings/display/msm/qcom,sm6350-mdss.yaml
++++ b/Documentation/devicetree/bindings/display/msm/qcom,sm6350-mdss.yaml
+@@ -35,10 +35,14 @@ properties:
+ maxItems: 1
+
+ interconnects:
+- maxItems: 2
++ items:
++ - description: Interconnect path from mdp0 port to the data bus
++ - description: Interconnect path from CPU to the reg bus
+
+ interconnect-names:
+- maxItems: 2
++ items:
++ - const: mdp0-mem
++ - const: cpu-cfg
+
+ patternProperties:
+ "^display-controller@[0-9a-f]+$":
+diff --git a/Documentation/devicetree/bindings/display/msm/qcom,sm6375-mdss.yaml b/Documentation/devicetree/bindings/display/msm/qcom,sm6375-mdss.yaml
+index b15c3950f09d..8e8a288d318c 100644
+--- a/Documentation/devicetree/bindings/display/msm/qcom,sm6375-mdss.yaml
++++ b/Documentation/devicetree/bindings/display/msm/qcom,sm6375-mdss.yaml
+@@ -35,10 +35,14 @@ properties:
+ maxItems: 1
+
+ interconnects:
+- maxItems: 2
++ items:
++ - description: Interconnect path from mdp0 port to the data bus
++ - description: Interconnect path from CPU to the reg bus
+
+ interconnect-names:
+- maxItems: 2
++ items:
++ - const: mdp0-mem
++ - const: cpu-cfg
+
+ patternProperties:
+ "^display-controller@[0-9a-f]+$":
+diff --git a/Documentation/devicetree/bindings/display/msm/qcom,sm8450-mdss.yaml b/Documentation/devicetree/bindings/display/msm/qcom,sm8450-mdss.yaml
+index 001b26e65301..747a2e9665f4 100644
+--- a/Documentation/devicetree/bindings/display/msm/qcom,sm8450-mdss.yaml
++++ b/Documentation/devicetree/bindings/display/msm/qcom,sm8450-mdss.yaml
+@@ -30,10 +30,10 @@ properties:
+ maxItems: 1
+
+ interconnects:
+- maxItems: 2
++ maxItems: 3
+
+ interconnect-names:
+- maxItems: 2
++ maxItems: 3
+
+ patternProperties:
+ "^display-controller@[0-9a-f]+$":
+@@ -91,9 +91,12 @@ examples:
+ reg = <0x0ae00000 0x1000>;
+ reg-names = "mdss";
+
+- interconnects = <&mmss_noc MASTER_MDP_DISP 0 &mc_virt SLAVE_EBI1_DISP 0>,
+- <&mmss_noc MASTER_MDP_DISP 0 &mc_virt SLAVE_EBI1_DISP 0>;
+- interconnect-names = "mdp0-mem", "mdp1-mem";
++ interconnects = <&mmss_noc MASTER_MDP_DISP &mc_virt SLAVE_EBI1_DISP>,
++ <&mmss_noc MASTER_MDP_DISP &mc_virt SLAVE_EBI1_DISP>,
++ <&gem_noc MASTER_APPSS_PROC &config_noc SLAVE_DISPLAY_CFG>;
++ interconnect-names = "mdp0-mem",
++ "mdp1-mem",
++ "cpu-cfg";
+
+ resets = <&dispcc DISP_CC_MDSS_CORE_BCR>;
+
+--
+2.43.0
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0003_drm_msm_mdss_inline_msm_mdss_icc_request_bw.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0003_drm_msm_mdss_inline_msm_mdss_icc_request_bw.patch
new file mode 100644
index 0000000..5e430b1
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0003_drm_msm_mdss_inline_msm_mdss_icc_request_bw.patch
@@ -0,0 +1,69 @@
+From: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
+Subject: drm/msm/mdss: inline msm_mdss_icc_request_bw()
+Date: Sun, 03 Dec 2023 01:42:46 +0300
+
+There are just two places where we set the bandwidth: in the resume and
+in the suspend paths. Drop the wrapping function
+msm_mdss_icc_request_bw() and call icc_set_bw() directly.
+
+Reviewed-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Reviewed-by: Abhinav Kumar <quic_abhinavk@quicinc.com>
+Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
+Upstream-Status: Backport [https://gitlab.freedesktop.org/lumag/msm/-/commit/7323694e118a]
+---
+ drivers/gpu/drm/msm/msm_mdss.c | 19 ++++++++-----------
+ 1 file changed, 8 insertions(+), 11 deletions(-)
+
+diff --git a/drivers/gpu/drm/msm/msm_mdss.c b/drivers/gpu/drm/msm/msm_mdss.c
+index e1b208fd072e..eeca281e9d6d 100644
+--- a/drivers/gpu/drm/msm/msm_mdss.c
++++ b/drivers/gpu/drm/msm/msm_mdss.c
+@@ -66,14 +66,6 @@ static int msm_mdss_parse_data_bus_icc_path(struct device *dev,
+ return 0;
+ }
+
+-static void msm_mdss_icc_request_bw(struct msm_mdss *msm_mdss, unsigned long bw)
+-{
+- int i;
+-
+- for (i = 0; i < msm_mdss->num_mdp_paths; i++)
+- icc_set_bw(msm_mdss->mdp_path[i], 0, Bps_to_icc(bw));
+-}
+-
+ static void msm_mdss_irq(struct irq_desc *desc)
+ {
+ struct msm_mdss *msm_mdss = irq_desc_get_handler_data(desc);
+@@ -227,14 +219,15 @@ const struct msm_mdss_data *msm_mdss_get_mdss_data(struct device *dev)
+
+ static int msm_mdss_enable(struct msm_mdss *msm_mdss)
+ {
+- int ret;
++ int ret, i;
+
+ /*
+ * Several components have AXI clocks that can only be turned on if
+ * the interconnect is enabled (non-zero bandwidth). Let's make sure
+ * that the interconnects are at least at a minimum amount.
+ */
+- msm_mdss_icc_request_bw(msm_mdss, MIN_IB_BW);
++ for (i = 0; i < msm_mdss->num_mdp_paths; i++)
++ icc_set_bw(msm_mdss->mdp_path[i], 0, Bps_to_icc(MIN_IB_BW));
+
+ ret = clk_bulk_prepare_enable(msm_mdss->num_clocks, msm_mdss->clocks);
+ if (ret) {
+@@ -286,8 +279,12 @@ static int msm_mdss_enable(struct msm_mdss *msm_mdss)
+
+ static int msm_mdss_disable(struct msm_mdss *msm_mdss)
+ {
++ int i;
++
+ clk_bulk_disable_unprepare(msm_mdss->num_clocks, msm_mdss->clocks);
+- msm_mdss_icc_request_bw(msm_mdss, 0);
++
++ for (i = 0; i < msm_mdss->num_mdp_paths; i++)
++ icc_set_bw(msm_mdss->mdp_path[i], 0, 0);
+
+ return 0;
+ }
+--
+2.39.2
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0004_drm_msm_mdss_handle_the_reg_bus_icc_path.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0004_drm_msm_mdss_handle_the_reg_bus_icc_path.patch
new file mode 100644
index 0000000..87a4b37
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/mdss-icc/0004_drm_msm_mdss_handle_the_reg_bus_icc_path.patch
@@ -0,0 +1,238 @@
+From: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
+Subject: drm/msm/mdss: Handle the reg bus ICC path
+Date: Sun, 03 Dec 2023 01:42:47 +0300
+
+Apart from the already handled data bus (MAS_MDP_Pn<->DDR), there's
+another path that needs to be handled to ensure MDSS functions properly,
+namely the "reg bus", a.k.a the CPU-MDSS interconnect.
+
+Gating that path may have a variety of effects, from none to otherwise
+inexplicable DSI timeouts.
+
+Provide a way for MDSS driver to vote on this bus.
+
+A note regarding vote values. Newer platforms have corresponding
+bandwidth values in the vendor DT files. For the older platforms there
+was a static vote in the mdss_mdp and rotator drivers. I choose to be
+conservative here and choose this value as a default.
+
+Co-developed-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Reviewed-by: Abhinav Kumar <quic_abhinavk@quicinc.com>
+Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org>
+Upstream-Status: Backport [https://gitlab.freedesktop.org/lumag/msm/-/commit/a55c8ff252d3]
+---
+ drivers/gpu/drm/msm/msm_mdss.c | 49 +++++++++++++++++++++++++++++++---
+ drivers/gpu/drm/msm/msm_mdss.h | 1 +
+ 2 files changed, 46 insertions(+), 4 deletions(-)
+
+diff --git a/drivers/gpu/drm/msm/msm_mdss.c b/drivers/gpu/drm/msm/msm_mdss.c
+index eeca281e9d6d..18b07619d6fc 100644
+--- a/drivers/gpu/drm/msm/msm_mdss.c
++++ b/drivers/gpu/drm/msm/msm_mdss.c
+@@ -28,6 +28,8 @@
+
+ #define MIN_IB_BW 400000000UL /* Min ib vote 400MB */
+
++#define DEFAULT_REG_BW 153600 /* Used in mdss fbdev driver */
++
+ struct msm_mdss {
+ struct device *dev;
+
+@@ -42,6 +44,7 @@ struct msm_mdss {
+ const struct msm_mdss_data *mdss_data;
+ struct icc_path *mdp_path[2];
+ u32 num_mdp_paths;
++ struct icc_path *reg_bus_path;
+ };
+
+ static int msm_mdss_parse_data_bus_icc_path(struct device *dev,
+@@ -49,6 +52,7 @@ static int msm_mdss_parse_data_bus_icc_path(struct device *dev,
+ {
+ struct icc_path *path0;
+ struct icc_path *path1;
++ struct icc_path *reg_bus_path;
+
+ path0 = devm_of_icc_get(dev, "mdp0-mem");
+ if (IS_ERR_OR_NULL(path0))
+@@ -63,6 +67,10 @@ static int msm_mdss_parse_data_bus_icc_path(struct device *dev,
+ msm_mdss->num_mdp_paths++;
+ }
+
++ reg_bus_path = of_icc_get(dev, "cpu-cfg");
++ if (!IS_ERR_OR_NULL(reg_bus_path))
++ msm_mdss->reg_bus_path = reg_bus_path;
++
+ return 0;
+ }
+
+@@ -229,6 +237,13 @@ static int msm_mdss_enable(struct msm_mdss *msm_mdss)
+ for (i = 0; i < msm_mdss->num_mdp_paths; i++)
+ icc_set_bw(msm_mdss->mdp_path[i], 0, Bps_to_icc(MIN_IB_BW));
+
++ if (msm_mdss->mdss_data && msm_mdss->mdss_data->reg_bus_bw)
++ icc_set_bw(msm_mdss->reg_bus_path, 0,
++ msm_mdss->mdss_data->reg_bus_bw);
++ else
++ icc_set_bw(msm_mdss->reg_bus_path, 0,
++ DEFAULT_REG_BW);
++
+ ret = clk_bulk_prepare_enable(msm_mdss->num_clocks, msm_mdss->clocks);
+ if (ret) {
+ dev_err(msm_mdss->dev, "clock enable failed, ret:%d\n", ret);
+@@ -286,6 +301,9 @@ static int msm_mdss_disable(struct msm_mdss *msm_mdss)
+ for (i = 0; i < msm_mdss->num_mdp_paths; i++)
+ icc_set_bw(msm_mdss->mdp_path[i], 0, 0);
+
++ if (msm_mdss->reg_bus_path)
++ icc_set_bw(msm_mdss->reg_bus_path, 0, 0);
++
+ return 0;
+ }
+
+@@ -372,6 +390,8 @@ static struct msm_mdss *msm_mdss_init(struct platform_device *pdev, bool is_mdp5
+ if (!msm_mdss)
+ return ERR_PTR(-ENOMEM);
+
++ msm_mdss->mdss_data = of_device_get_match_data(&pdev->dev);
++
+ msm_mdss->mmio = devm_platform_ioremap_resource_byname(pdev, is_mdp5 ? "mdss_phys" : "mdss");
+ if (IS_ERR(msm_mdss->mmio))
+ return ERR_CAST(msm_mdss->mmio);
+@@ -462,8 +482,6 @@ static int mdss_probe(struct platform_device *pdev)
+ if (IS_ERR(mdss))
+ return PTR_ERR(mdss);
+
+- mdss->mdss_data = of_device_get_match_data(&pdev->dev);
+-
+ platform_set_drvdata(pdev, mdss);
+
+ /*
+@@ -495,11 +513,13 @@ static const struct msm_mdss_data msm8998_data = {
+ .ubwc_enc_version = UBWC_1_0,
+ .ubwc_dec_version = UBWC_1_0,
+ .highest_bank_bit = 2,
++ .reg_bus_bw = 76800,
+ };
+
+ static const struct msm_mdss_data qcm2290_data = {
+ /* no UBWC */
+ .highest_bank_bit = 0x2,
++ .reg_bus_bw = 76800,
+ };
+
+ static const struct msm_mdss_data sc7180_data = {
+@@ -507,6 +527,7 @@ static const struct msm_mdss_data sc7180_data = {
+ .ubwc_dec_version = UBWC_2_0,
+ .ubwc_static = 0x1e,
+ .highest_bank_bit = 0x3,
++ .reg_bus_bw = 76800,
+ };
+
+ static const struct msm_mdss_data sc7280_data = {
+@@ -516,6 +537,7 @@ static const struct msm_mdss_data sc7280_data = {
+ .ubwc_static = 1,
+ .highest_bank_bit = 1,
+ .macrotile_mode = 1,
++ .reg_bus_bw = 74000,
+ };
+
+ static const struct msm_mdss_data sc8180x_data = {
+@@ -523,6 +545,7 @@ static const struct msm_mdss_data sc8180x_data = {
+ .ubwc_dec_version = UBWC_3_0,
+ .highest_bank_bit = 3,
+ .macrotile_mode = 1,
++ .reg_bus_bw = 76800,
+ };
+
+ static const struct msm_mdss_data sc8280xp_data = {
+@@ -532,12 +555,14 @@ static const struct msm_mdss_data sc8280xp_data = {
+ .ubwc_static = 1,
+ .highest_bank_bit = 3,
+ .macrotile_mode = 1,
++ .reg_bus_bw = 76800,
+ };
+
+ static const struct msm_mdss_data sdm845_data = {
+ .ubwc_enc_version = UBWC_2_0,
+ .ubwc_dec_version = UBWC_2_0,
+ .highest_bank_bit = 2,
++ .reg_bus_bw = 76800,
+ };
+
+ static const struct msm_mdss_data sm6350_data = {
+@@ -546,12 +571,14 @@ static const struct msm_mdss_data sm6350_data = {
+ .ubwc_swizzle = 6,
+ .ubwc_static = 0x1e,
+ .highest_bank_bit = 1,
++ .reg_bus_bw = 76800,
+ };
+
+ static const struct msm_mdss_data sm8150_data = {
+ .ubwc_enc_version = UBWC_3_0,
+ .ubwc_dec_version = UBWC_3_0,
+ .highest_bank_bit = 2,
++ .reg_bus_bw = 76800,
+ };
+
+ static const struct msm_mdss_data sm6115_data = {
+@@ -560,6 +587,7 @@ static const struct msm_mdss_data sm6115_data = {
+ .ubwc_swizzle = 7,
+ .ubwc_static = 0x11f,
+ .highest_bank_bit = 0x1,
++ .reg_bus_bw = 76800,
+ };
+
+ static const struct msm_mdss_data sm6125_data = {
+@@ -577,6 +605,18 @@ static const struct msm_mdss_data sm8250_data = {
+ /* TODO: highest_bank_bit = 2 for LP_DDR4 */
+ .highest_bank_bit = 3,
+ .macrotile_mode = 1,
++ .reg_bus_bw = 76800,
++};
++
++static const struct msm_mdss_data sm8350_data = {
++ .ubwc_enc_version = UBWC_4_0,
++ .ubwc_dec_version = UBWC_4_0,
++ .ubwc_swizzle = 6,
++ .ubwc_static = 1,
++ /* TODO: highest_bank_bit = 2 for LP_DDR4 */
++ .highest_bank_bit = 3,
++ .macrotile_mode = 1,
++ .reg_bus_bw = 74000,
+ };
+
+ static const struct msm_mdss_data sm8550_data = {
+@@ -587,6 +627,7 @@ static const struct msm_mdss_data sm8550_data = {
+ /* TODO: highest_bank_bit = 2 for LP_DDR4 */
+ .highest_bank_bit = 3,
+ .macrotile_mode = 1,
++ .reg_bus_bw = 57000,
+ };
+ static const struct of_device_id mdss_dt_match[] = {
+ { .compatible = "qcom,mdss" },
+@@ -603,8 +644,8 @@ static const struct of_device_id mdss_dt_match[] = {
+ { .compatible = "qcom,sm6375-mdss", .data = &sm6350_data },
+ { .compatible = "qcom,sm8150-mdss", .data = &sm8150_data },
+ { .compatible = "qcom,sm8250-mdss", .data = &sm8250_data },
+- { .compatible = "qcom,sm8350-mdss", .data = &sm8250_data },
+- { .compatible = "qcom,sm8450-mdss", .data = &sm8250_data },
++ { .compatible = "qcom,sm8350-mdss", .data = &sm8350_data },
++ { .compatible = "qcom,sm8450-mdss", .data = &sm8350_data },
+ { .compatible = "qcom,sm8550-mdss", .data = &sm8550_data },
+ {}
+ };
+diff --git a/drivers/gpu/drm/msm/msm_mdss.h b/drivers/gpu/drm/msm/msm_mdss.h
+index 02bbab42adbc..3afef4b1786d 100644
+--- a/drivers/gpu/drm/msm/msm_mdss.h
++++ b/drivers/gpu/drm/msm/msm_mdss.h
+@@ -14,6 +14,7 @@ struct msm_mdss_data {
+ u32 ubwc_static;
+ u32 highest_bank_bit;
+ u32 macrotile_mode;
++ u32 reg_bus_bw;
+ };
+
+ #define UBWC_1_0 0x10000000
+--
+2.39.2
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/mpm/0001-dt-bindings-interrupt-controller-mpm-Pass-MSG-RAM-sl.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/mpm/0001-dt-bindings-interrupt-controller-mpm-Pass-MSG-RAM-sl.patch
new file mode 100644
index 0000000..4614771
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/mpm/0001-dt-bindings-interrupt-controller-mpm-Pass-MSG-RAM-sl.patch
@@ -0,0 +1,72 @@
+From d974d3afa058b6857c95e860493542807d4a2eec Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Wed, 5 Apr 2023 12:48:34 +0200
+Subject: [PATCH 1/2] dt-bindings: interrupt-controller: mpm: Pass MSG RAM
+ slice through phandle
+
+Due to the wild nature of the Qualcomm RPM Message RAM, we can't really
+use 'reg' to point to the MPM's slice of Message RAM without cutting into
+an already-defined RPM MSG RAM node used for GLINK and SMEM.
+
+Document passing the register space as a slice of SRAM through the
+qcom,rpm-msg-ram property. This also makes 'reg' deprecated.
+
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git d974d3afa058]
+---
+ .../bindings/interrupt-controller/qcom,mpm.yaml | 12 +++++++++---
+ 1 file changed, 9 insertions(+), 3 deletions(-)
+
+diff --git a/Documentation/devicetree/bindings/interrupt-controller/qcom,mpm.yaml b/Documentation/devicetree/bindings/interrupt-controller/qcom,mpm.yaml
+index 6a206111d4e0..ec957949a440 100644
+--- a/Documentation/devicetree/bindings/interrupt-controller/qcom,mpm.yaml
++++ b/Documentation/devicetree/bindings/interrupt-controller/qcom,mpm.yaml
+@@ -29,6 +29,12 @@ properties:
+ maxItems: 1
+ description:
+ Specifies the base address and size of vMPM registers in RPM MSG RAM.
++ deprecated: true
++
++ qcom,rpm-msg-ram:
++ $ref: /schemas/types.yaml#/definitions/phandle
++ description:
++ Phandle to the APSS MPM slice of the RPM Message RAM
+
+ interrupts:
+ maxItems: 1
+@@ -67,23 +73,22 @@ properties:
+
+ required:
+ - compatible
+- - reg
+ - interrupts
+ - mboxes
+ - interrupt-controller
+ - '#interrupt-cells'
+ - qcom,mpm-pin-count
+ - qcom,mpm-pin-map
++ - qcom,rpm-msg-ram
+
+ additionalProperties: false
+
+ examples:
+ - |
+ #include <dt-bindings/interrupt-controller/arm-gic.h>
+- mpm: interrupt-controller@45f01b8 {
++ mpm: interrupt-controller {
+ compatible = "qcom,mpm";
+ interrupts = <GIC_SPI 197 IRQ_TYPE_EDGE_RISING>;
+- reg = <0x45f01b8 0x1000>;
+ mboxes = <&apcs_glb 1>;
+ interrupt-controller;
+ #interrupt-cells = <2>;
+@@ -96,5 +101,6 @@ examples:
+ <86 183>,
+ <90 260>,
+ <91 260>;
++ qcom,rpm-msg-ram = <&apss_mpm>;
+ #power-domain-cells = <0>;
+ };
+--
+2.39.2
+
diff --git a/recipes-kernel/linux/linux-yocto/generic-drivers/mpm/0002-irqchip-irq-qcom-mpm-Support-passing-a-slice-of-SRAM.patch b/recipes-kernel/linux/linux-yocto/generic-drivers/mpm/0002-irqchip-irq-qcom-mpm-Support-passing-a-slice-of-SRAM.patch
new file mode 100644
index 0000000..bb9a7c3
--- /dev/null
+++ b/recipes-kernel/linux/linux-yocto/generic-drivers/mpm/0002-irqchip-irq-qcom-mpm-Support-passing-a-slice-of-SRAM.patch
@@ -0,0 +1,78 @@
+From 24ac56bf8085adf448b6db9574d9b16ed5cd6c0b Mon Sep 17 00:00:00 2001
+From: Konrad Dybcio <konrad.dybcio@linaro.org>
+Date: Wed, 5 Apr 2023 12:48:35 +0200
+Subject: [PATCH 2/2] irqchip: irq-qcom-mpm: Support passing a slice of SRAM as
+ reg space
+
+The MPM hardware is accessible to us from the ARM CPUs through a shared
+memory region (RPM MSG RAM) that's also concurrently accessed by other
+kinds of cores on the system (like modem, ADSP etc.). Modeling this
+relation in a (somewhat) sane manner in the device tree basically
+requires us to either present the MPM as a child of said memory region
+(which makes little sense, as a mapped memory carveout is not a bus),
+define nodes which bleed their register spaces into one another, or
+passing their slice of the MSG RAM through some kind of a property.
+
+Go with the third option and add a way to map a region passed through
+the "qcom,rpm-msg-ram" property as our register space.
+
+The current way of using 'reg' is preserved for ABI reasons.
+
+Acked-by: Shawn Guo <shawn.guo@linaro.org>
+Signed-off-by: Konrad Dybcio <konrad.dybcio@linaro.org>
+Upstream-Status: Backport [https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git 24ac56bf8085]
+---
+ drivers/irqchip/irq-qcom-mpm.c | 21 ++++++++++++++++++---
+ 1 file changed, 18 insertions(+), 3 deletions(-)
+
+diff --git a/drivers/irqchip/irq-qcom-mpm.c b/drivers/irqchip/irq-qcom-mpm.c
+index 7124565234a5..7115e3056aa5 100644
+--- a/drivers/irqchip/irq-qcom-mpm.c
++++ b/drivers/irqchip/irq-qcom-mpm.c
+@@ -14,6 +14,7 @@
+ #include <linux/mailbox_client.h>
+ #include <linux/module.h>
+ #include <linux/of.h>
++#include <linux/of_address.h>
+ #include <linux/of_platform.h>
+ #include <linux/platform_device.h>
+ #include <linux/pm_domain.h>
+@@ -322,8 +323,10 @@ static int qcom_mpm_init(struct device_node *np, struct device_node *parent)
+ struct device *dev = &pdev->dev;
+ struct irq_domain *parent_domain;
+ struct generic_pm_domain *genpd;
++ struct device_node *msgram_np;
+ struct qcom_mpm_priv *priv;
+ unsigned int pin_cnt;
++ struct resource res;
+ int i, irq;
+ int ret;
+
+@@ -374,9 +377,21 @@ static int qcom_mpm_init(struct device_node *np, struct device_node *parent)
+
+ raw_spin_lock_init(&priv->lock);
+
+- priv->base = devm_platform_ioremap_resource(pdev, 0);
+- if (IS_ERR(priv->base))
+- return PTR_ERR(priv->base);
++ /* If we have a handle to an RPM message ram partition, use it. */
++ msgram_np = of_parse_phandle(np, "qcom,rpm-msg-ram", 0);
++ if (msgram_np) {
++ ret = of_address_to_resource(msgram_np, 0, &res);
++ /* Don't use devm_ioremap_resource, as we're accessing a shared region. */
++ priv->base = devm_ioremap(dev, res.start, resource_size(&res));
++ of_node_put(msgram_np);
++ if (IS_ERR(priv->base))
++ return PTR_ERR(priv->base);
++ } else {
++ /* Otherwise, fall back to simple MMIO. */
++ priv->base = devm_platform_ioremap_resource(pdev, 0);
++ if (IS_ERR(priv->base))
++ return PTR_ERR(priv->base);
++ }
+
+ for (i = 0; i < priv->reg_stride; i++) {
+ qcom_mpm_write(priv, MPM_REG_ENABLE, i, 0);
+--
+2.39.2
+