hash_index is evaluated by looping phdrs till QCOM_MDT_TYPE_HASH is found. Add an upperbound check to phdrs to access within elf size.
Fixes: 64fb5eb87d58 ("soc: qcom: mdt_loader: Allow hash to reside in any segment") Cc: stable@vger.kernel.org Signed-off-by: Auditya Bhattaram quic_audityab@quicinc.com Acked-by: Mukesh Ojha quic_mojha@quicinc.com --- Changes in v4: - Added additional prints incase of Invalid access. Link to v3 https://lore.kernel.org/stable/1c91c653-cebe-4407-bdd6-cfc73b64c0fb@quicinc.... Link to v2 https://lore.kernel.org/linux-arm-msm/9773d189-c896-d5c5-804c-e086c24987b4@q... Link to v1 https://lore.kernel.org/linux-arm-msm/5d7a3b97-d840-4863-91a0-32c1d8e7532f@l... --- drivers/soc/qcom/mdt_loader.c | 7 +++++++ 1 file changed, 7 insertions(+)
diff --git a/drivers/soc/qcom/mdt_loader.c b/drivers/soc/qcom/mdt_loader.c index 6f177e46fa0f..1a79a7bba468 100644 --- a/drivers/soc/qcom/mdt_loader.c +++ b/drivers/soc/qcom/mdt_loader.c @@ -145,6 +143,13 @@ void *qcom_mdt_read_metadata(const struct firmware *fw, size_t *data_len, if (phdrs[0].p_type == PT_LOAD) return ERR_PTR(-EINVAL);
+ if (((size_t)(phdrs + ehdr->e_phnum)) > ((size_t)ehdr + fw->size)) { + dev_err(dev, + "Invalid phdrs access for fw: %s, e_phnum: %u, fw->size: %zu\n", + fw_name, ehdr->e_phnum, fw->size); + return ERR_PTR(-EINVAL); + } + for (i = 1; i < ehdr->e_phnum; i++) { if ((phdrs[i].p_flags & QCOM_MDT_TYPE_MASK) == QCOM_MDT_TYPE_HASH) { hash_segment = i; -- 2.17.1