Commit af39e6f4 authored by Lijo Lazar's avatar Lijo Lazar Committed by Alex Deucher
Browse files

drm/amdgpu: Add reg_state sysfs attribute



Add reg_state attribute to fetch the register snapshot of different
IPs like XGMI, WAFL,PCIE and USR. To get a snapshot for a particular IP
	1) Open the sysfs file
	2) Seek to the offset as defined in amdgpu_sysfs_reg_offset
	3) Read

Signed-off-by: default avatarLijo Lazar <lijo.lazar@amd.com>
Reviewed-by: default avatarHawking Zhang <Hawking.Zhang@amd.com>
Signed-off-by: default avatarAlex Deucher <alexander.deucher@amd.com>
parent 9a5095e7
Loading
Loading
Loading
Loading
+62 −0
Original line number Diff line number Diff line
@@ -162,6 +162,65 @@ static ssize_t amdgpu_device_get_pcie_replay_count(struct device *dev,
static DEVICE_ATTR(pcie_replay_count, 0444,
		amdgpu_device_get_pcie_replay_count, NULL);

static ssize_t amdgpu_sysfs_reg_state_get(struct file *f, struct kobject *kobj,
					  struct bin_attribute *attr, char *buf,
					  loff_t ppos, size_t count)
{
	struct device *dev = kobj_to_dev(kobj);
	struct drm_device *ddev = dev_get_drvdata(dev);
	struct amdgpu_device *adev = drm_to_adev(ddev);
	ssize_t bytes_read;

	switch (ppos) {
	case AMDGPU_SYS_REG_STATE_XGMI:
		bytes_read = amdgpu_asic_get_reg_state(
			adev, AMDGPU_REG_STATE_TYPE_XGMI, buf, count);
		break;
	case AMDGPU_SYS_REG_STATE_WAFL:
		bytes_read = amdgpu_asic_get_reg_state(
			adev, AMDGPU_REG_STATE_TYPE_WAFL, buf, count);
		break;
	case AMDGPU_SYS_REG_STATE_PCIE:
		bytes_read = amdgpu_asic_get_reg_state(
			adev, AMDGPU_REG_STATE_TYPE_PCIE, buf, count);
		break;
	case AMDGPU_SYS_REG_STATE_USR:
		bytes_read = amdgpu_asic_get_reg_state(
			adev, AMDGPU_REG_STATE_TYPE_USR, buf, count);
		break;
	case AMDGPU_SYS_REG_STATE_USR_1:
		bytes_read = amdgpu_asic_get_reg_state(
			adev, AMDGPU_REG_STATE_TYPE_USR_1, buf, count);
		break;
	default:
		return -EINVAL;
	}

	return bytes_read;
}

BIN_ATTR(reg_state, 0444, amdgpu_sysfs_reg_state_get, NULL,
	 AMDGPU_SYS_REG_STATE_END);

int amdgpu_reg_state_sysfs_init(struct amdgpu_device *adev)
{
	int ret;

	if (!amdgpu_asic_get_reg_state_supported(adev))
		return 0;

	ret = sysfs_create_bin_file(&adev->dev->kobj, &bin_attr_reg_state);

	return ret;
}

void amdgpu_reg_state_sysfs_fini(struct amdgpu_device *adev)
{
	if (!amdgpu_asic_get_reg_state_supported(adev))
		return;
	sysfs_remove_bin_file(&adev->dev->kobj, &bin_attr_reg_state);
}

/**
 * DOC: board_info
 *
@@ -4233,6 +4292,7 @@ int amdgpu_device_init(struct amdgpu_device *adev,
			"Could not create amdgpu board attributes\n");

	amdgpu_fru_sysfs_init(adev);
	amdgpu_reg_state_sysfs_init(adev);

	if (IS_ENABLED(CONFIG_PERF_EVENTS))
		r = amdgpu_pmu_init(adev);
@@ -4355,6 +4415,8 @@ void amdgpu_device_fini_hw(struct amdgpu_device *adev)
	sysfs_remove_files(&adev->dev->kobj, amdgpu_dev_attributes);
	amdgpu_fru_sysfs_fini(adev);

	amdgpu_reg_state_sysfs_fini(adev);

	/* disable ras feature must before hw fini */
	amdgpu_ras_pre_fini(adev);

+13 −0
Original line number Diff line number Diff line
@@ -34,6 +34,15 @@ enum amdgpu_reg_state {
	AMDGPU_REG_STATE_TYPE_USR_1	= 5
};

enum amdgpu_sysfs_reg_offset {
	AMDGPU_SYS_REG_STATE_XGMI	= 0x0000,
	AMDGPU_SYS_REG_STATE_WAFL	= 0x1000,
	AMDGPU_SYS_REG_STATE_PCIE	= 0x2000,
	AMDGPU_SYS_REG_STATE_USR	= 0x3000,
	AMDGPU_SYS_REG_STATE_USR_1	= 0x4000,
	AMDGPU_SYS_REG_STATE_END	= 0x5000,
};

struct amdgpu_reg_state_header {
	uint16_t		structure_size;
	uint8_t			format_revision;
@@ -137,4 +146,8 @@ static inline size_t amdgpu_reginst_size(uint16_t num_inst, size_t inst_size,
						   (size)) :               \
		 0)


int amdgpu_reg_state_sysfs_init(struct amdgpu_device *adev);
void amdgpu_reg_state_sysfs_fini(struct amdgpu_device *adev);

#endif