aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/amd/amdgpu/amdgpu_discovery.c
diff options
context:
space:
mode:
authorXiaojie Yuan <xiaojie.yuan@amd.com>2019-03-27 17:58:25 +0800
committerAlex Deucher <alexander.deucher@amd.com>2019-06-21 18:58:21 -0500
commit437298b833996de86a94d53e4051461cac25010d (patch)
tree603d726440d0c280c04c36a45777f06746f0af54 /drivers/gpu/drm/amd/amdgpu/amdgpu_discovery.c
parentdrm/amdgpu/discovery: add module param for ip discovery enablement (diff)
downloadlinux-dev-437298b833996de86a94d53e4051461cac25010d.tar.xz
linux-dev-437298b833996de86a94d53e4051461cac25010d.zip
drm/amdgpu/discovery: refactor ip list traversal
for each ip, check whether it is needed by amdgpu driver, if yes, record its base addresses v2: change some DRM_INFO to DRM_DEBUG v3: remove unused variable (Alex) Signed-off-by: Xiaojie Yuan <xiaojie.yuan@amd.com> Reviewed-by: Hawking Zhang <Hawking.Zhang@amd.com> Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
Diffstat (limited to 'drivers/gpu/drm/amd/amdgpu/amdgpu_discovery.c')
-rw-r--r--drivers/gpu/drm/amd/amdgpu/amdgpu_discovery.c71
1 files changed, 42 insertions, 29 deletions
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_discovery.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_discovery.c
index 697800c4741f..e049ae6a76fb 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_discovery.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_discovery.c
@@ -266,7 +266,6 @@ int amdgpu_discovery_reg_base_init(struct amdgpu_device *adev)
uint16_t num_ips;
uint8_t num_base_address;
int hw_ip;
- int hw_id;
int i, j, k;
if (!adev->discovery) {
@@ -279,40 +278,54 @@ int amdgpu_discovery_reg_base_init(struct amdgpu_device *adev)
le16_to_cpu(bhdr->table_list[IP_DISCOVERY].offset));
num_dies = le16_to_cpu(ihdr->num_dies);
- for (hw_ip = 0; hw_ip < MAX_HWIP; hw_ip++) {
- hw_id = hw_id_map[hw_ip];
-
- for (i = 0; i < num_dies; i++) {
- die_offset = le16_to_cpu(ihdr->die_info[i].die_offset);
- dhdr = (struct die_header *)(adev->discovery + die_offset);
- num_ips = le16_to_cpu(dhdr->num_ips);
- ip_offset = die_offset + sizeof(*dhdr);
-
- for (j = 0; j < num_ips; j++) {
- ip = (struct ip *)(adev->discovery + ip_offset);
- num_base_address = ip->num_base_address;
-
- if (le16_to_cpu(ip->hw_id) == hw_id) {
- DRM_DEBUG("%s(%d) v%d.%d.%d:\n",
- hw_id_names[hw_id], hw_id,
- ip->major, ip->minor,
- ip->revision);
-
- for (k = 0; k < num_base_address; k++) {
- /*
- * convert the endianness of base addresses in place,
- * so that we don't need to convert them when accessing adev->reg_offset.
- */
- ip->base_address[k] = le32_to_cpu(ip->base_address[k]);
- DRM_DEBUG("\t0x%08x\n", ip->base_address[k]);
- }
+ DRM_DEBUG("number of dies: %d\n", num_dies);
+ for (i = 0; i < num_dies; i++) {
+ die_offset = le16_to_cpu(ihdr->die_info[i].die_offset);
+ dhdr = (struct die_header *)(adev->discovery + die_offset);
+ num_ips = le16_to_cpu(dhdr->num_ips);
+ ip_offset = die_offset + sizeof(*dhdr);
+
+ if (le16_to_cpu(dhdr->die_id) != i) {
+ DRM_ERROR("invalid die id %d, expected %d\n",
+ le16_to_cpu(dhdr->die_id), i);
+ return -EINVAL;
+ }
+
+ DRM_DEBUG("number of hardware IPs on die%d: %d\n",
+ le16_to_cpu(dhdr->die_id), num_ips);
+
+ for (j = 0; j < num_ips; j++) {
+ ip = (struct ip *)(adev->discovery + ip_offset);
+ num_base_address = ip->num_base_address;
+
+ DRM_DEBUG("%s(%d) #%d v%d.%d.%d:\n",
+ hw_id_names[le16_to_cpu(ip->hw_id)],
+ le16_to_cpu(ip->hw_id),
+ ip->number_instance,
+ ip->major, ip->minor,
+ ip->revision);
+
+ for (k = 0; k < num_base_address; k++) {
+ /*
+ * convert the endianness of base addresses in place,
+ * so that we don't need to convert them when accessing adev->reg_offset.
+ */
+ ip->base_address[k] = le32_to_cpu(ip->base_address[k]);
+ DRM_DEBUG("\t0x%08x\n", ip->base_address[k]);
+ }
+
+ for (hw_ip = 0; hw_ip < MAX_HWIP; hw_ip++) {
+ if (hw_id_map[hw_ip] == le16_to_cpu(ip->hw_id)) {
+ DRM_INFO("set register base offset for %s\n",
+ hw_id_names[le16_to_cpu(ip->hw_id)]);
adev->reg_offset[hw_ip][ip->number_instance] =
ip->base_address;
}
- ip_offset += sizeof(*ip) + 4 * (ip->num_base_address - 1);
}
+
+ ip_offset += sizeof(*ip) + 4 * (ip->num_base_address - 1);
}
}