Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 2b0c3aee authored by Huang Rui's avatar Huang Rui Committed by Alex Deucher
Browse files

drm/amdgpu: use private memory to store psp firmware data



Rework in order to properly support suspend.

Signed-off-by: default avatarHuang Rui <ray.huang@amd.com>
Reviewed-by: default avatarAlex Deucher <alexander.deucher@amd.com>
Signed-off-by: default avatarAlex Deucher <alexander.deucher@amd.com>
parent 53a5cf57
Loading
Loading
Loading
Loading
+8 −20
Original line number Diff line number Diff line
@@ -209,9 +209,9 @@ static void psp_prep_asd_cmd_buf(struct psp_gfx_cmd_resp *cmd,
static int psp_asd_load(struct psp_context *psp)
{
	int ret;
	struct amdgpu_bo *asd_bo, *asd_shared_bo;
	uint64_t asd_mc_addr, asd_shared_mc_addr;
	void *asd_buf, *asd_shared_buf;
	struct amdgpu_bo *asd_shared_bo;
	uint64_t asd_shared_mc_addr;
	void *asd_shared_buf;
	struct psp_gfx_cmd_resp *cmd;

	cmd = kzalloc(sizeof(struct psp_gfx_cmd_resp), GFP_KERNEL);
@@ -224,38 +224,26 @@ static int psp_asd_load(struct psp_context *psp)
	 */
	ret = amdgpu_bo_create_kernel(psp->adev, PSP_ASD_SHARED_MEM_SIZE, PAGE_SIZE,
				      AMDGPU_GEM_DOMAIN_VRAM,
				      &asd_shared_bo, &asd_shared_mc_addr, &asd_buf);
				      &asd_shared_bo, &asd_shared_mc_addr, &asd_shared_buf);
	if (ret)
		goto failed;

	/*
	 * Allocate 256k memory aligned to 4k from Frame Buffer (local
	 * physical) for ASD firmware
	 */
	ret = amdgpu_bo_create_kernel(psp->adev, PSP_ASD_BIN_SIZE, PAGE_SIZE,
				      AMDGPU_GEM_DOMAIN_VRAM,
				      &asd_bo, &asd_mc_addr, &asd_buf);
	if (ret)
		goto failed_mem;
	memset(psp->fw_pri_buf, 0, PSP_1_MEG);
	memcpy(psp->fw_pri_buf, psp->asd_start_addr, psp->asd_ucode_size);

	memcpy(asd_buf, psp->asd_start_addr, psp->asd_ucode_size);

	psp_prep_asd_cmd_buf(cmd, asd_mc_addr, asd_shared_mc_addr,
	psp_prep_asd_cmd_buf(cmd, psp->fw_pri_mc_addr, asd_shared_mc_addr,
			     psp->asd_ucode_size, PSP_ASD_SHARED_MEM_SIZE);

	ret = psp_cmd_submit_buf(psp, NULL, cmd,
				 psp->fence_buf_mc_addr, 2);
	if (ret)
		goto failed_mem1;
		goto failed_mem;

	amdgpu_bo_free_kernel(&asd_bo, &asd_mc_addr, &asd_buf);
	amdgpu_bo_free_kernel(&asd_shared_bo, &asd_shared_mc_addr, &asd_shared_buf);
	kfree(cmd);

	return 0;

failed_mem1:
	amdgpu_bo_free_kernel(&asd_bo, &asd_mc_addr, &asd_buf);
failed_mem:
	amdgpu_bo_free_kernel(&asd_shared_bo, &asd_shared_mc_addr, &asd_shared_buf);
failed:
+0 −1
Original line number Diff line number Diff line
@@ -30,7 +30,6 @@

#define PSP_FENCE_BUFFER_SIZE	0x1000
#define PSP_CMD_BUFFER_SIZE	0x1000
#define PSP_ASD_BIN_SIZE	0x40000
#define PSP_ASD_SHARED_MEM_SIZE	0x4000
#define PSP_1_MEG		0x100000

+8 −40
Original line number Diff line number Diff line
@@ -166,11 +166,8 @@ int psp_v3_1_bootloader_load_sysdrv(struct psp_context *psp)
{
	int ret;
	uint32_t psp_gfxdrv_command_reg = 0;
	struct amdgpu_bo *psp_sysdrv;
	void *psp_sysdrv_virt = NULL;
	uint64_t psp_sysdrv_mem;
	struct amdgpu_device *adev = psp->adev;
	uint32_t size, sol_reg;
	uint32_t sol_reg;

	/* Check sOS sign of life register to confirm sys driver and sOS
	 * are already been loaded.
@@ -185,27 +182,14 @@ int psp_v3_1_bootloader_load_sysdrv(struct psp_context *psp)
	if (ret)
		return ret;

	/*
	 * Create a 1 meg GART memory to store the psp sys driver
	 * binary with a 1 meg aligned address
	 */
	size = (psp->sys_bin_size + (PSP_BOOTLOADER_1_MEG_ALIGNMENT - 1)) &
		(~(PSP_BOOTLOADER_1_MEG_ALIGNMENT - 1));

	ret = amdgpu_bo_create_kernel(adev, size, PSP_BOOTLOADER_1_MEG_ALIGNMENT,
				      AMDGPU_GEM_DOMAIN_GTT,
				      &psp_sysdrv,
				      &psp_sysdrv_mem,
				      &psp_sysdrv_virt);
	if (ret)
		return ret;
	memset(psp->fw_pri_buf, 0, PSP_1_MEG);

	/* Copy PSP System Driver binary to memory */
	memcpy(psp_sysdrv_virt, psp->sys_start_addr, psp->sys_bin_size);
	memcpy(psp->fw_pri_buf, psp->sys_start_addr, psp->sys_bin_size);

	/* Provide the sys driver to bootrom */
	WREG32(SOC15_REG_OFFSET(MP0, 0, mmMP0_SMN_C2PMSG_36),
	       (uint32_t)(psp_sysdrv_mem >> 20));
	       (uint32_t)(psp->fw_pri_mc_addr >> 20));
	psp_gfxdrv_command_reg = 1 << 16;
	WREG32(SOC15_REG_OFFSET(MP0, 0, mmMP0_SMN_C2PMSG_35),
	       psp_gfxdrv_command_reg);
@@ -216,8 +200,6 @@ int psp_v3_1_bootloader_load_sysdrv(struct psp_context *psp)
	ret = psp_wait_for(psp, SOC15_REG_OFFSET(MP0, 0, mmMP0_SMN_C2PMSG_35),
			   0x80000000, 0x80000000, false);

	amdgpu_bo_free_kernel(&psp_sysdrv, &psp_sysdrv_mem, &psp_sysdrv_virt);

	return ret;
}

@@ -225,11 +207,8 @@ int psp_v3_1_bootloader_load_sos(struct psp_context *psp)
{
	int ret;
	unsigned int psp_gfxdrv_command_reg = 0;
	struct amdgpu_bo *psp_sos;
	void *psp_sos_virt = NULL;
	uint64_t psp_sos_mem;
	struct amdgpu_device *adev = psp->adev;
	uint32_t size, sol_reg;
	uint32_t sol_reg;

	/* Check sOS sign of life register to confirm sys driver and sOS
	 * are already been loaded.
@@ -244,23 +223,14 @@ int psp_v3_1_bootloader_load_sos(struct psp_context *psp)
	if (ret)
		return ret;

	size = (psp->sos_bin_size + (PSP_BOOTLOADER_1_MEG_ALIGNMENT - 1)) &
		(~((uint64_t)PSP_BOOTLOADER_1_MEG_ALIGNMENT - 1));

	ret = amdgpu_bo_create_kernel(adev, size, PSP_BOOTLOADER_1_MEG_ALIGNMENT,
				      AMDGPU_GEM_DOMAIN_GTT,
				      &psp_sos,
				      &psp_sos_mem,
				      &psp_sos_virt);
	if (ret)
		return ret;
	memset(psp->fw_pri_buf, 0, PSP_1_MEG);

	/* Copy Secure OS binary to PSP memory */
	memcpy(psp_sos_virt, psp->sos_start_addr, psp->sos_bin_size);
	memcpy(psp->fw_pri_buf, psp->sos_start_addr, psp->sos_bin_size);

	/* Provide the PSP secure OS to bootrom */
	WREG32(SOC15_REG_OFFSET(MP0, 0, mmMP0_SMN_C2PMSG_36),
	       (uint32_t)(psp_sos_mem >> 20));
	       (uint32_t)(psp->fw_pri_mc_addr >> 20));
	psp_gfxdrv_command_reg = 2 << 16;
	WREG32(SOC15_REG_OFFSET(MP0, 0, mmMP0_SMN_C2PMSG_35),
	       psp_gfxdrv_command_reg);
@@ -273,8 +243,6 @@ int psp_v3_1_bootloader_load_sos(struct psp_context *psp)
			   0, true);
#endif

	amdgpu_bo_free_kernel(&psp_sos, &psp_sos_mem, &psp_sos_virt);

	return ret;
}