soc: qcom: mdt-loader: Return relocation base
In order to implement support for grabbing core dumps in remoteproc it's necessary to know the relocated base of the image, as the offsets from the virtual memory base might not be based on the physical address. Return the adjusted physical base address to the caller. Acked-by: Andy Gross <andy.gross@linaro.org> Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org>
This commit is contained in:
Родитель
c1d35c1ab4
Коммит
4dd27f544c
|
@ -89,14 +89,14 @@ static int zap_shader_load_mdt(struct msm_gpu *gpu, const char *fwname)
|
||||||
*/
|
*/
|
||||||
if (to_adreno_gpu(gpu)->fwloc == FW_LOCATION_LEGACY) {
|
if (to_adreno_gpu(gpu)->fwloc == FW_LOCATION_LEGACY) {
|
||||||
ret = qcom_mdt_load(dev, fw, fwname, GPU_PAS_ID,
|
ret = qcom_mdt_load(dev, fw, fwname, GPU_PAS_ID,
|
||||||
mem_region, mem_phys, mem_size);
|
mem_region, mem_phys, mem_size, NULL);
|
||||||
} else {
|
} else {
|
||||||
char newname[strlen("qcom/") + strlen(fwname) + 1];
|
char newname[strlen("qcom/") + strlen(fwname) + 1];
|
||||||
|
|
||||||
sprintf(newname, "qcom/%s", fwname);
|
sprintf(newname, "qcom/%s", fwname);
|
||||||
|
|
||||||
ret = qcom_mdt_load(dev, fw, newname, GPU_PAS_ID,
|
ret = qcom_mdt_load(dev, fw, newname, GPU_PAS_ID,
|
||||||
mem_region, mem_phys, mem_size);
|
mem_region, mem_phys, mem_size, NULL);
|
||||||
}
|
}
|
||||||
if (ret)
|
if (ret)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
|
@ -76,7 +76,7 @@ int venus_boot(struct device *dev, const char *fwname)
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = qcom_mdt_load(dev, mdt, fwname, VENUS_PAS_ID, mem_va, mem_phys,
|
ret = qcom_mdt_load(dev, mdt, fwname, VENUS_PAS_ID, mem_va, mem_phys,
|
||||||
mem_size);
|
mem_size, NULL);
|
||||||
|
|
||||||
release_firmware(mdt);
|
release_firmware(mdt);
|
||||||
|
|
||||||
|
|
|
@ -82,7 +82,9 @@ static int adsp_load(struct rproc *rproc, const struct firmware *fw)
|
||||||
struct qcom_adsp *adsp = (struct qcom_adsp *)rproc->priv;
|
struct qcom_adsp *adsp = (struct qcom_adsp *)rproc->priv;
|
||||||
|
|
||||||
return qcom_mdt_load(adsp->dev, fw, rproc->firmware, adsp->pas_id,
|
return qcom_mdt_load(adsp->dev, fw, rproc->firmware, adsp->pas_id,
|
||||||
adsp->mem_region, adsp->mem_phys, adsp->mem_size);
|
adsp->mem_region, adsp->mem_phys, adsp->mem_size,
|
||||||
|
&adsp->mem_reloc);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static int adsp_start(struct rproc *rproc)
|
static int adsp_start(struct rproc *rproc)
|
||||||
|
|
|
@ -153,7 +153,8 @@ static int wcnss_load(struct rproc *rproc, const struct firmware *fw)
|
||||||
struct qcom_wcnss *wcnss = (struct qcom_wcnss *)rproc->priv;
|
struct qcom_wcnss *wcnss = (struct qcom_wcnss *)rproc->priv;
|
||||||
|
|
||||||
return qcom_mdt_load(wcnss->dev, fw, rproc->firmware, WCNSS_PAS_ID,
|
return qcom_mdt_load(wcnss->dev, fw, rproc->firmware, WCNSS_PAS_ID,
|
||||||
wcnss->mem_region, wcnss->mem_phys, wcnss->mem_size);
|
wcnss->mem_region, wcnss->mem_phys,
|
||||||
|
wcnss->mem_size, &wcnss->mem_reloc);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void wcnss_indicate_nv_download(struct qcom_wcnss *wcnss)
|
static void wcnss_indicate_nv_download(struct qcom_wcnss *wcnss)
|
||||||
|
|
|
@ -83,12 +83,14 @@ EXPORT_SYMBOL_GPL(qcom_mdt_get_size);
|
||||||
* @mem_region: allocated memory region to load firmware into
|
* @mem_region: allocated memory region to load firmware into
|
||||||
* @mem_phys: physical address of allocated memory region
|
* @mem_phys: physical address of allocated memory region
|
||||||
* @mem_size: size of the allocated memory region
|
* @mem_size: size of the allocated memory region
|
||||||
|
* @reloc_base: adjusted physical address after relocation
|
||||||
*
|
*
|
||||||
* Returns 0 on success, negative errno otherwise.
|
* Returns 0 on success, negative errno otherwise.
|
||||||
*/
|
*/
|
||||||
int qcom_mdt_load(struct device *dev, const struct firmware *fw,
|
int qcom_mdt_load(struct device *dev, const struct firmware *fw,
|
||||||
const char *firmware, int pas_id, void *mem_region,
|
const char *firmware, int pas_id, void *mem_region,
|
||||||
phys_addr_t mem_phys, size_t mem_size)
|
phys_addr_t mem_phys, size_t mem_size,
|
||||||
|
phys_addr_t *reloc_base)
|
||||||
{
|
{
|
||||||
const struct elf32_phdr *phdrs;
|
const struct elf32_phdr *phdrs;
|
||||||
const struct elf32_phdr *phdr;
|
const struct elf32_phdr *phdr;
|
||||||
|
@ -192,6 +194,9 @@ int qcom_mdt_load(struct device *dev, const struct firmware *fw,
|
||||||
memset(ptr + phdr->p_filesz, 0, phdr->p_memsz - phdr->p_filesz);
|
memset(ptr + phdr->p_filesz, 0, phdr->p_memsz - phdr->p_filesz);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (reloc_base)
|
||||||
|
*reloc_base = mem_reloc;
|
||||||
|
|
||||||
out:
|
out:
|
||||||
kfree(fw_name);
|
kfree(fw_name);
|
||||||
|
|
||||||
|
|
|
@ -14,6 +14,7 @@ struct firmware;
|
||||||
ssize_t qcom_mdt_get_size(const struct firmware *fw);
|
ssize_t qcom_mdt_get_size(const struct firmware *fw);
|
||||||
int qcom_mdt_load(struct device *dev, const struct firmware *fw,
|
int qcom_mdt_load(struct device *dev, const struct firmware *fw,
|
||||||
const char *fw_name, int pas_id, void *mem_region,
|
const char *fw_name, int pas_id, void *mem_region,
|
||||||
phys_addr_t mem_phys, size_t mem_size);
|
phys_addr_t mem_phys, size_t mem_size,
|
||||||
|
phys_addr_t *reloc_base);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
Загрузка…
Ссылка в новой задаче