Commit dfc53681 authored by Likun Gao's avatar Likun Gao Committed by Alex Deucher

drm/amdgpu: add sysfs to shows psp vbflash status

Add new sysfs interface to shows the status of psp vbflash status.

V2: rename the sysfs interface, and set more return value.
    (0: not start; 1: in progress; MBX115 value when vbflash finish)
V3: warning fixes
Signed-off-by: default avatarLikun Gao <Likun.Gao@amd.com>
Reviewed-by: default avatarHawking Zhang <Hawking.Zhang@amd.com>
Signed-off-by: default avatarAlex Deucher <alexander.deucher@amd.com>
parent 8424f2cc
...@@ -3453,6 +3453,8 @@ static ssize_t amdgpu_psp_vbflash_write(struct file *filp, struct kobject *kobj, ...@@ -3453,6 +3453,8 @@ static ssize_t amdgpu_psp_vbflash_write(struct file *filp, struct kobject *kobj,
struct drm_device *ddev = dev_get_drvdata(dev); struct drm_device *ddev = dev_get_drvdata(dev);
struct amdgpu_device *adev = drm_to_adev(ddev); struct amdgpu_device *adev = drm_to_adev(ddev);
adev->psp.vbflash_done = false;
/* Safeguard against memory drain */ /* Safeguard against memory drain */
if (adev->psp.vbflash_image_size > AMD_VBIOS_FILE_MAX_SIZE_B) { if (adev->psp.vbflash_image_size > AMD_VBIOS_FILE_MAX_SIZE_B) {
dev_err(adev->dev, "File size cannot exceed %u", AMD_VBIOS_FILE_MAX_SIZE_B); dev_err(adev->dev, "File size cannot exceed %u", AMD_VBIOS_FILE_MAX_SIZE_B);
...@@ -3524,6 +3526,23 @@ static ssize_t amdgpu_psp_vbflash_read(struct file *filp, struct kobject *kobj, ...@@ -3524,6 +3526,23 @@ static ssize_t amdgpu_psp_vbflash_read(struct file *filp, struct kobject *kobj,
return 0; return 0;
} }
static ssize_t amdgpu_psp_vbflash_status(struct device *dev,
struct device_attribute *attr,
char *buf)
{
struct drm_device *ddev = dev_get_drvdata(dev);
struct amdgpu_device *adev = drm_to_adev(ddev);
uint32_t vbflash_status;
vbflash_status = psp_vbflash_status(&adev->psp);
if (!adev->psp.vbflash_done)
vbflash_status = 0;
else if (adev->psp.vbflash_done && !(vbflash_status & 0x80000000))
vbflash_status = 1;
return sysfs_emit(buf, "0x%x\n", vbflash_status);
}
static const struct bin_attribute psp_vbflash_bin_attr = { static const struct bin_attribute psp_vbflash_bin_attr = {
.attr = {.name = "psp_vbflash", .mode = 0664}, .attr = {.name = "psp_vbflash", .mode = 0664},
.size = 0, .size = 0,
...@@ -3531,6 +3550,8 @@ static const struct bin_attribute psp_vbflash_bin_attr = { ...@@ -3531,6 +3550,8 @@ static const struct bin_attribute psp_vbflash_bin_attr = {
.read = amdgpu_psp_vbflash_read, .read = amdgpu_psp_vbflash_read,
}; };
static DEVICE_ATTR(psp_vbflash_status, 0444, amdgpu_psp_vbflash_status, NULL);
int amdgpu_psp_sysfs_init(struct amdgpu_device *adev) int amdgpu_psp_sysfs_init(struct amdgpu_device *adev)
{ {
int ret = 0; int ret = 0;
...@@ -3549,6 +3570,9 @@ int amdgpu_psp_sysfs_init(struct amdgpu_device *adev) ...@@ -3549,6 +3570,9 @@ int amdgpu_psp_sysfs_init(struct amdgpu_device *adev)
ret = sysfs_create_bin_file(&adev->dev->kobj, &psp_vbflash_bin_attr); ret = sysfs_create_bin_file(&adev->dev->kobj, &psp_vbflash_bin_attr);
if (ret) if (ret)
dev_err(adev->dev, "Failed to create device file psp_vbflash"); dev_err(adev->dev, "Failed to create device file psp_vbflash");
ret = device_create_file(adev->dev, &dev_attr_psp_vbflash_status);
if (ret)
dev_err(adev->dev, "Failed to create device file psp_vbflash_status");
return ret; return ret;
default: default:
return 0; return 0;
...@@ -3586,6 +3610,7 @@ static int psp_sysfs_init(struct amdgpu_device *adev) ...@@ -3586,6 +3610,7 @@ static int psp_sysfs_init(struct amdgpu_device *adev)
void amdgpu_psp_sysfs_fini(struct amdgpu_device *adev) void amdgpu_psp_sysfs_fini(struct amdgpu_device *adev)
{ {
sysfs_remove_bin_file(&adev->dev->kobj, &psp_vbflash_bin_attr); sysfs_remove_bin_file(&adev->dev->kobj, &psp_vbflash_bin_attr);
device_remove_file(adev->dev, &dev_attr_psp_vbflash_status);
} }
static void psp_sysfs_fini(struct amdgpu_device *adev) static void psp_sysfs_fini(struct amdgpu_device *adev)
......
...@@ -130,6 +130,7 @@ struct psp_funcs ...@@ -130,6 +130,7 @@ struct psp_funcs
int (*load_usbc_pd_fw)(struct psp_context *psp, uint64_t fw_pri_mc_addr); int (*load_usbc_pd_fw)(struct psp_context *psp, uint64_t fw_pri_mc_addr);
int (*read_usbc_pd_fw)(struct psp_context *psp, uint32_t *fw_ver); int (*read_usbc_pd_fw)(struct psp_context *psp, uint32_t *fw_ver);
int (*update_spirom)(struct psp_context *psp, uint64_t fw_pri_mc_addr); int (*update_spirom)(struct psp_context *psp, uint64_t fw_pri_mc_addr);
int (*vbflash_stat)(struct psp_context *psp);
}; };
#define AMDGPU_XGMI_MAX_CONNECTED_NODES 64 #define AMDGPU_XGMI_MAX_CONNECTED_NODES 64
...@@ -375,6 +376,7 @@ struct psp_context ...@@ -375,6 +376,7 @@ struct psp_context
char *vbflash_tmp_buf; char *vbflash_tmp_buf;
size_t vbflash_image_size; size_t vbflash_image_size;
bool vbflash_done;
}; };
struct amdgpu_psp_funcs { struct amdgpu_psp_funcs {
...@@ -425,6 +427,10 @@ struct amdgpu_psp_funcs { ...@@ -425,6 +427,10 @@ struct amdgpu_psp_funcs {
((psp)->funcs->update_spirom ? \ ((psp)->funcs->update_spirom ? \
(psp)->funcs->update_spirom((psp), fw_pri_mc_addr) : -EINVAL) (psp)->funcs->update_spirom((psp), fw_pri_mc_addr) : -EINVAL)
#define psp_vbflash_status(psp) \
((psp)->funcs->vbflash_stat ? \
(psp)->funcs->vbflash_stat((psp)) : -EINVAL)
extern const struct amd_ip_funcs psp_ip_funcs; extern const struct amd_ip_funcs psp_ip_funcs;
extern const struct amdgpu_ip_block_version psp_v3_1_ip_block; extern const struct amdgpu_ip_block_version psp_v3_1_ip_block;
......
...@@ -487,6 +487,9 @@ static int psp_v13_0_exec_spi_cmd(struct psp_context *psp, int cmd) ...@@ -487,6 +487,9 @@ static int psp_v13_0_exec_spi_cmd(struct psp_context *psp, int cmd)
/* Ring the doorbell */ /* Ring the doorbell */
WREG32_SOC15(MP0, 0, regMP0_SMN_C2PMSG_73, 1); WREG32_SOC15(MP0, 0, regMP0_SMN_C2PMSG_73, 1);
if (cmd == C2PMSG_CMD_SPI_UPDATE_FLASH_IMAGE)
return 0;
ret = psp_wait_for(psp, SOC15_REG_OFFSET(MP0, 0, regMP0_SMN_C2PMSG_115), ret = psp_wait_for(psp, SOC15_REG_OFFSET(MP0, 0, regMP0_SMN_C2PMSG_115),
MBOX_READY_FLAG, MBOX_READY_MASK, false); MBOX_READY_FLAG, MBOX_READY_MASK, false);
if (ret) { if (ret) {
...@@ -504,7 +507,8 @@ static int psp_v13_0_exec_spi_cmd(struct psp_context *psp, int cmd) ...@@ -504,7 +507,8 @@ static int psp_v13_0_exec_spi_cmd(struct psp_context *psp, int cmd)
return 0; return 0;
} }
int psp_v13_0_update_spirom(struct psp_context *psp, uint64_t fw_pri_mc_addr) static int psp_v13_0_update_spirom(struct psp_context *psp,
uint64_t fw_pri_mc_addr)
{ {
struct amdgpu_device *adev = psp->adev; struct amdgpu_device *adev = psp->adev;
int ret; int ret;
...@@ -529,6 +533,8 @@ int psp_v13_0_update_spirom(struct psp_context *psp, uint64_t fw_pri_mc_addr) ...@@ -529,6 +533,8 @@ int psp_v13_0_update_spirom(struct psp_context *psp, uint64_t fw_pri_mc_addr)
if (ret) if (ret)
return ret; return ret;
psp->vbflash_done = true;
ret = psp_v13_0_exec_spi_cmd(psp, C2PMSG_CMD_SPI_UPDATE_FLASH_IMAGE); ret = psp_v13_0_exec_spi_cmd(psp, C2PMSG_CMD_SPI_UPDATE_FLASH_IMAGE);
if (ret) if (ret)
return ret; return ret;
...@@ -536,6 +542,13 @@ int psp_v13_0_update_spirom(struct psp_context *psp, uint64_t fw_pri_mc_addr) ...@@ -536,6 +542,13 @@ int psp_v13_0_update_spirom(struct psp_context *psp, uint64_t fw_pri_mc_addr)
return 0; return 0;
} }
static int psp_v13_0_vbflash_status(struct psp_context *psp)
{
struct amdgpu_device *adev = psp->adev;
return RREG32_SOC15(MP0, 0, regMP0_SMN_C2PMSG_115);
}
static const struct psp_funcs psp_v13_0_funcs = { static const struct psp_funcs psp_v13_0_funcs = {
.init_microcode = psp_v13_0_init_microcode, .init_microcode = psp_v13_0_init_microcode,
.bootloader_load_kdb = psp_v13_0_bootloader_load_kdb, .bootloader_load_kdb = psp_v13_0_bootloader_load_kdb,
...@@ -553,7 +566,8 @@ static const struct psp_funcs psp_v13_0_funcs = { ...@@ -553,7 +566,8 @@ static const struct psp_funcs psp_v13_0_funcs = {
.ring_set_wptr = psp_v13_0_ring_set_wptr, .ring_set_wptr = psp_v13_0_ring_set_wptr,
.load_usbc_pd_fw = psp_v13_0_load_usbc_pd_fw, .load_usbc_pd_fw = psp_v13_0_load_usbc_pd_fw,
.read_usbc_pd_fw = psp_v13_0_read_usbc_pd_fw, .read_usbc_pd_fw = psp_v13_0_read_usbc_pd_fw,
.update_spirom = psp_v13_0_update_spirom .update_spirom = psp_v13_0_update_spirom,
.vbflash_stat = psp_v13_0_vbflash_status
}; };
void psp_v13_0_set_psp_funcs(struct psp_context *psp) void psp_v13_0_set_psp_funcs(struct psp_context *psp)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment