diff options
author | Huang Rui <ray.huang@amd.com> | 2016-09-09 04:37:08 -0400 |
---|---|---|
committer | Alex Deucher <alexander.deucher@amd.com> | 2016-09-19 14:38:24 -0400 |
commit | 865ab832ba78a1baf03fed90dccf5088e63a3aa3 (patch) | |
tree | c5bd156536f5e14b761f33600dc98aeaf8c125d4 /drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c | |
parent | e805ed83ba1ca0961d19496c944faed27aef82a3 (diff) |
drm/amdgpu: implement raster configuration for gfx v6
This patch is to implement the raster configuration and harvested
configuration of gfx v6.
Signed-off-by: Huang Rui <ray.huang@amd.com>
Reviewed-by: Alex Deucher <alexander.deucher@amd.com>
Acked-by: Edward O'Callaghan <funfunctor@folklore1984.net>
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
Diffstat (limited to 'drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c')
-rw-r--r-- | drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c | 131 |
1 files changed, 130 insertions, 1 deletions
diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c b/drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c index 410b29c05671..40abb6b81c09 100644 --- a/drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c +++ b/drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c | |||
@@ -931,6 +931,123 @@ static u32 gfx_v6_0_get_rb_disabled(struct amdgpu_device *adev, | |||
931 | return data & mask; | 931 | return data & mask; |
932 | } | 932 | } |
933 | 933 | ||
934 | static void gfx_v6_0_raster_config(struct amdgpu_device *adev, u32 *rconf) | ||
935 | { | ||
936 | switch (adev->asic_type) { | ||
937 | case CHIP_TAHITI: | ||
938 | case CHIP_PITCAIRN: | ||
939 | *rconf |= RB_XSEL2(2) | RB_XSEL | PKR_MAP(2) | PKR_YSEL(1) | | ||
940 | SE_MAP(2) | SE_XSEL(2) | SE_YSEL(2); | ||
941 | break; | ||
942 | case CHIP_VERDE: | ||
943 | *rconf |= RB_XSEL | PKR_MAP(2) | PKR_YSEL(1); | ||
944 | break; | ||
945 | case CHIP_OLAND: | ||
946 | *rconf |= RB_YSEL; | ||
947 | break; | ||
948 | case CHIP_HAINAN: | ||
949 | *rconf |= 0x0; | ||
950 | break; | ||
951 | default: | ||
952 | DRM_ERROR("unknown asic: 0x%x\n", adev->asic_type); | ||
953 | break; | ||
954 | } | ||
955 | } | ||
956 | |||
957 | static void gfx_v6_0_write_harvested_raster_configs(struct amdgpu_device *adev, | ||
958 | u32 raster_config, unsigned rb_mask, | ||
959 | unsigned num_rb) | ||
960 | { | ||
961 | unsigned sh_per_se = max_t(unsigned, adev->gfx.config.max_sh_per_se, 1); | ||
962 | unsigned num_se = max_t(unsigned, adev->gfx.config.max_shader_engines, 1); | ||
963 | unsigned rb_per_pkr = min_t(unsigned, num_rb / num_se / sh_per_se, 2); | ||
964 | unsigned rb_per_se = num_rb / num_se; | ||
965 | unsigned se_mask[4]; | ||
966 | unsigned se; | ||
967 | |||
968 | se_mask[0] = ((1 << rb_per_se) - 1) & rb_mask; | ||
969 | se_mask[1] = (se_mask[0] << rb_per_se) & rb_mask; | ||
970 | se_mask[2] = (se_mask[1] << rb_per_se) & rb_mask; | ||
971 | se_mask[3] = (se_mask[2] << rb_per_se) & rb_mask; | ||
972 | |||
973 | WARN_ON(!(num_se == 1 || num_se == 2 || num_se == 4)); | ||
974 | WARN_ON(!(sh_per_se == 1 || sh_per_se == 2)); | ||
975 | WARN_ON(!(rb_per_pkr == 1 || rb_per_pkr == 2)); | ||
976 | |||
977 | for (se = 0; se < num_se; se++) { | ||
978 | unsigned raster_config_se = raster_config; | ||
979 | unsigned pkr0_mask = ((1 << rb_per_pkr) - 1) << (se * rb_per_se); | ||
980 | unsigned pkr1_mask = pkr0_mask << rb_per_pkr; | ||
981 | int idx = (se / 2) * 2; | ||
982 | |||
983 | if ((num_se > 1) && (!se_mask[idx] || !se_mask[idx + 1])) { | ||
984 | raster_config_se &= ~SE_MAP_MASK; | ||
985 | |||
986 | if (!se_mask[idx]) { | ||
987 | raster_config_se |= SE_MAP(RASTER_CONFIG_SE_MAP_3); | ||
988 | } else { | ||
989 | raster_config_se |= SE_MAP(RASTER_CONFIG_SE_MAP_0); | ||
990 | } | ||
991 | } | ||
992 | |||
993 | pkr0_mask &= rb_mask; | ||
994 | pkr1_mask &= rb_mask; | ||
995 | if (rb_per_se > 2 && (!pkr0_mask || !pkr1_mask)) { | ||
996 | raster_config_se &= ~PKR_MAP_MASK; | ||
997 | |||
998 | if (!pkr0_mask) { | ||
999 | raster_config_se |= PKR_MAP(RASTER_CONFIG_PKR_MAP_3); | ||
1000 | } else { | ||
1001 | raster_config_se |= PKR_MAP(RASTER_CONFIG_PKR_MAP_0); | ||
1002 | } | ||
1003 | } | ||
1004 | |||
1005 | if (rb_per_se >= 2) { | ||
1006 | unsigned rb0_mask = 1 << (se * rb_per_se); | ||
1007 | unsigned rb1_mask = rb0_mask << 1; | ||
1008 | |||
1009 | rb0_mask &= rb_mask; | ||
1010 | rb1_mask &= rb_mask; | ||
1011 | if (!rb0_mask || !rb1_mask) { | ||
1012 | raster_config_se &= ~RB_MAP_PKR0_MASK; | ||
1013 | |||
1014 | if (!rb0_mask) { | ||
1015 | raster_config_se |= | ||
1016 | RB_MAP_PKR0(RASTER_CONFIG_RB_MAP_3); | ||
1017 | } else { | ||
1018 | raster_config_se |= | ||
1019 | RB_MAP_PKR0(RASTER_CONFIG_RB_MAP_0); | ||
1020 | } | ||
1021 | } | ||
1022 | |||
1023 | if (rb_per_se > 2) { | ||
1024 | rb0_mask = 1 << (se * rb_per_se + rb_per_pkr); | ||
1025 | rb1_mask = rb0_mask << 1; | ||
1026 | rb0_mask &= rb_mask; | ||
1027 | rb1_mask &= rb_mask; | ||
1028 | if (!rb0_mask || !rb1_mask) { | ||
1029 | raster_config_se &= ~RB_MAP_PKR1_MASK; | ||
1030 | |||
1031 | if (!rb0_mask) { | ||
1032 | raster_config_se |= | ||
1033 | RB_MAP_PKR1(RASTER_CONFIG_RB_MAP_3); | ||
1034 | } else { | ||
1035 | raster_config_se |= | ||
1036 | RB_MAP_PKR1(RASTER_CONFIG_RB_MAP_0); | ||
1037 | } | ||
1038 | } | ||
1039 | } | ||
1040 | } | ||
1041 | |||
1042 | /* GRBM_GFX_INDEX has a different offset on SI */ | ||
1043 | gfx_v6_0_select_se_sh(adev, se, 0xffffffff, 0xffffffff); | ||
1044 | WREG32(PA_SC_RASTER_CONFIG, raster_config_se); | ||
1045 | } | ||
1046 | |||
1047 | /* GRBM_GFX_INDEX has a different offset on SI */ | ||
1048 | gfx_v6_0_select_se_sh(adev, 0xffffffff, 0xffffffff, 0xffffffff); | ||
1049 | } | ||
1050 | |||
934 | static void gfx_v6_0_setup_rb(struct amdgpu_device *adev, | 1051 | static void gfx_v6_0_setup_rb(struct amdgpu_device *adev, |
935 | u32 se_num, u32 sh_per_se, | 1052 | u32 se_num, u32 sh_per_se, |
936 | u32 max_rb_num_per_se) | 1053 | u32 max_rb_num_per_se) |
@@ -939,6 +1056,7 @@ static void gfx_v6_0_setup_rb(struct amdgpu_device *adev, | |||
939 | u32 data, mask; | 1056 | u32 data, mask; |
940 | u32 disabled_rbs = 0; | 1057 | u32 disabled_rbs = 0; |
941 | u32 enabled_rbs = 0; | 1058 | u32 enabled_rbs = 0; |
1059 | unsigned num_rb_pipes; | ||
942 | 1060 | ||
943 | mutex_lock(&adev->grbm_idx_mutex); | 1061 | mutex_lock(&adev->grbm_idx_mutex); |
944 | for (i = 0; i < se_num; i++) { | 1062 | for (i = 0; i < se_num; i++) { |
@@ -961,6 +1079,9 @@ static void gfx_v6_0_setup_rb(struct amdgpu_device *adev, | |||
961 | adev->gfx.config.backend_enable_mask = enabled_rbs; | 1079 | adev->gfx.config.backend_enable_mask = enabled_rbs; |
962 | adev->gfx.config.num_rbs = hweight32(enabled_rbs); | 1080 | adev->gfx.config.num_rbs = hweight32(enabled_rbs); |
963 | 1081 | ||
1082 | num_rb_pipes = min_t(unsigned, adev->gfx.config.max_backends_per_se * | ||
1083 | adev->gfx.config.max_shader_engines, 16); | ||
1084 | |||
964 | mutex_lock(&adev->grbm_idx_mutex); | 1085 | mutex_lock(&adev->grbm_idx_mutex); |
965 | for (i = 0; i < se_num; i++) { | 1086 | for (i = 0; i < se_num; i++) { |
966 | gfx_v6_0_select_se_sh(adev, i, 0xffffffff, 0xffffffff); | 1087 | gfx_v6_0_select_se_sh(adev, i, 0xffffffff, 0xffffffff); |
@@ -980,7 +1101,15 @@ static void gfx_v6_0_setup_rb(struct amdgpu_device *adev, | |||
980 | } | 1101 | } |
981 | enabled_rbs >>= 2; | 1102 | enabled_rbs >>= 2; |
982 | } | 1103 | } |
983 | WREG32(PA_SC_RASTER_CONFIG, data); | 1104 | gfx_v6_0_raster_config(adev, &data); |
1105 | |||
1106 | if (!adev->gfx.config.backend_enable_mask || | ||
1107 | adev->gfx.config.num_rbs >= num_rb_pipes) | ||
1108 | WREG32(PA_SC_RASTER_CONFIG, data); | ||
1109 | else | ||
1110 | gfx_v6_0_write_harvested_raster_configs(adev, data, | ||
1111 | adev->gfx.config.backend_enable_mask, | ||
1112 | num_rb_pipes); | ||
984 | } | 1113 | } |
985 | gfx_v6_0_select_se_sh(adev, 0xffffffff, 0xffffffff, 0xffffffff); | 1114 | gfx_v6_0_select_se_sh(adev, 0xffffffff, 0xffffffff, 0xffffffff); |
986 | mutex_unlock(&adev->grbm_idx_mutex); | 1115 | mutex_unlock(&adev->grbm_idx_mutex); |