From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from mx0b-0031df01.pphosted.com (mx0b-0031df01.pphosted.com [205.220.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id CA19B31F992 for ; Fri, 3 Jul 2026 04:45:41 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.180.131 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783053955; cv=none; b=muvBgLmavSLsgPkPtYcQJvyDh/eM5/lqpbWnXoxPDH7Y7/4HpsvNKMLSq+N2ic0JEwdBnSYD+QVezyBIIGwYbZ6OUR+5W8X6BdhppOmpu7I1fZFTW9XifXHmduYciX5kI9AjqQXJouv2xban6bZ/EhcBAqGM9BAWhNzKnpHdptI= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1783053955; c=relaxed/simple; bh=QL+b1Uv/Tr6IbU7khICMy0KbSNqhdxtZNbBtNoUgWVQ=; h=Message-ID:Date:MIME-Version:Subject:To:References:From:Cc: In-Reply-To:Content-Type; b=ay6FM8ghcJd8LPgG7RD4RC9mjYVbiK5WDaNdOBIQhd/etRpJZLdvTSkKs5CBj/chgxi87LWgCgCLhszfCF42zHSHjBY4BoR/cAM9HPF18wScX29W3/pryP1+7+v9JC+kWEgFZh/Rw2DpBphcDqy4ISQA+DoorLqovAYB0+F3hD4= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oss.qualcomm.com; spf=pass smtp.mailfrom=oss.qualcomm.com; dkim=pass (2048-bit key) header.d=qualcomm.com header.i=@qualcomm.com header.b=i6c+HR87; dkim=pass (2048-bit key) header.d=oss.qualcomm.com header.i=@oss.qualcomm.com header.b=HKtpLfjK; arc=none smtp.client-ip=205.220.180.131 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oss.qualcomm.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=oss.qualcomm.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=qualcomm.com header.i=@qualcomm.com header.b="i6c+HR87"; dkim=pass (2048-bit key) header.d=oss.qualcomm.com header.i=@oss.qualcomm.com header.b="HKtpLfjK" Received: from pps.filterd (m0279868.ppops.net [127.0.0.1]) by mx0a-0031df01.pphosted.com (8.18.1.11/8.18.1.11) with ESMTP id 66342Wcx2817733 for ; Fri, 3 Jul 2026 04:45:40 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=qualcomm.com; h= cc:content-transfer-encoding:content-type:date:from:in-reply-to :message-id:mime-version:references:subject:to; s=qcppdkim1; bh= mK64gRUrP1jCi37aIEHAFmpI/+fr4iexNBUgM3vWG1k=; b=i6c+HR87E+mptGUT c6J73ULsKq4y2pb3ZoBgo5KOrCZezfUzcLZcA9jauzR31XS+BRxE5gYvBbVd/s/S BftW3VHjhc2yqIULhA9LxiN38VF7ZnD8qme4DbrMtYOlGvdc0tt/CZah3KQKN42s bY7PAFRCew6Qz03DSwS5T0HAhfD/C/oAVol3dvXNeUBN9T59qIDtw2CJDaFQLw1e Dd2fl86Z3/kZUlvvv+6UMB6wXaTffooGv2RAWCkc4EmNyC43X5IrPAI9He3Ytz3H DmPGCpGfRdsV6g6bZ3eM8Ic++i+yEIWRagqxkltjVt196P5hrAgLEoQyqR6N3n8c QQudNw== Received: from mail-pl1-f200.google.com (mail-pl1-f200.google.com [209.85.214.200]) by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 4f5tpnjh8q-1 (version=TLSv1.3 cipher=TLS_AES_128_GCM_SHA256 bits=128 verify=NOT) for ; Fri, 03 Jul 2026 04:45:39 +0000 (GMT) Received: by mail-pl1-f200.google.com with SMTP id d9443c01a7336-2ca0d4fb061so3314335ad.3 for ; Thu, 02 Jul 2026 21:45:39 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oss.qualcomm.com; s=google; t=1783053939; x=1783658739; darn=vger.kernel.org; h=content-transfer-encoding:in-reply-to:cc:from:content-language :references:to:subject:user-agent:mime-version:date:message-id:from :to:cc:subject:date:message-id:reply-to; bh=mK64gRUrP1jCi37aIEHAFmpI/+fr4iexNBUgM3vWG1k=; b=HKtpLfjKgZfxm5xqt/SxHaCq+dRJFCLQfuIUoFn7FGcEjtSlcTowZO+paOPJkgxxAD lQyI6jyPd0qrd59OD8UqxEIIH7Hej8F79LGLa6zzLPTiTcYM70RpoYdZgR+Z1x4y4fR1 qKf8i4PQLy6EbY0Lq1ZjFQXNiHlZQiYxWb0gTyKUV7Ul1ST10r2nEfdJOxJ+7Qu4QsNn kiQeF5C4UUGs2Vu5mn3MXqZEez2umh0N7aVxBkPlLokrXxUfIpdu98dt+HTBNzbZiJ85 2zBouEjufJIKSKgW4MPs0C+OJta0B4P2NzqUKirgN4fOQBOMC7Q4CsnVrkkdYkUcXR2h f17g== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20251104; t=1783053939; x=1783658739; h=content-transfer-encoding:in-reply-to:cc:from:content-language :references:to:subject:user-agent:mime-version:date:message-id :x-gm-gg:x-gm-message-state:from:to:cc:subject:date:message-id :reply-to; bh=mK64gRUrP1jCi37aIEHAFmpI/+fr4iexNBUgM3vWG1k=; b=WR7W82NwkSB0TjI651v835bUfmmCj1eULkrvq7u5UWaSZVjykDe8Q2WrdJio9fcU7O p02i5JbImIpbcsrVaszF/EOSBDyoZGoj9aN/mSsOPKvgHK1SHcnRvwZUlRVIMyuo+xeT zNwqGAtkDeMJ6NI2Ml4SB9MkgkV38nfpS7PbcZZDv1VVaEVShpyPwQ2ElY/zbLvTHAb5 Y5APq5mlkpiIVtGeMVsPb5zOHzzr4UeL6QVO8z5W49QGBSxhagyjI1CNobAQ00TGIeMr 5NSdBRxrzEk+WC56FQ2CpiFxgXEg2ajEQjxnVx5qyhqe94iH1FvElGyQwn5EKHpw/QXe 2kfw== X-Forwarded-Encrypted: i=1; AHgh+Rq54reJSyjLavkZpwrhV74Clidmqa2DVBbyOUqchxETx9iNRZ01CTgnMGXJglv2dO0CpdWQI2cpfFdFzI8=@vger.kernel.org X-Gm-Message-State: AOJu0Yxaf2lEDOdlaBbZ6X7bRwOPgSeZECYQQ5oSO9MHuMPP8Grf74FZ SDp5Ev1voSUn6oFgDavPXSu7HF7+RRskvBSOOOMvAdKs0OV1BZE4lxJYOSiKLyNX8xPnvtemd66 RhzG4rmVjXVKUMEwk039wXlp2YIkTVlKmosZamPHvMPBejoM4UFn6FAv5u+pU+3h9T6E= X-Gm-Gg: AfdE7cnMrqY8GVgmR+nKS0gncmsoJcJdv/mHJ1PcT05WpiOSNhEWTeClKyyi8WgN3rC gY5/fD+RntSYbSXlMsNm6xfmqYw5spLBVM2lY+szMm6NByKYJLACnrYTHLcNI/xhpY+PJyUvDNU x0vMSd2sL34pggyhvKyF2b2RpkvkS/fRPqQrYuC5EL+saO1AuXFu5CUveNxhzb4bCFx3S0yhugC 5WOX+Qxi9GMkK4X6YUUNGzBAg4VY45GVDdaLlhFP3BZFMdpsj3zwvfWxqRgu5ktEGh0yJiGA7vI 82GtXX4hp1/TAV9gI/ji9yRS/nRyUvKG7ENnEOt7alPZkyQnZLOERrwVEDTtHXQrQcqeagVxC6E 33dLUR1umJbcKjTvNk4kwxcJtJabxOMK35kefCAZygVwix5qjHUZHkFMzOPHiK1Fg82eX09ljCs +nI7H6Xw== X-Received: by 2002:a17:902:f543:b0:2ca:5d24:720b with SMTP id d9443c01a7336-2ca7e882dd6mr98199565ad.39.1783053938696; Thu, 02 Jul 2026 21:45:38 -0700 (PDT) X-Received: by 2002:a17:902:f543:b0:2ca:5d24:720b with SMTP id d9443c01a7336-2ca7e882dd6mr98199175ad.39.1783053937967; Thu, 02 Jul 2026 21:45:37 -0700 (PDT) Received: from [10.133.33.167] (tpe-colo-wan-fw-bordernet.qualcomm.com. [103.229.16.4]) by smtp.gmail.com with ESMTPSA id d9443c01a7336-2cad776589fsm3083945ad.43.2026.07.02.21.45.32 (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Thu, 02 Jul 2026 21:45:35 -0700 (PDT) Message-ID: <056046b5-00bf-449a-8945-43fa11329286@oss.qualcomm.com> Date: Fri, 3 Jul 2026 12:45:16 +0800 Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 User-Agent: Mozilla Thunderbird Subject: Re: [PATCH v8 3/4] misc: fastrpc: Allocate entire reserved memory for Audio PD in probe To: Srinivas Kandagatla References: <20260609025938.457-1-jianping.li@oss.qualcomm.com> <20260609025938.457-4-jianping.li@oss.qualcomm.com> Content-Language: en-US From: Jianping Li Cc: amahesh@qti.qualcomm.com, Ekansh Gupta , arnd@arndb.de, Greg KH , abelvesa@kernel.org, jorge.ramirez-ortiz@linaro.org, linux-arm-msm@vger.kernel.org, dri-devel@lists.freedesktop.org, linux-kernel@vger.kernel.org, quic_chennak@quicinc.com In-Reply-To: Content-Type: text/plain; charset=UTF-8; format=flowed Content-Transfer-Encoding: 8bit X-Proofpoint-GUID: Z9o1p_SttInJjOlpvOntqMu70yGTHTzd X-Proofpoint-ORIG-GUID: Z9o1p_SttInJjOlpvOntqMu70yGTHTzd X-Authority-Analysis: v=2.4 cv=UMft2ify c=1 sm=1 tr=0 ts=6a473e73 cx=c_pps a=IZJwPbhc+fLeJZngyXXI0A==:117 a=nuhDOHQX5FNHPW3J6Bj6AA==:17 a=IkcTkHD0fZMA:10 a=RAioF0-LDSMA:10 a=s4-Qcg_JpJYA:10 a=VkNPw1HP01LnGYTKEx00:22 a=u7WPNUs3qKkmUXheDGA7:22 a=ZpdpYltYx_vBUK5n70dp:22 a=VwQbUJbxAAAA:8 a=EUspDBNiAAAA:8 a=kdAfD6VJjniLw_QBAp4A:9 a=3ZKOabzyN94A:10 a=QEXdDO2ut3YA:10 a=uG9DUKGECoFWVXl0Dc02:22 X-Proofpoint-Spam-Info: AW1haW4tMjYwNzAzMDA0MSBTYWx0ZWRfXzzkTzqThfZc7 DSNhGjxXUC6Q1kXCH4d6TSeBbMPfZIF9pg7+nhL+grcKkNL8slvoPyqzv9EGYFsDL41pM/+8hJ5 uyPyqnmOj+EAJ6SmaVpTtwVa1zZO3Lg= X-Proofpoint-Spam-Details-Enc: AW1haW4tMjYwNzAzMDA0MSBTYWx0ZWRfX7FyrSA2JYCmv bQu0ZGSBFelf1o/aBaNDkoG9GVwN4FUC3j36530WKiGzUhpwAXENrSMMqW9Wudfa6ZE0KUfukPn QFMpx54tPeNCgnaJ0g4rh4al6zNJfhPjhCFPmiMyFsl8POrjSPzRsywy/zNVkcDgZObb1FN0HO+ TohE1WBLbfmvkNq7HN1STUUjsEB6GQoB7Sa1jwa87QNzNadYcs0hlnV2CJQ6JrSwDQK2IazIEZa 7pa+7j8Her9ooZHaF/TxB9u2ZxJugiGmR9WpqnmfDXtzZV1XwxxeAEWcWF1AHqPF0gmi4Qs64uf 2S27ptwMOjCR8eWFm/cr4VNklqSjukRuSUQAmVEL+VJEUQ2FLrJt3Qk+6lQB2ipHbEplZ2p262S 1MBtPB3P9ed4htLYmLu4fos8kSG7a8QhUohsQVijC2XkEIjWVHx/46HFO/nflKcXXuPPQJURGNF c3NSk2XzNNeeMzui5og== X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1143,Hydra:6.1.125,FMLib:17.12.100.49 definitions=2026-07-03_01,2026-06-26_01,2025-10-01_01 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 malwarescore=0 lowpriorityscore=0 suspectscore=0 phishscore=0 priorityscore=1501 bulkscore=0 impostorscore=0 spamscore=0 adultscore=0 clxscore=1015 classifier=typeunknown authscore=0 authtc= authcc= route=outbound adjust=0 reason=mlx scancount=1 engine=8.22.0-2606150000 definitions=main-2607030041 On 7/2/2026 4:37 AM, Srinivas Kandagatla wrote: > > On 6/9/26 3:59 AM, Jianping Li wrote: >> Allocating and freeing Audio PD memory from userspace is unsafe because >> the kernel cannot reliably determine when the DSP has finished using the >> memory. Userspace may free buffers while they are still in use by the DSP, >> and remote free requests cannot be safely trusted. >> >> Additionally, the current implementation allows userspace to repeatedly >> grow the Audio PD heap, but does not support shrinking it. This can lead >> to unbounded memory usage over time, effectively causing a memory leak. >> >> Fix this by allocating the entire Audio PD reserved-memory region during >> rpmsg probe and tying its lifetime to the rpmsg channel. This removes >> userspace-controlled alloc/free and ensures that memory is reclaimed only >> when the DSP process is torn down. >> >> Add explicit validation for remote_heap presence and size before sending >> the memory to DSP, and fail early if the reserved-memory region is >> missing or incomplete. >> >> Fixes: 0871561055e66 ("misc: fastrpc: Add support for audiopd") >> Cc: stable@kernel.org >> Signed-off-by: Jianping Li >> --- >> drivers/misc/fastrpc.c | 112 ++++++++++++++++++++++------------------- >> 1 file changed, 59 insertions(+), 53 deletions(-) >> >> diff --git a/drivers/misc/fastrpc.c b/drivers/misc/fastrpc.c >> index 517884000331..1942e74535e5 100644 >> --- a/drivers/misc/fastrpc.c >> +++ b/drivers/misc/fastrpc.c >> @@ -276,6 +276,8 @@ struct fastrpc_channel_ctx { >> struct kref refcount; >> /* Flag if dsp attributes are cached */ >> bool valid_attributes; >> + /* Flag if audio PD init mem was allocated */ >> + bool audio_init_mem; >> u32 dsp_attributes[FASTRPC_MAX_DSP_ATTRIBUTES]; >> struct fastrpc_device *secure_fdevice; >> struct fastrpc_device *fdevice; >> @@ -1341,15 +1343,24 @@ static int fastrpc_init_create_static_process(struct fastrpc_user *fl, >> struct fastrpc_init_create_static init; >> struct fastrpc_invoke_args *args; >> struct fastrpc_phy_page pages[1]; >> + struct fastrpc_channel_ctx *cctx = fl->cctx; >> char *name; >> int err; >> - bool scm_done = false; >> struct { >> int client_id; >> u32 namelen; >> u32 pageslen; >> } inbuf; >> u32 sc; >> + unsigned long flags; >> + >> + if (!cctx->remote_heap || !cctx->remote_heap->dma_addr || >> + !cctx->remote_heap->size) { >> + err = -ENOMEM; >> + dev_err(fl->sctx->dev, >> + "remote heap memory region is not added\n"); >> + return err; >> + } >> >> args = kzalloc_objs(*args, FASTRPC_CREATE_STATIC_PROCESS_NARGS); >> if (!args) >> @@ -1373,31 +1384,6 @@ static int fastrpc_init_create_static_process(struct fastrpc_user *fl, >> inbuf.client_id = fl->client_id; >> inbuf.namelen = init.namelen; >> inbuf.pageslen = 0; >> - if (!fl->cctx->remote_heap) { >> - err = fastrpc_remote_heap_alloc(fl, fl->sctx->dev, init.memlen, >> - &fl->cctx->remote_heap); >> - if (err) >> - goto err_name; >> - >> - /* Map if we have any heap VMIDs associated with this ADSP Static Process. */ >> - if (fl->cctx->vmcount) { >> - u64 src_perms = BIT(QCOM_SCM_VMID_HLOS); >> - >> - err = qcom_scm_assign_mem(fl->cctx->remote_heap->dma_addr, >> - (u64)fl->cctx->remote_heap->size, >> - &src_perms, >> - fl->cctx->vmperms, fl->cctx->vmcount); >> - if (err) { >> - dev_err(fl->sctx->dev, >> - "Failed to assign memory with dma_addr %pad size 0x%llx err %d\n", >> - &fl->cctx->remote_heap->dma_addr, >> - fl->cctx->remote_heap->size, err); >> - goto err_map; >> - } >> - scm_done = true; >> - inbuf.pageslen = 1; >> - } >> - } >> >> fl->pd = USER_PD; >> >> @@ -1409,8 +1395,17 @@ static int fastrpc_init_create_static_process(struct fastrpc_user *fl, >> args[1].length = inbuf.namelen; >> args[1].fd = -1; >> >> - pages[0].addr = fl->cctx->remote_heap->dma_addr; >> - pages[0].size = fl->cctx->remote_heap->size; >> + spin_lock_irqsave(&cctx->lock, flags); >> + if (!cctx->audio_init_mem) { >> + pages[0].addr = cctx->remote_heap->dma_addr; >> + pages[0].size = cctx->remote_heap->size; >> + cctx->audio_init_mem = true; >> + inbuf.pageslen = 1; >> + } else { >> + pages[0].addr = 0; >> + pages[0].size = 0; > What is the expected behavoiur in this case? You're right that this behaviour is subtle and deserves an in-code comment. I'll add one in v9, right above the spin_lock, along the lines of: /* * Audio PD is a static PD and retains the remote heap * information across daemon restarts. Therefore only * the first attach should provide heap information to * DSP. Subsequent attaches reuse the previously * initialized memory pool. */ > >> + } >> + spin_unlock_irqrestore(&cctx->lock, flags); >> >> args[2].ptr = (u64)(uintptr_t) pages; >> args[2].length = sizeof(*pages); >> @@ -1428,27 +1423,7 @@ static int fastrpc_init_create_static_process(struct fastrpc_user *fl, >> >> return 0; >> err_invoke: >> - if (fl->cctx->vmcount && scm_done) { >> - u64 src_perms = 0; >> - struct qcom_scm_vmperm dst_perms; >> - u32 i; >> - >> - for (i = 0; i < fl->cctx->vmcount; i++) >> - src_perms |= BIT(fl->cctx->vmperms[i].vmid); >> - >> - dst_perms.vmid = QCOM_SCM_VMID_HLOS; >> - dst_perms.perm = QCOM_SCM_PERM_RWX; >> - err = qcom_scm_assign_mem(fl->cctx->remote_heap->dma_addr, >> - (u64)fl->cctx->remote_heap->size, >> - &src_perms, &dst_perms, 1); >> - if (err) >> - dev_err(fl->sctx->dev, "Failed to assign memory dma_addr %pad size 0x%llx err %d\n", >> - &fl->cctx->remote_heap->dma_addr, fl->cctx->remote_heap->size, err); >> - } >> -err_map: >> - fastrpc_buf_free(fl->cctx->remote_heap); >> - fl->cctx->remote_heap = NULL; >> -err_name: >> + cctx->audio_init_mem = false; > this can race. Thanks for the review. I'd like to clarify the intent here — please let me know if I'm missing something. The lock is not really there to protect 'audio_init_mem' itself, but to make sure the following is only sent to the DSP once: pages[0].addr = fl->cctx->remote_heap->phys; pages[0].size = fl->cctx->remote_heap->size; The flow I had in mind is: - Thread A enters the critical section, sees audio_init_mem == false, sets it to true, and proceeds to send the pages to the DSP. - If Thread A's invoke fails, we reset audio_init_mem back to false in err_invoke so that a later attempt can retry sending the region. - Once any thread successfully sends the region, audio_init_mem stays true forever and the false branch is never taken again. So the reset on failure is only meant to allow a retry, not to be racy with a concurrent successful path (there can't be one, since only one thread is inside the critical section at a time). Do you see a specific interleaving I've overlooked? If so, I'm happy to switch to a different scheme. > >> kfree(name); >> err: >> kfree(args); >> @@ -2415,12 +2390,23 @@ static int fastrpc_rpmsg_probe(struct rpmsg_device *rpdev) >> } >> } >> >> - if (domain_id == SDSP_DOMAIN_ID) { >> + if (domain_id == SDSP_DOMAIN_ID || domain_id == ADSP_DOMAIN_ID) { >> struct resource res; >> u64 src_perms; >> >> err = of_reserved_mem_region_to_resource(rdev->of_node, 0, &res); >> if (!err) { >> + if (domain_id == ADSP_DOMAIN_ID) { >> + data->remote_heap = >> + kzalloc_obj(*data->remote_heap, GFP_KERNEL); >> + if (!data->remote_heap) { >> + err = -ENOMEM; >> + goto err_free_data; >> + } >> + >> + data->remote_heap->dma_addr = res.start; >> + data->remote_heap->size = resource_size(&res); >> + } >> src_perms = BIT(QCOM_SCM_VMID_HLOS); >> >> err = qcom_scm_assign_mem(res.start, resource_size(&res), &src_perms, >> @@ -2428,7 +2414,6 @@ static int fastrpc_rpmsg_probe(struct rpmsg_device *rpdev) >> if (err) >> goto err_free_data; >> } >> - >> } >> >> secure_dsp = !(of_property_read_bool(rdev->of_node, "qcom,non-secure-domain")); >> @@ -2487,6 +2472,7 @@ static int fastrpc_rpmsg_probe(struct rpmsg_device *rpdev) >> misc_deregister(&data->secure_fdevice->miscdev); >> >> err_free_data: >> + kfree(data->remote_heap); >> kfree(data); >> return err; >> } >> @@ -2509,6 +2495,7 @@ static void fastrpc_rpmsg_remove(struct rpmsg_device *rpdev) >> struct fastrpc_buf *buf, *b; >> struct fastrpc_user *user; >> unsigned long flags; >> + int err; >> >> /* No invocations past this point */ >> spin_lock_irqsave(&cctx->lock, flags); >> @@ -2526,8 +2513,27 @@ static void fastrpc_rpmsg_remove(struct rpmsg_device *rpdev) >> list_for_each_entry_safe(buf, b, &cctx->invoke_interrupted_mmaps, node) >> list_del(&buf->node); >> >> - if (cctx->remote_heap) >> - fastrpc_buf_free(cctx->remote_heap); >> + if (cctx->remote_heap && cctx->vmcount) { >> + u64 src_perms = 0; >> + struct qcom_scm_vmperm dst_perms; >> + >> + for (u32 i = 0; i < cctx->vmcount; i++) >> + src_perms |= BIT(cctx->vmperms[i].vmid); >> + >> + dst_perms.vmid = QCOM_SCM_VMID_HLOS; >> + dst_perms.perm = QCOM_SCM_PERM_RWX; >> + >> + err = qcom_scm_assign_mem(cctx->remote_heap->dma_addr, >> + cctx->remote_heap->size, &src_perms, >> + &dst_perms, 1); >> + if (err) >> + dev_err(&rpdev->dev, >> + "Failed to assign memory back to HLOS: dma_addr %pad size %#llx err %d\n", >> + &cctx->remote_heap->dma_addr, cctx->remote_heap->size, err); >> + } >> + >> + kfree(cctx->remote_heap); >> + cctx->remote_heap = NULL; >> >> of_platform_depopulate(&rpdev->dev); >>