From e2584fa02cbb93b14e4616808cc4e79def172017 Mon Sep 17 00:00:00 2001 From: Kaushal Sanadhya Date: Wed, 29 Nov 2023 23:01:37 +0530 Subject: [PATCH] msm: kgsl: Do not free sharedmem if it cannot be unmapped If sharedmem cannot be unmapped from the mmu, it can still be accessed by the GPU. Therefore it is not safe to free the backing memory. In the case that unmap fails, do not free it or return it to the system. Change-Id: Iad3e86d043f129a4d71cf862865d9033d4a315e3 Signed-off-by: Lynus Vaz Signed-off-by: Kaushal Sanadhya --- drivers/gpu/msm/kgsl_mmu.c | 4 +++- drivers/gpu/msm/kgsl_sharedmem.c | 7 +++++++ 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/msm/kgsl_mmu.c b/drivers/gpu/msm/kgsl_mmu.c index 344814e31d90..9c3afb3b90cc 100644 --- a/drivers/gpu/msm/kgsl_mmu.c +++ b/drivers/gpu/msm/kgsl_mmu.c @@ -1,5 +1,5 @@ /* Copyright (c) 2002,2007-2017,2021, The Linux Foundation. All rights reserved. - * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. + * Copyright (c) 2022-2023, Qualcomm Innovation Center, Inc. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -505,6 +505,8 @@ kgsl_mmu_unmap(struct kgsl_pagetable *pagetable, size = kgsl_memdesc_footprint(memdesc); ret = pagetable->pt_ops->mmu_unmap(pagetable, memdesc); + if (ret) + return ret; atomic_dec(&pagetable->stats.entries); atomic_long_sub(size, &pagetable->stats.mapped); diff --git a/drivers/gpu/msm/kgsl_sharedmem.c b/drivers/gpu/msm/kgsl_sharedmem.c index aa25ee888c96..f6b39dc6c0e3 100644 --- a/drivers/gpu/msm/kgsl_sharedmem.c +++ b/drivers/gpu/msm/kgsl_sharedmem.c @@ -1,4 +1,5 @@ /* Copyright (c) 2002,2007-2021, The Linux Foundation. All rights reserved. + * Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and @@ -479,6 +480,9 @@ done: static void kgsl_page_alloc_free(struct kgsl_memdesc *memdesc) { + if (memdesc->priv & KGSL_MEMDESC_MAPPED) + return; + kgsl_page_alloc_unmap_kernel(memdesc); /* we certainly do not expect the hostptr to still be mapped */ BUG_ON(memdesc->hostptr); @@ -582,6 +586,9 @@ static void kgsl_cma_coherent_free(struct kgsl_memdesc *memdesc) { unsigned long attrs = 0; + if (memdesc->priv & KGSL_MEMDESC_MAPPED) + return; + if (memdesc->hostptr) { if (memdesc->priv & KGSL_MEMDESC_SECURE) { atomic_long_sub(memdesc->size,