drm/amdgpu: Move EEPROM I2C adapter to amdgpu_device
Puts the i2c adapter in common place for sharing by RAS and upcoming data read from FRU EEPROM feature. v2: Move i2c adapter to amdgpu_pm and rename it. v3: Move i2c adapter init to ASIC specific code and get rid of the switch case in amdgpu_device Signed-off-by: Andrey Grodzovsky <andrey.grodzovsky@amd.com> Reviewed-by: Alex Deucher <alexander.deucher@amd.com> Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
This commit is contained in:
Родитель
57210c19e4
Коммит
9015d60c9e
|
@ -448,6 +448,8 @@ struct amdgpu_pm {
|
||||||
/* powerplay feature */
|
/* powerplay feature */
|
||||||
uint32_t pp_feature;
|
uint32_t pp_feature;
|
||||||
|
|
||||||
|
/* Used for I2C access to various EEPROMs on relevant ASICs */
|
||||||
|
struct i2c_adapter smu_i2c;
|
||||||
};
|
};
|
||||||
|
|
||||||
#define R600_SSTU_DFLT 0
|
#define R600_SSTU_DFLT 0
|
||||||
|
|
|
@ -25,7 +25,6 @@
|
||||||
#include "amdgpu.h"
|
#include "amdgpu.h"
|
||||||
#include "amdgpu_ras.h"
|
#include "amdgpu_ras.h"
|
||||||
#include <linux/bits.h>
|
#include <linux/bits.h>
|
||||||
#include "smu_v11_0_i2c.h"
|
|
||||||
#include "atom.h"
|
#include "atom.h"
|
||||||
|
|
||||||
#define EEPROM_I2C_TARGET_ADDR_VEGA20 0xA0
|
#define EEPROM_I2C_TARGET_ADDR_VEGA20 0xA0
|
||||||
|
@ -124,6 +123,7 @@ static int __update_table_header(struct amdgpu_ras_eeprom_control *control,
|
||||||
unsigned char *buff)
|
unsigned char *buff)
|
||||||
{
|
{
|
||||||
int ret = 0;
|
int ret = 0;
|
||||||
|
struct amdgpu_device *adev = to_amdgpu_device(control);
|
||||||
struct i2c_msg msg = {
|
struct i2c_msg msg = {
|
||||||
.addr = 0,
|
.addr = 0,
|
||||||
.flags = 0,
|
.flags = 0,
|
||||||
|
@ -137,7 +137,7 @@ static int __update_table_header(struct amdgpu_ras_eeprom_control *control,
|
||||||
|
|
||||||
msg.addr = control->i2c_address;
|
msg.addr = control->i2c_address;
|
||||||
|
|
||||||
ret = i2c_transfer(&control->eeprom_accessor, &msg, 1);
|
ret = i2c_transfer(&adev->pm.smu_i2c, &msg, 1);
|
||||||
if (ret < 1)
|
if (ret < 1)
|
||||||
DRM_ERROR("Failed to write EEPROM table header, ret:%d", ret);
|
DRM_ERROR("Failed to write EEPROM table header, ret:%d", ret);
|
||||||
|
|
||||||
|
@ -251,33 +251,18 @@ int amdgpu_ras_eeprom_init(struct amdgpu_ras_eeprom_control *control)
|
||||||
.buf = buff,
|
.buf = buff,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/* Verify i2c adapter is initialized */
|
||||||
|
if (!adev->pm.smu_i2c.algo)
|
||||||
|
return -ENOENT;
|
||||||
|
|
||||||
if (!__get_eeprom_i2c_addr(adev, &control->i2c_address))
|
if (!__get_eeprom_i2c_addr(adev, &control->i2c_address))
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
|
|
||||||
mutex_init(&control->tbl_mutex);
|
mutex_init(&control->tbl_mutex);
|
||||||
|
|
||||||
switch (adev->asic_type) {
|
|
||||||
case CHIP_VEGA20:
|
|
||||||
ret = smu_v11_0_i2c_eeprom_control_init(&control->eeprom_accessor);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CHIP_ARCTURUS:
|
|
||||||
ret = smu_i2c_eeprom_init(&adev->smu, &control->eeprom_accessor);
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ret) {
|
|
||||||
DRM_ERROR("Failed to init I2C controller, ret:%d", ret);
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
msg.addr = control->i2c_address;
|
msg.addr = control->i2c_address;
|
||||||
|
|
||||||
/* Read/Create table header from EEPROM address 0 */
|
/* Read/Create table header from EEPROM address 0 */
|
||||||
ret = i2c_transfer(&control->eeprom_accessor, &msg, 1);
|
ret = i2c_transfer(&adev->pm.smu_i2c, &msg, 1);
|
||||||
if (ret < 1) {
|
if (ret < 1) {
|
||||||
DRM_ERROR("Failed to read EEPROM table header, ret:%d", ret);
|
DRM_ERROR("Failed to read EEPROM table header, ret:%d", ret);
|
||||||
return ret;
|
return ret;
|
||||||
|
@ -303,23 +288,6 @@ int amdgpu_ras_eeprom_init(struct amdgpu_ras_eeprom_control *control)
|
||||||
return ret == 1 ? 0 : -EIO;
|
return ret == 1 ? 0 : -EIO;
|
||||||
}
|
}
|
||||||
|
|
||||||
void amdgpu_ras_eeprom_fini(struct amdgpu_ras_eeprom_control *control)
|
|
||||||
{
|
|
||||||
struct amdgpu_device *adev = to_amdgpu_device(control);
|
|
||||||
|
|
||||||
switch (adev->asic_type) {
|
|
||||||
case CHIP_VEGA20:
|
|
||||||
smu_v11_0_i2c_eeprom_control_fini(&control->eeprom_accessor);
|
|
||||||
break;
|
|
||||||
case CHIP_ARCTURUS:
|
|
||||||
smu_i2c_eeprom_fini(&adev->smu, &control->eeprom_accessor);
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void __encode_table_record_to_buff(struct amdgpu_ras_eeprom_control *control,
|
static void __encode_table_record_to_buff(struct amdgpu_ras_eeprom_control *control,
|
||||||
struct eeprom_table_record *record,
|
struct eeprom_table_record *record,
|
||||||
unsigned char *buff)
|
unsigned char *buff)
|
||||||
|
@ -476,7 +444,7 @@ int amdgpu_ras_eeprom_process_recods(struct amdgpu_ras_eeprom_control *control,
|
||||||
control->next_addr += EEPROM_TABLE_RECORD_SIZE;
|
control->next_addr += EEPROM_TABLE_RECORD_SIZE;
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = i2c_transfer(&control->eeprom_accessor, msgs, num);
|
ret = i2c_transfer(&adev->pm.smu_i2c, msgs, num);
|
||||||
if (ret < 1) {
|
if (ret < 1) {
|
||||||
DRM_ERROR("Failed to process EEPROM table records, ret:%d", ret);
|
DRM_ERROR("Failed to process EEPROM table records, ret:%d", ret);
|
||||||
|
|
||||||
|
|
|
@ -44,7 +44,6 @@ struct amdgpu_ras_eeprom_table_header {
|
||||||
|
|
||||||
struct amdgpu_ras_eeprom_control {
|
struct amdgpu_ras_eeprom_control {
|
||||||
struct amdgpu_ras_eeprom_table_header tbl_hdr;
|
struct amdgpu_ras_eeprom_table_header tbl_hdr;
|
||||||
struct i2c_adapter eeprom_accessor;
|
|
||||||
uint32_t next_addr;
|
uint32_t next_addr;
|
||||||
unsigned int num_recs;
|
unsigned int num_recs;
|
||||||
struct mutex tbl_mutex;
|
struct mutex tbl_mutex;
|
||||||
|
@ -79,7 +78,6 @@ struct eeprom_table_record {
|
||||||
}__attribute__((__packed__));
|
}__attribute__((__packed__));
|
||||||
|
|
||||||
int amdgpu_ras_eeprom_init(struct amdgpu_ras_eeprom_control *control);
|
int amdgpu_ras_eeprom_init(struct amdgpu_ras_eeprom_control *control);
|
||||||
void amdgpu_ras_eeprom_fini(struct amdgpu_ras_eeprom_control *control);
|
|
||||||
int amdgpu_ras_eeprom_reset_table(struct amdgpu_ras_eeprom_control *control);
|
int amdgpu_ras_eeprom_reset_table(struct amdgpu_ras_eeprom_control *control);
|
||||||
|
|
||||||
int amdgpu_ras_eeprom_process_recods(struct amdgpu_ras_eeprom_control *control,
|
int amdgpu_ras_eeprom_process_recods(struct amdgpu_ras_eeprom_control *control,
|
||||||
|
|
|
@ -46,8 +46,7 @@
|
||||||
#define I2C_NO_STOP 1
|
#define I2C_NO_STOP 1
|
||||||
#define I2C_RESTART 2
|
#define I2C_RESTART 2
|
||||||
|
|
||||||
#define to_amdgpu_device(x) (container_of(x, struct amdgpu_ras, eeprom_control.eeprom_accessor))->adev
|
#define to_amdgpu_device(x) (container_of(x, struct amdgpu_device, pm.smu_i2c))
|
||||||
#define to_eeprom_control(x) container_of(x, struct amdgpu_ras_eeprom_control, eeprom_accessor)
|
|
||||||
|
|
||||||
static void smu_v11_0_i2c_set_clock_gating(struct i2c_adapter *control, bool en)
|
static void smu_v11_0_i2c_set_clock_gating(struct i2c_adapter *control, bool en)
|
||||||
{
|
{
|
||||||
|
@ -592,7 +591,8 @@ static uint32_t smu_v11_0_i2c_eeprom_write_data(struct i2c_adapter *control,
|
||||||
|
|
||||||
static void lock_bus(struct i2c_adapter *i2c, unsigned int flags)
|
static void lock_bus(struct i2c_adapter *i2c, unsigned int flags)
|
||||||
{
|
{
|
||||||
struct amdgpu_ras_eeprom_control *control = to_eeprom_control(i2c);
|
struct amdgpu_device *adev = to_amdgpu_device(i2c);
|
||||||
|
struct amdgpu_ras_eeprom_control *control = &adev->psp.ras.ras->eeprom_control;
|
||||||
|
|
||||||
if (!smu_v11_0_i2c_bus_lock(i2c)) {
|
if (!smu_v11_0_i2c_bus_lock(i2c)) {
|
||||||
DRM_ERROR("Failed to lock the bus from SMU");
|
DRM_ERROR("Failed to lock the bus from SMU");
|
||||||
|
@ -610,7 +610,8 @@ static int trylock_bus(struct i2c_adapter *i2c, unsigned int flags)
|
||||||
|
|
||||||
static void unlock_bus(struct i2c_adapter *i2c, unsigned int flags)
|
static void unlock_bus(struct i2c_adapter *i2c, unsigned int flags)
|
||||||
{
|
{
|
||||||
struct amdgpu_ras_eeprom_control *control = to_eeprom_control(i2c);
|
struct amdgpu_device *adev = to_amdgpu_device(i2c);
|
||||||
|
struct amdgpu_ras_eeprom_control *control = &adev->psp.ras.ras->eeprom_control;
|
||||||
|
|
||||||
if (!smu_v11_0_i2c_bus_unlock(i2c)) {
|
if (!smu_v11_0_i2c_bus_unlock(i2c)) {
|
||||||
DRM_ERROR("Failed to unlock the bus from SMU");
|
DRM_ERROR("Failed to unlock the bus from SMU");
|
||||||
|
@ -630,7 +631,8 @@ static int smu_v11_0_i2c_eeprom_i2c_xfer(struct i2c_adapter *i2c_adap,
|
||||||
struct i2c_msg *msgs, int num)
|
struct i2c_msg *msgs, int num)
|
||||||
{
|
{
|
||||||
int i, ret;
|
int i, ret;
|
||||||
struct amdgpu_ras_eeprom_control *control = to_eeprom_control(i2c_adap);
|
struct amdgpu_device *adev = to_amdgpu_device(i2c_adap);
|
||||||
|
struct amdgpu_ras_eeprom_control *control = &adev->psp.ras.ras->eeprom_control;
|
||||||
|
|
||||||
if (!control->bus_locked) {
|
if (!control->bus_locked) {
|
||||||
DRM_ERROR("I2C bus unlocked, stopping transaction!");
|
DRM_ERROR("I2C bus unlocked, stopping transaction!");
|
||||||
|
@ -679,7 +681,7 @@ int smu_v11_0_i2c_eeprom_control_init(struct i2c_adapter *control)
|
||||||
control->class = I2C_CLASS_SPD;
|
control->class = I2C_CLASS_SPD;
|
||||||
control->dev.parent = &adev->pdev->dev;
|
control->dev.parent = &adev->pdev->dev;
|
||||||
control->algo = &smu_v11_0_i2c_eeprom_i2c_algo;
|
control->algo = &smu_v11_0_i2c_eeprom_i2c_algo;
|
||||||
snprintf(control->name, sizeof(control->name), "RAS EEPROM");
|
snprintf(control->name, sizeof(control->name), "AMDGPU EEPROM");
|
||||||
control->lock_ops = &smu_v11_0_i2c_i2c_lock_ops;
|
control->lock_ops = &smu_v11_0_i2c_i2c_lock_ops;
|
||||||
|
|
||||||
res = i2c_add_adapter(control);
|
res = i2c_add_adapter(control);
|
||||||
|
|
|
@ -932,6 +932,13 @@ static int smu_sw_init(void *handle)
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (adev->smu.ppt_funcs->i2c_eeprom_init) {
|
||||||
|
ret = smu_i2c_eeprom_init(smu, &adev->pm.smu_i2c);
|
||||||
|
|
||||||
|
if (ret)
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -941,6 +948,9 @@ static int smu_sw_fini(void *handle)
|
||||||
struct smu_context *smu = &adev->smu;
|
struct smu_context *smu = &adev->smu;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
|
if (adev->smu.ppt_funcs->i2c_eeprom_fini)
|
||||||
|
smu_i2c_eeprom_fini(smu, &adev->pm.smu_i2c);
|
||||||
|
|
||||||
kfree(smu->irq_source);
|
kfree(smu->irq_source);
|
||||||
smu->irq_source = NULL;
|
smu->irq_source = NULL;
|
||||||
|
|
||||||
|
|
|
@ -41,7 +41,7 @@
|
||||||
#include <linux/pci.h>
|
#include <linux/pci.h>
|
||||||
#include "amdgpu_ras.h"
|
#include "amdgpu_ras.h"
|
||||||
|
|
||||||
#define to_amdgpu_device(x) (container_of(x, struct amdgpu_ras, eeprom_control.eeprom_accessor))->adev
|
#define to_amdgpu_device(x) (container_of(x, struct amdgpu_device, pm.smu_i2c))
|
||||||
|
|
||||||
#define CTF_OFFSET_EDGE 5
|
#define CTF_OFFSET_EDGE 5
|
||||||
#define CTF_OFFSET_HOTSPOT 5
|
#define CTF_OFFSET_HOTSPOT 5
|
||||||
|
@ -2190,7 +2190,7 @@ static int arcturus_i2c_eeprom_control_init(struct i2c_adapter *control)
|
||||||
control->class = I2C_CLASS_SPD;
|
control->class = I2C_CLASS_SPD;
|
||||||
control->dev.parent = &adev->pdev->dev;
|
control->dev.parent = &adev->pdev->dev;
|
||||||
control->algo = &arcturus_i2c_eeprom_i2c_algo;
|
control->algo = &arcturus_i2c_eeprom_i2c_algo;
|
||||||
snprintf(control->name, sizeof(control->name), "RAS EEPROM");
|
snprintf(control->name, sizeof(control->name), "AMDGPU EEPROM");
|
||||||
|
|
||||||
res = i2c_add_adapter(control);
|
res = i2c_add_adapter(control);
|
||||||
if (res)
|
if (res)
|
||||||
|
|
|
@ -33,6 +33,8 @@
|
||||||
#include "smu7_smumgr.h"
|
#include "smu7_smumgr.h"
|
||||||
#include "vega20_hwmgr.h"
|
#include "vega20_hwmgr.h"
|
||||||
|
|
||||||
|
#include "smu_v11_0_i2c.h"
|
||||||
|
|
||||||
/* MP Apertures */
|
/* MP Apertures */
|
||||||
#define MP0_Public 0x03800000
|
#define MP0_Public 0x03800000
|
||||||
#define MP0_SRAM 0x03900000
|
#define MP0_SRAM 0x03900000
|
||||||
|
@ -406,6 +408,7 @@ static int vega20_smu_init(struct pp_hwmgr *hwmgr)
|
||||||
struct vega20_smumgr *priv;
|
struct vega20_smumgr *priv;
|
||||||
unsigned long tools_size = 0x19000;
|
unsigned long tools_size = 0x19000;
|
||||||
int ret = 0;
|
int ret = 0;
|
||||||
|
struct amdgpu_device *adev = hwmgr->adev;
|
||||||
|
|
||||||
struct cgs_firmware_info info = {0};
|
struct cgs_firmware_info info = {0};
|
||||||
|
|
||||||
|
@ -505,6 +508,10 @@ static int vega20_smu_init(struct pp_hwmgr *hwmgr)
|
||||||
priv->smu_tables.entry[TABLE_ACTIVITY_MONITOR_COEFF].version = 0x01;
|
priv->smu_tables.entry[TABLE_ACTIVITY_MONITOR_COEFF].version = 0x01;
|
||||||
priv->smu_tables.entry[TABLE_ACTIVITY_MONITOR_COEFF].size = sizeof(DpmActivityMonitorCoeffInt_t);
|
priv->smu_tables.entry[TABLE_ACTIVITY_MONITOR_COEFF].size = sizeof(DpmActivityMonitorCoeffInt_t);
|
||||||
|
|
||||||
|
ret = smu_v11_0_i2c_eeprom_control_init(&adev->pm.smu_i2c);
|
||||||
|
if (ret)
|
||||||
|
goto err4;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
err4:
|
err4:
|
||||||
|
@ -537,6 +544,9 @@ static int vega20_smu_fini(struct pp_hwmgr *hwmgr)
|
||||||
{
|
{
|
||||||
struct vega20_smumgr *priv =
|
struct vega20_smumgr *priv =
|
||||||
(struct vega20_smumgr *)(hwmgr->smu_backend);
|
(struct vega20_smumgr *)(hwmgr->smu_backend);
|
||||||
|
struct amdgpu_device *adev = hwmgr->adev;
|
||||||
|
|
||||||
|
smu_v11_0_i2c_eeprom_control_fini(&adev->pm.smu_i2c);
|
||||||
|
|
||||||
if (priv) {
|
if (priv) {
|
||||||
amdgpu_bo_free_kernel(&priv->smu_tables.entry[TABLE_PPTABLE].handle,
|
amdgpu_bo_free_kernel(&priv->smu_tables.entry[TABLE_PPTABLE].handle,
|
||||||
|
@ -560,6 +570,7 @@ static int vega20_smu_fini(struct pp_hwmgr *hwmgr)
|
||||||
kfree(hwmgr->smu_backend);
|
kfree(hwmgr->smu_backend);
|
||||||
hwmgr->smu_backend = NULL;
|
hwmgr->smu_backend = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Загрузка…
Ссылка в новой задаче