summaryrefslogtreecommitdiff
path: root/drivers/gpu/drm/amd/ras
diff options
context:
space:
mode:
authorGangliang Xie <ganglxie@amd.com>2025-12-12 16:15:56 +0800
committerAlex Deucher <alexander.deucher@amd.com>2026-03-02 16:43:40 -0500
commit0d21084c02864fc95df18c5cdd3bab6efafdd406 (patch)
treecf332b8a2efdc526014a04e169ada0023de47cca /drivers/gpu/drm/amd/ras
parent12f4d4482af9271534db8ecaeca1f1a5a4ef3259 (diff)
drm/amd/ras: add wrapper funcs for pmfw eeprom
add wrapper funcs for pmfw eeprom interface to make them easier to be called Signed-off-by: Gangliang Xie <ganglxie@amd.com> Reviewed-by: Tao Zhou <tao.zhou1@amd.com> Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
Diffstat (limited to 'drivers/gpu/drm/amd/ras')
-rw-r--r--drivers/gpu/drm/amd/ras/rascore/ras_eeprom_fw.c125
-rw-r--r--drivers/gpu/drm/amd/ras/rascore/ras_eeprom_fw.h16
2 files changed, 141 insertions, 0 deletions
diff --git a/drivers/gpu/drm/amd/ras/rascore/ras_eeprom_fw.c b/drivers/gpu/drm/amd/ras/rascore/ras_eeprom_fw.c
index e94c368c3159..f880fc49477d 100644
--- a/drivers/gpu/drm/amd/ras/rascore/ras_eeprom_fw.c
+++ b/drivers/gpu/drm/amd/ras/rascore/ras_eeprom_fw.c
@@ -36,3 +36,128 @@ void ras_fw_init_feature_flags(struct ras_core_context *ras_core)
if (!sys_func->mp1_get_ras_enabled_mask(ras_core, &flags))
ras_core->ras_fw_features = flags;
}
+
+bool ras_fw_eeprom_supported(struct ras_core_context *ras_core)
+{
+ return !!(ras_core->ras_fw_features & RAS_CORE_FW_FEATURE_BIT__RAS_EEPROM);
+}
+
+int ras_fw_get_table_version(struct ras_core_context *ras_core,
+ uint32_t *table_version)
+{
+ struct ras_mp1 *mp1 = &ras_core->ras_mp1;
+ const struct ras_mp1_sys_func *sys_func = mp1->sys_func;
+
+ return sys_func->mp1_send_eeprom_msg(ras_core,
+ RAS_SMU_GetRASTableVersion, 0, table_version);
+}
+
+int ras_fw_get_badpage_count(struct ras_core_context *ras_core,
+ uint32_t *count, uint32_t timeout)
+{
+ struct ras_mp1 *mp1 = &ras_core->ras_mp1;
+ const struct ras_mp1_sys_func *sys_func = mp1->sys_func;
+ uint64_t end, now;
+ int ret = 0;
+
+ now = (uint64_t)ktime_to_ms(ktime_get());
+ end = now + timeout;
+
+ do {
+ ret = sys_func->mp1_send_eeprom_msg(ras_core,
+ RAS_SMU_GetBadPageCount, 0, count);
+ /* eeprom is not ready */
+ if (ret != -EBUSY)
+ return ret;
+
+ mdelay(10);
+ now = (uint64_t)ktime_to_ms(ktime_get());
+ } while (now < end);
+
+ RAS_DEV_ERR(ras_core->dev,
+ "smu get bad page count timeout!\n");
+ return ret;
+}
+
+int ras_fw_get_badpage_mca_addr(struct ras_core_context *ras_core,
+ uint16_t index, uint64_t *mca_addr)
+{
+ struct ras_mp1 *mp1 = &ras_core->ras_mp1;
+ const struct ras_mp1_sys_func *sys_func = mp1->sys_func;
+ uint32_t temp_arg, temp_addr_lo, temp_addr_high;
+ int ret;
+
+ temp_arg = index | (1 << 16);
+ ret = sys_func->mp1_send_eeprom_msg(ras_core,
+ RAS_SMU_GetBadPageMcaAddr, temp_arg, &temp_addr_lo);
+ if (ret)
+ return ret;
+
+ temp_arg = index | (2 << 16);
+ ret = sys_func->mp1_send_eeprom_msg(ras_core,
+ RAS_SMU_GetBadPageMcaAddr, temp_arg, &temp_addr_high);
+
+ if (!ret)
+ *mca_addr = (uint64_t)temp_addr_high << 32 | temp_addr_lo;
+
+ return ret;
+}
+
+int ras_fw_set_timestamp(struct ras_core_context *ras_core,
+ uint64_t timestamp)
+{
+ struct ras_mp1 *mp1 = &ras_core->ras_mp1;
+ const struct ras_mp1_sys_func *sys_func = mp1->sys_func;
+
+ return sys_func->mp1_send_eeprom_msg(ras_core,
+ RAS_SMU_SetTimestamp, (uint32_t)timestamp, 0);
+}
+
+int ras_fw_get_timestamp(struct ras_core_context *ras_core,
+ uint16_t index, uint64_t *timestamp)
+{
+ struct ras_mp1 *mp1 = &ras_core->ras_mp1;
+ const struct ras_mp1_sys_func *sys_func = mp1->sys_func;
+ uint32_t temp = 0;
+ int ret;
+
+ ret = sys_func->mp1_send_eeprom_msg(ras_core,
+ RAS_SMU_GetTimestamp, index, &temp);
+ if (!ret)
+ *timestamp = temp;
+
+ return ret;
+}
+
+int ras_fw_get_badpage_ipid(struct ras_core_context *ras_core,
+ uint16_t index, uint64_t *ipid)
+{
+ struct ras_mp1 *mp1 = &ras_core->ras_mp1;
+ const struct ras_mp1_sys_func *sys_func = mp1->sys_func;
+ uint32_t temp_arg, temp_ipid_lo, temp_ipid_high;
+ int ret;
+
+ temp_arg = index | (1 << 16);
+ ret = sys_func->mp1_send_eeprom_msg(ras_core,
+ RAS_SMU_GetBadPageIpid, temp_arg, &temp_ipid_lo);
+ if (ret)
+ return ret;
+
+ temp_arg = index | (2 << 16);
+ ret = sys_func->mp1_send_eeprom_msg(ras_core,
+ RAS_SMU_GetBadPageIpid, temp_arg, &temp_ipid_high);
+ if (!ret)
+ *ipid = (uint64_t)temp_ipid_high << 32 | temp_ipid_lo;
+
+ return ret;
+}
+
+int ras_fw_erase_ras_table(struct ras_core_context *ras_core,
+ uint32_t *result)
+{
+ struct ras_mp1 *mp1 = &ras_core->ras_mp1;
+ const struct ras_mp1_sys_func *sys_func = mp1->sys_func;
+
+ return sys_func->mp1_send_eeprom_msg(ras_core,
+ RAS_SMU_EraseRasTable, 0, result);
+}
diff --git a/drivers/gpu/drm/amd/ras/rascore/ras_eeprom_fw.h b/drivers/gpu/drm/amd/ras/rascore/ras_eeprom_fw.h
index b41665467368..46f45e82a3f3 100644
--- a/drivers/gpu/drm/amd/ras/rascore/ras_eeprom_fw.h
+++ b/drivers/gpu/drm/amd/ras/rascore/ras_eeprom_fw.h
@@ -24,6 +24,22 @@
#ifndef __RAS_EEPROM_FW_H__
#define __RAS_EEPROM_FW_H__
+
void ras_fw_init_feature_flags(struct ras_core_context *ras_core);
+bool ras_fw_eeprom_supported(struct ras_core_context *ras_core);
+int ras_fw_get_table_version(struct ras_core_context *ras_core,
+ uint32_t *table_version);
+int ras_fw_get_badpage_count(struct ras_core_context *ras_core,
+ uint32_t *count, uint32_t timeout);
+int ras_fw_get_badpage_mca_addr(struct ras_core_context *ras_core,
+ uint16_t index, uint64_t *mca_addr);
+int ras_fw_set_timestamp(struct ras_core_context *ras_core,
+ uint64_t timestamp);
+int ras_fw_get_timestamp(struct ras_core_context *ras_core,
+ uint16_t index, uint64_t *timestamp);
+int ras_fw_get_badpage_ipid(struct ras_core_context *ras_core,
+ uint16_t index, uint64_t *ipid);
+int ras_fw_erase_ras_table(struct ras_core_context *ras_core,
+ uint32_t *result);
#endif