From e4ab5d7cb5f19858305395e034f214c92afc3cf5 Mon Sep 17 00:00:00 2001 From: Andrew Halaney Date: Thu, 25 Jul 2024 11:23:33 -0500 Subject: [PATCH 1/8] soc: qcom: pd-mapper: Depend on ARCH_QCOM || COMPILE_TEST The pd-mapper driver doesn't make sense on non Qualcomm systems. Let's follow suit with the rest of the Qualcomm SoC Kconfigs and depend on ARCH_QCOM || COMPILE_TEST to avoid asking users about a config they will not use. Fixes: 1ebcde047c54 ("soc: qcom: add pd-mapper implementation") Signed-off-by: Andrew Halaney Reviewed-by: Dmitry Baryshkov Link: https://lore.kernel.org/r/20240725-pd-mapper-config-v1-1-f26e513608c6@redhat.com Signed-off-by: Bjorn Andersson --- drivers/soc/qcom/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/soc/qcom/Kconfig b/drivers/soc/qcom/Kconfig index 7f02f0525933..74b9121240f8 100644 --- a/drivers/soc/qcom/Kconfig +++ b/drivers/soc/qcom/Kconfig @@ -77,7 +77,7 @@ config QCOM_PD_MAPPER select QCOM_QMI_HELPERS select QCOM_PDR_MSG select AUXILIARY_BUS - depends on NET && QRTR + depends on NET && QRTR && (ARCH_QCOM || COMPILE_TEST) default QCOM_RPROC_COMMON help The Protection Domain Mapper maps registered services to the domains From f9bb896eab221618927ae6a2f1d566567999839d Mon Sep 17 00:00:00 2001 From: Volodymyr Babchuk Date: Thu, 18 Jul 2024 11:33:23 +0530 Subject: [PATCH 2/8] soc: qcom: cmd-db: Map shared memory as WC, not WB Linux does not write into cmd-db region. This region of memory is write protected by XPU. XPU may sometime falsely detect clean cache eviction as "write" into the write protected region leading to secure interrupt which causes an endless loop somewhere in Trust Zone. The only reason it is working right now is because Qualcomm Hypervisor maps the same region as Non-Cacheable memory in Stage 2 translation tables. The issue manifests if we want to use another hypervisor (like Xen or KVM), which does not know anything about those specific mappings. Changing the mapping of cmd-db memory from MEMREMAP_WB to MEMREMAP_WT/WC removes dependency on correct mappings in Stage 2 tables. This patch fixes the issue by updating the mapping to MEMREMAP_WC. I tested this on SA8155P with Xen. Fixes: 312416d9171a ("drivers: qcom: add command DB driver") Cc: stable@vger.kernel.org # 5.4+ Signed-off-by: Volodymyr Babchuk Tested-by: Nikita Travkin # sc7180 WoA in EL2 Signed-off-by: Maulik Shah Tested-by: Pavankumar Kondeti Reviewed-by: Caleb Connolly Link: https://lore.kernel.org/r/20240718-cmd_db_uncached-v2-1-f6cf53164c90@quicinc.com Signed-off-by: Bjorn Andersson --- drivers/soc/qcom/cmd-db.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/soc/qcom/cmd-db.c b/drivers/soc/qcom/cmd-db.c index d84572662017..ae66c2623d25 100644 --- a/drivers/soc/qcom/cmd-db.c +++ b/drivers/soc/qcom/cmd-db.c @@ -349,7 +349,7 @@ static int cmd_db_dev_probe(struct platform_device *pdev) return -EINVAL; } - cmd_db_header = memremap(rmem->base, rmem->size, MEMREMAP_WB); + cmd_db_header = memremap(rmem->base, rmem->size, MEMREMAP_WC); if (!cmd_db_header) { ret = -ENOMEM; cmd_db_header = NULL; From dbd6bd124e34f9f859271ed9ae2afc39f36c7e8c Mon Sep 17 00:00:00 2001 From: Arnd Bergmann Date: Fri, 19 Jul 2024 12:12:31 +0200 Subject: [PATCH 3/8] soc: qcom: pd-mapper: mark qcom_pdm_domains as __maybe_unused The qcom_pdm_domains[] array is used only when passing it into of_match_node() but is not also referenced by MODULE_DEVICE_TABLE() or the platform driver as a table. When CONFIG_OF is disabled, this causes a harmless build warning: drivers/soc/qcom/qcom_pd_mapper.c:520:34: error: 'qcom_pdm_domains' defined but not used [-Werror=unused-const-variable=] Avoid this by marking the variable as __maybe_unused. This also makes it clear that anything referenced by it will be dropped by the compiler when it is unused. Fixes: 1ebcde047c54 ("soc: qcom: add pd-mapper implementation") Signed-off-by: Arnd Bergmann Reviewed-by: Dmitry Baryshkov Link: https://lore.kernel.org/r/20240719101238.199850-1-arnd@kernel.org Signed-off-by: Bjorn Andersson --- drivers/soc/qcom/qcom_pd_mapper.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/soc/qcom/qcom_pd_mapper.c b/drivers/soc/qcom/qcom_pd_mapper.c index a4c007080665..9afa09c3920e 100644 --- a/drivers/soc/qcom/qcom_pd_mapper.c +++ b/drivers/soc/qcom/qcom_pd_mapper.c @@ -517,7 +517,7 @@ static const struct qcom_pdm_domain_data *sm8550_domains[] = { NULL, }; -static const struct of_device_id qcom_pdm_domains[] = { +static const struct of_device_id qcom_pdm_domains[] __maybe_unused = { { .compatible = "qcom,apq8064", .data = NULL, }, { .compatible = "qcom,apq8074", .data = NULL, }, { .compatible = "qcom,apq8084", .data = NULL, }, From 72c93f3e0dcdc05fceafcb32e79352a45716d181 Mon Sep 17 00:00:00 2001 From: Konrad Dybcio Date: Fri, 26 Jul 2024 13:18:23 +0200 Subject: [PATCH 4/8] mailmap: Add an entry for Konrad Dybcio Map my old addresses. Signed-off-by: Konrad Dybcio Signed-off-by: Konrad Dybcio Acked-by: Neil Armstrong Link: https://lore.kernel.org/r/20240726-topic-konrad_email-v1-1-f94665da2919@kernel.org Signed-off-by: Bjorn Andersson --- .mailmap | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.mailmap b/.mailmap index e51d76df75c2..d189c6424697 100644 --- a/.mailmap +++ b/.mailmap @@ -353,6 +353,8 @@ Kenneth Westfield Kiran Gunda Kirill Tkhai Kishon Vijay Abraham I +Konrad Dybcio +Konrad Dybcio Konstantin Khlebnikov Konstantin Khlebnikov Koushik From fce6a1eefb2a1db706fa17ca21e3e7107811d2e8 Mon Sep 17 00:00:00 2001 From: Konrad Dybcio Date: Fri, 26 Jul 2024 13:18:24 +0200 Subject: [PATCH 5/8] MAINTAINERS: Update Konrad Dybcio's email address Use my @kernel.org address everywhere. Signed-off-by: Konrad Dybcio Signed-off-by: Konrad Dybcio Acked-by: Neil Armstrong Link: https://lore.kernel.org/r/20240726-topic-konrad_email-v1-2-f94665da2919@kernel.org Signed-off-by: Bjorn Andersson --- MAINTAINERS | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/MAINTAINERS b/MAINTAINERS index 42decde38320..7b599269a821 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -2745,7 +2745,7 @@ F: include/linux/soc/qcom/ ARM/QUALCOMM SUPPORT M: Bjorn Andersson -M: Konrad Dybcio +M: Konrad Dybcio L: linux-arm-msm@vger.kernel.org S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/qcom/linux.git @@ -7106,7 +7106,7 @@ F: drivers/gpu/drm/tiny/panel-mipi-dbi.c DRM DRIVER for Qualcomm Adreno GPUs M: Rob Clark R: Sean Paul -R: Konrad Dybcio +R: Konrad Dybcio L: linux-arm-msm@vger.kernel.org L: dri-devel@lists.freedesktop.org L: freedreno@lists.freedesktop.org @@ -18771,7 +18771,7 @@ F: include/uapi/drm/qaic_accel.h QUALCOMM CORE POWER REDUCTION (CPR) AVS DRIVER M: Bjorn Andersson -M: Konrad Dybcio +M: Konrad Dybcio L: linux-pm@vger.kernel.org L: linux-arm-msm@vger.kernel.org S: Maintained From 9960085a3a82c58d3323c1c20b991db6045063b0 Mon Sep 17 00:00:00 2001 From: Murali Nalajala Date: Wed, 14 Aug 2024 15:32:44 -0700 Subject: [PATCH 6/8] firmware: qcom: scm: Mark get_wq_ctx() as atomic call Currently get_wq_ctx() is wrongly configured as a standard call. When two SMC calls are in sleep and one SMC wakes up, it calls get_wq_ctx() to resume the corresponding sleeping thread. But if get_wq_ctx() is interrupted, goes to sleep and another SMC call is waiting to be allocated a waitq context, it leads to a deadlock. To avoid this get_wq_ctx() must be an atomic call and can't be a standard SMC call. Hence mark get_wq_ctx() as a fast call. Fixes: 6bf325992236 ("firmware: qcom: scm: Add wait-queue handling logic") Cc: stable@vger.kernel.org Signed-off-by: Murali Nalajala Signed-off-by: Unnathi Chalicheemala Reviewed-by: Elliot Berman Link: https://lore.kernel.org/r/20240814223244.40081-1-quic_uchalich@quicinc.com Signed-off-by: Bjorn Andersson --- drivers/firmware/qcom/qcom_scm-smc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/firmware/qcom/qcom_scm-smc.c b/drivers/firmware/qcom/qcom_scm-smc.c index dca5f3f1883b..2b4c2826f572 100644 --- a/drivers/firmware/qcom/qcom_scm-smc.c +++ b/drivers/firmware/qcom/qcom_scm-smc.c @@ -73,7 +73,7 @@ int scm_get_wq_ctx(u32 *wq_ctx, u32 *flags, u32 *more_pending) struct arm_smccc_res get_wq_res; struct arm_smccc_args get_wq_ctx = {0}; - get_wq_ctx.args[0] = ARM_SMCCC_CALL_VAL(ARM_SMCCC_STD_CALL, + get_wq_ctx.args[0] = ARM_SMCCC_CALL_VAL(ARM_SMCCC_FAST_CALL, ARM_SMCCC_SMC_64, ARM_SMCCC_OWNER_SIP, SCM_SMC_FNID(QCOM_SCM_SVC_WAITQ, QCOM_SCM_WAITQ_GET_WQ_CTX)); From 1c753d001a259d0278fe318a1ed3c8aa5f3ea09e Mon Sep 17 00:00:00 2001 From: Bartosz Golaszewski Date: Wed, 31 Jul 2024 09:44:56 +0200 Subject: [PATCH 7/8] firmware: qcom: tzmem: fix virtual-to-physical address conversion We currently only correctly convert the virtual address passed by the caller to qcom_tzmem_to_phys() if it corresponds to the base address of the chunk. If the user wants to convert some pointer at an offset relative to that base address, we'll return 0. Let's change the implementation of qcom_tzmem_to_phys(): iterate over the chunks and try to call gen_pool_virt_to_phys() just-in-time instead of trying to call it only once when creating the chunk. Fixes: 84f5a7b67b61 ("firmware: qcom: add a dedicated TrustZone buffer allocator") Reported-by: Johan Hovold Closes: https://lore.kernel.org/lkml/20240729095542.21097-1-johan+linaro@kernel.org/ Acked-by: Andrew Halaney Signed-off-by: Bartosz Golaszewski Link: https://lore.kernel.org/r/20240731-tzmem-efivars-fix-v2-1-f0e84071ec07@linaro.org Signed-off-by: Bjorn Andersson --- drivers/firmware/qcom/qcom_tzmem.c | 32 ++++++++++++++++++++---------- 1 file changed, 21 insertions(+), 11 deletions(-) diff --git a/drivers/firmware/qcom/qcom_tzmem.c b/drivers/firmware/qcom/qcom_tzmem.c index 17948cfc82e7..caedeef0059c 100644 --- a/drivers/firmware/qcom/qcom_tzmem.c +++ b/drivers/firmware/qcom/qcom_tzmem.c @@ -40,7 +40,6 @@ struct qcom_tzmem_pool { }; struct qcom_tzmem_chunk { - phys_addr_t paddr; size_t size; struct qcom_tzmem_pool *owner; }; @@ -385,7 +384,6 @@ again: return NULL; } - chunk->paddr = gen_pool_virt_to_phys(pool->genpool, vaddr); chunk->size = size; chunk->owner = pool; @@ -431,25 +429,37 @@ void qcom_tzmem_free(void *vaddr) EXPORT_SYMBOL_GPL(qcom_tzmem_free); /** - * qcom_tzmem_to_phys() - Map the virtual address of a TZ buffer to physical. - * @vaddr: Virtual address of the buffer allocated from a TZ memory pool. + * qcom_tzmem_to_phys() - Map the virtual address of TZ memory to physical. + * @vaddr: Virtual address of memory allocated from a TZ memory pool. * - * Can be used in any context. The address must have been returned by a call - * to qcom_tzmem_alloc(). + * Can be used in any context. The address must point to memory allocated + * using qcom_tzmem_alloc(). * - * Returns: Physical address of the buffer. + * Returns: + * Physical address mapped from the virtual or 0 if the mapping failed. */ phys_addr_t qcom_tzmem_to_phys(void *vaddr) { struct qcom_tzmem_chunk *chunk; + struct radix_tree_iter iter; + void __rcu **slot; + phys_addr_t ret; guard(spinlock_irqsave)(&qcom_tzmem_chunks_lock); - chunk = radix_tree_lookup(&qcom_tzmem_chunks, (unsigned long)vaddr); - if (!chunk) - return 0; + radix_tree_for_each_slot(slot, &qcom_tzmem_chunks, &iter, 0) { + chunk = radix_tree_deref_slot_protected(slot, + &qcom_tzmem_chunks_lock); - return chunk->paddr; + ret = gen_pool_virt_to_phys(chunk->owner->genpool, + (unsigned long)vaddr); + if (ret == -1) + continue; + + return ret; + } + + return 0; } EXPORT_SYMBOL_GPL(qcom_tzmem_to_phys); From 924fc22c282edbf93869b150d9e1b47e0b10485e Mon Sep 17 00:00:00 2001 From: Bartosz Golaszewski Date: Wed, 31 Jul 2024 09:44:57 +0200 Subject: [PATCH 8/8] firmware: qcom: qseecom: remove unused functions qseecom_scm_dev(), qseecom_dma_alloc() and qseecom_dma_free() are no longer used following the conversion to using tzmem. Remove them. Fixes: 6612103ec35a ("firmware: qcom: qseecom: convert to using the TZ allocator") Reviewed-by: Andrew Halaney Signed-off-by: Bartosz Golaszewski Link: https://lore.kernel.org/r/20240731-tzmem-efivars-fix-v2-2-f0e84071ec07@linaro.org Signed-off-by: Bjorn Andersson --- include/linux/firmware/qcom/qcom_qseecom.h | 45 ---------------------- 1 file changed, 45 deletions(-) diff --git a/include/linux/firmware/qcom/qcom_qseecom.h b/include/linux/firmware/qcom/qcom_qseecom.h index 1dc5b3b50aa9..3387897bf368 100644 --- a/include/linux/firmware/qcom/qcom_qseecom.h +++ b/include/linux/firmware/qcom/qcom_qseecom.h @@ -25,51 +25,6 @@ struct qseecom_client { u32 app_id; }; -/** - * qseecom_scm_dev() - Get the SCM device associated with the QSEECOM client. - * @client: The QSEECOM client device. - * - * Returns the SCM device under which the provided QSEECOM client device - * operates. This function is intended to be used for DMA allocations. - */ -static inline struct device *qseecom_scm_dev(struct qseecom_client *client) -{ - return client->aux_dev.dev.parent->parent; -} - -/** - * qseecom_dma_alloc() - Allocate DMA memory for a QSEECOM client. - * @client: The QSEECOM client to allocate the memory for. - * @size: The number of bytes to allocate. - * @dma_handle: Pointer to where the DMA address should be stored. - * @gfp: Allocation flags. - * - * Wrapper function for dma_alloc_coherent(), allocating DMA memory usable for - * TZ/QSEECOM communication. Refer to dma_alloc_coherent() for details. - */ -static inline void *qseecom_dma_alloc(struct qseecom_client *client, size_t size, - dma_addr_t *dma_handle, gfp_t gfp) -{ - return dma_alloc_coherent(qseecom_scm_dev(client), size, dma_handle, gfp); -} - -/** - * dma_free_coherent() - Free QSEECOM DMA memory. - * @client: The QSEECOM client for which the memory has been allocated. - * @size: The number of bytes allocated. - * @cpu_addr: Virtual memory address to free. - * @dma_handle: DMA memory address to free. - * - * Wrapper function for dma_free_coherent(), freeing memory previously - * allocated with qseecom_dma_alloc(). Refer to dma_free_coherent() for - * details. - */ -static inline void qseecom_dma_free(struct qseecom_client *client, size_t size, - void *cpu_addr, dma_addr_t dma_handle) -{ - return dma_free_coherent(qseecom_scm_dev(client), size, cpu_addr, dma_handle); -} - /** * qcom_qseecom_app_send() - Send to and receive data from a given QSEE app. * @client: The QSEECOM client associated with the target app.