diff options
Diffstat (limited to 'drivers/gpu/drm/amd/amdgpu/soc15.c')
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/soc15.c | 251 | 
1 files changed, 169 insertions, 82 deletions
| diff --git a/drivers/gpu/drm/amd/amdgpu/soc15.c b/drivers/gpu/drm/amd/amdgpu/soc15.c index 6b55d451ae7f..f2c3a49f73a0 100644 --- a/drivers/gpu/drm/amd/amdgpu/soc15.c +++ b/drivers/gpu/drm/amd/amdgpu/soc15.c @@ -23,9 +23,9 @@  #include <linux/firmware.h>  #include <linux/slab.h>  #include <linux/module.h> -#include "drmP.h" +#include <drm/drmP.h>  #include "amdgpu.h" -#include "amdgpu_atomfirmware.h" +#include "amdgpu_atombios.h"  #include "amdgpu_ih.h"  #include "amdgpu_uvd.h"  #include "amdgpu_vce.h" @@ -57,12 +57,11 @@  #include "sdma_v4_0.h"  #include "uvd_v7_0.h"  #include "vce_v4_0.h" +#include "vcn_v1_0.h"  #include "amdgpu_powerplay.h"  #include "dce_virtual.h"  #include "mxgpu_ai.h" -MODULE_FIRMWARE("amdgpu/vega10_smc.bin"); -  #define mmFabricConfigAccessControl                                                                    0x0410  #define mmFabricConfigAccessControl_BASE_IDX                                                           0  #define mmFabricConfigAccessControl_DEFAULT                                      0x00000000 @@ -104,10 +103,10 @@ static u32 soc15_pcie_rreg(struct amdgpu_device *adev, u32 reg)  	u32 r;  	struct nbio_pcie_index_data *nbio_pcie_id; -	if (adev->asic_type == CHIP_VEGA10) -		nbio_pcie_id = &nbio_v6_1_pcie_index_data; +	if (adev->flags & AMD_IS_APU) +		nbio_pcie_id = &nbio_v7_0_pcie_index_data;  	else -		BUG(); +		nbio_pcie_id = &nbio_v6_1_pcie_index_data;  	address = nbio_pcie_id->index_offset;  	data = nbio_pcie_id->data_offset; @@ -125,10 +124,10 @@ static void soc15_pcie_wreg(struct amdgpu_device *adev, u32 reg, u32 v)  	unsigned long flags, address, data;  	struct nbio_pcie_index_data *nbio_pcie_id; -	if (adev->asic_type == CHIP_VEGA10) -		nbio_pcie_id = &nbio_v6_1_pcie_index_data; +	if (adev->flags & AMD_IS_APU) +		nbio_pcie_id = &nbio_v7_0_pcie_index_data;  	else -		BUG(); +		nbio_pcie_id = &nbio_v6_1_pcie_index_data;  	address = nbio_pcie_id->index_offset;  	data = nbio_pcie_id->data_offset; @@ -197,15 +196,66 @@ static void soc15_didt_wreg(struct amdgpu_device *adev, u32 reg, u32 v)  	spin_unlock_irqrestore(&adev->didt_idx_lock, flags);  } +static u32 soc15_gc_cac_rreg(struct amdgpu_device *adev, u32 reg) +{ +	unsigned long flags; +	u32 r; + +	spin_lock_irqsave(&adev->gc_cac_idx_lock, flags); +	WREG32_SOC15(GC, 0, mmGC_CAC_IND_INDEX, (reg)); +	r = RREG32_SOC15(GC, 0, mmGC_CAC_IND_DATA); +	spin_unlock_irqrestore(&adev->gc_cac_idx_lock, flags); +	return r; +} + +static void soc15_gc_cac_wreg(struct amdgpu_device *adev, u32 reg, u32 v) +{ +	unsigned long flags; + +	spin_lock_irqsave(&adev->gc_cac_idx_lock, flags); +	WREG32_SOC15(GC, 0, mmGC_CAC_IND_INDEX, (reg)); +	WREG32_SOC15(GC, 0, mmGC_CAC_IND_DATA, (v)); +	spin_unlock_irqrestore(&adev->gc_cac_idx_lock, flags); +} + +static u32 soc15_se_cac_rreg(struct amdgpu_device *adev, u32 reg) +{ +	unsigned long flags; +	u32 r; + +	spin_lock_irqsave(&adev->se_cac_idx_lock, flags); +	WREG32_SOC15(GC, 0, mmSE_CAC_IND_INDEX, (reg)); +	r = RREG32_SOC15(GC, 0, mmSE_CAC_IND_DATA); +	spin_unlock_irqrestore(&adev->se_cac_idx_lock, flags); +	return r; +} + +static void soc15_se_cac_wreg(struct amdgpu_device *adev, u32 reg, u32 v) +{ +	unsigned long flags; + +	spin_lock_irqsave(&adev->se_cac_idx_lock, flags); +	WREG32_SOC15(GC, 0, mmSE_CAC_IND_INDEX, (reg)); +	WREG32_SOC15(GC, 0, mmSE_CAC_IND_DATA, (v)); +	spin_unlock_irqrestore(&adev->se_cac_idx_lock, flags); +} +  static u32 soc15_get_config_memsize(struct amdgpu_device *adev)  { -	return nbio_v6_1_get_memsize(adev); +	if (adev->flags & AMD_IS_APU) +		return nbio_v7_0_get_memsize(adev); +	else +		return nbio_v6_1_get_memsize(adev);  }  static const u32 vega10_golden_init[] =  {  }; +static const u32 raven_golden_init[] = +{ +}; +  static void soc15_init_golden_registers(struct amdgpu_device *adev)  {  	/* Some of the registers might be dependent on GRBM_GFX_INDEX */ @@ -217,6 +267,11 @@ static void soc15_init_golden_registers(struct amdgpu_device *adev)  						 vega10_golden_init,  						 (const u32)ARRAY_SIZE(vega10_golden_init));  		break; +	case CHIP_RAVEN: +		amdgpu_program_register_sequence(adev, +						 raven_golden_init, +						 (const u32)ARRAY_SIZE(raven_golden_init)); +		break;  	default:  		break;  	} @@ -280,29 +335,25 @@ static bool soc15_read_bios_from_rom(struct amdgpu_device *adev,  	return true;  } -static struct amdgpu_allowed_register_entry vega10_allowed_read_registers[] = { -	/* todo */ -}; -  static struct amdgpu_allowed_register_entry soc15_allowed_read_registers[] = { -	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS2), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS_SE0), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS_SE1), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS_SE2), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS_SE3), false}, -	{ SOC15_REG_OFFSET(SDMA0, 0, mmSDMA0_STATUS_REG), false}, -	{ SOC15_REG_OFFSET(SDMA1, 0, mmSDMA1_STATUS_REG), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmCP_STAT), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmCP_STALLED_STAT1), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmCP_STALLED_STAT2), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmCP_STALLED_STAT3), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmCP_CPF_BUSY_STAT), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmCP_CPF_STALLED_STAT1), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmCP_CPF_STATUS), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmCP_CPC_STALLED_STAT1), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmCP_CPC_STATUS), false}, -	{ SOC15_REG_OFFSET(GC, 0, mmGB_ADDR_CONFIG), false}, +	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS)}, +	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS2)}, +	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS_SE0)}, +	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS_SE1)}, +	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS_SE2)}, +	{ SOC15_REG_OFFSET(GC, 0, mmGRBM_STATUS_SE3)}, +	{ SOC15_REG_OFFSET(SDMA0, 0, mmSDMA0_STATUS_REG)}, +	{ SOC15_REG_OFFSET(SDMA1, 0, mmSDMA1_STATUS_REG)}, +	{ SOC15_REG_OFFSET(GC, 0, mmCP_STAT)}, +	{ SOC15_REG_OFFSET(GC, 0, mmCP_STALLED_STAT1)}, +	{ SOC15_REG_OFFSET(GC, 0, mmCP_STALLED_STAT2)}, +	{ SOC15_REG_OFFSET(GC, 0, mmCP_STALLED_STAT3)}, +	{ SOC15_REG_OFFSET(GC, 0, mmCP_CPF_BUSY_STAT)}, +	{ SOC15_REG_OFFSET(GC, 0, mmCP_CPF_STALLED_STAT1)}, +	{ SOC15_REG_OFFSET(GC, 0, mmCP_CPF_STATUS)}, +	{ SOC15_REG_OFFSET(GC, 0, mmCP_CPC_STALLED_STAT1)}, +	{ SOC15_REG_OFFSET(GC, 0, mmCP_CPC_STATUS)}, +	{ SOC15_REG_OFFSET(GC, 0, mmGB_ADDR_CONFIG)},  };  static uint32_t soc15_read_indexed_register(struct amdgpu_device *adev, u32 se_num, @@ -341,41 +392,16 @@ static uint32_t soc15_get_register_value(struct amdgpu_device *adev,  static int soc15_read_register(struct amdgpu_device *adev, u32 se_num,  			    u32 sh_num, u32 reg_offset, u32 *value)  { -	struct amdgpu_allowed_register_entry *asic_register_table = NULL; -	struct amdgpu_allowed_register_entry *asic_register_entry; -	uint32_t size, i; +	uint32_t i;  	*value = 0; -	switch (adev->asic_type) { -	case CHIP_VEGA10: -		asic_register_table = vega10_allowed_read_registers; -		size = ARRAY_SIZE(vega10_allowed_read_registers); -		break; -	default: -		return -EINVAL; -	} - -	if (asic_register_table) { -		for (i = 0; i < size; i++) { -			asic_register_entry = asic_register_table + i; -			if (reg_offset != asic_register_entry->reg_offset) -				continue; -			if (!asic_register_entry->untouched) -				*value = soc15_get_register_value(adev, -								  asic_register_entry->grbm_indexed, -								  se_num, sh_num, reg_offset); -			return 0; -		} -	} -  	for (i = 0; i < ARRAY_SIZE(soc15_allowed_read_registers); i++) {  		if (reg_offset != soc15_allowed_read_registers[i].reg_offset)  			continue; -		if (!soc15_allowed_read_registers[i].untouched) -			*value = soc15_get_register_value(adev, -							  soc15_allowed_read_registers[i].grbm_indexed, -							  se_num, sh_num, reg_offset); +		*value = soc15_get_register_value(adev, +						  soc15_allowed_read_registers[i].grbm_indexed, +						  se_num, sh_num, reg_offset);  		return 0;  	}  	return -EINVAL; @@ -396,7 +422,10 @@ static void soc15_gpu_pci_config_reset(struct amdgpu_device *adev)  	/* wait for asic to come out of reset */  	for (i = 0; i < adev->usec_timeout; i++) { -		if (nbio_v6_1_get_memsize(adev) != 0xffffffff) +		u32 memsize = (adev->flags & AMD_IS_APU) ? +			nbio_v7_0_get_memsize(adev) : +			nbio_v6_1_get_memsize(adev); +		if (memsize != 0xffffffff)  			break;  		udelay(1);  	} @@ -405,11 +434,11 @@ static void soc15_gpu_pci_config_reset(struct amdgpu_device *adev)  static int soc15_asic_reset(struct amdgpu_device *adev)  { -	amdgpu_atomfirmware_scratch_regs_engine_hung(adev, true); +	amdgpu_atombios_scratch_regs_engine_hung(adev, true);  	soc15_gpu_pci_config_reset(adev); -	amdgpu_atomfirmware_scratch_regs_engine_hung(adev, false); +	amdgpu_atombios_scratch_regs_engine_hung(adev, false);  	return 0;  } @@ -470,8 +499,12 @@ static void soc15_program_aspm(struct amdgpu_device *adev)  static void soc15_enable_doorbell_aperture(struct amdgpu_device *adev,  					bool enable)  { -	nbio_v6_1_enable_doorbell_aperture(adev, enable); -	nbio_v6_1_enable_doorbell_selfring_aperture(adev, enable); +	if (adev->flags & AMD_IS_APU) { +		nbio_v7_0_enable_doorbell_aperture(adev, enable); +	} else { +		nbio_v6_1_enable_doorbell_aperture(adev, enable); +		nbio_v6_1_enable_doorbell_selfring_aperture(adev, enable); +	}  }  static const struct amdgpu_ip_block_version vega10_common_ip_block = @@ -493,8 +526,6 @@ int soc15_set_ip_blocks(struct amdgpu_device *adev)  	switch (adev->asic_type) {  	case CHIP_VEGA10:  		amdgpu_ip_block_add(adev, &vega10_common_ip_block); -		amdgpu_ip_block_add(adev, &gfxhub_v1_0_ip_block); -		amdgpu_ip_block_add(adev, &mmhub_v1_0_ip_block);  		amdgpu_ip_block_add(adev, &gmc_v9_0_ip_block);  		amdgpu_ip_block_add(adev, &vega10_ih_ip_block);  		if (amdgpu_fw_load_type == 2 || amdgpu_fw_load_type == -1) @@ -508,6 +539,18 @@ int soc15_set_ip_blocks(struct amdgpu_device *adev)  		amdgpu_ip_block_add(adev, &uvd_v7_0_ip_block);  		amdgpu_ip_block_add(adev, &vce_v4_0_ip_block);  		break; +	case CHIP_RAVEN: +		amdgpu_ip_block_add(adev, &vega10_common_ip_block); +		amdgpu_ip_block_add(adev, &gmc_v9_0_ip_block); +		amdgpu_ip_block_add(adev, &vega10_ih_ip_block); +		amdgpu_ip_block_add(adev, &psp_v10_0_ip_block); +		amdgpu_ip_block_add(adev, &amdgpu_pp_ip_block); +		if (adev->enable_virtual_display || amdgpu_sriov_vf(adev)) +			amdgpu_ip_block_add(adev, &dce_virtual_ip_block); +		amdgpu_ip_block_add(adev, &gfx_v9_0_ip_block); +		amdgpu_ip_block_add(adev, &sdma_v4_0_ip_block); +		amdgpu_ip_block_add(adev, &vcn_v1_0_ip_block); +		break;  	default:  		return -EINVAL;  	} @@ -517,14 +560,10 @@ int soc15_set_ip_blocks(struct amdgpu_device *adev)  static uint32_t soc15_get_rev_id(struct amdgpu_device *adev)  { -	return nbio_v6_1_get_rev_id(adev); -} - - -int gmc_v9_0_mc_wait_for_idle(struct amdgpu_device *adev) -{ -	/* to be implemented in MC IP*/ -	return 0; +	if (adev->flags & AMD_IS_APU) +		return nbio_v7_0_get_rev_id(adev); +	else +		return nbio_v6_1_get_rev_id(adev);  }  static const struct amdgpu_asic_funcs soc15_asic_funcs = @@ -553,6 +592,10 @@ static int soc15_common_early_init(void *handle)  	adev->uvd_ctx_wreg = &soc15_uvd_ctx_wreg;  	adev->didt_rreg = &soc15_didt_rreg;  	adev->didt_wreg = &soc15_didt_wreg; +	adev->gc_cac_rreg = &soc15_gc_cac_rreg; +	adev->gc_cac_wreg = &soc15_gc_cac_wreg; +	adev->se_cac_rreg = &soc15_se_cac_rreg; +	adev->se_cac_wreg = &soc15_se_cac_wreg;  	adev->asic_funcs = &soc15_asic_funcs; @@ -560,11 +603,6 @@ static int soc15_common_early_init(void *handle)  		(amdgpu_ip_block_mask & (1 << AMD_IP_BLOCK_TYPE_PSP)))  		psp_enabled = true; -	if (amdgpu_sriov_vf(adev)) { -		amdgpu_virt_init_setting(adev); -		xgpu_ai_mailbox_set_irq_funcs(adev); -	} -  	/*  	 * nbio need be used for both sdma and gfx9, but only  	 * initializes once @@ -573,6 +611,9 @@ static int soc15_common_early_init(void *handle)  	case CHIP_VEGA10:  		nbio_v6_1_init(adev);  		break; +	case CHIP_RAVEN: +		nbio_v7_0_init(adev); +		break;  	default:  		return -EINVAL;  	} @@ -603,11 +644,40 @@ static int soc15_common_early_init(void *handle)  		adev->pg_flags = 0;  		adev->external_rev_id = 0x1;  		break; +	case CHIP_RAVEN: +		adev->cg_flags = AMD_CG_SUPPORT_GFX_MGCG | +			AMD_CG_SUPPORT_GFX_MGLS | +			AMD_CG_SUPPORT_GFX_RLC_LS | +			AMD_CG_SUPPORT_GFX_CP_LS | +			AMD_CG_SUPPORT_GFX_3D_CGCG | +			AMD_CG_SUPPORT_GFX_3D_CGLS | +			AMD_CG_SUPPORT_GFX_CGCG | +			AMD_CG_SUPPORT_GFX_CGLS | +			AMD_CG_SUPPORT_BIF_MGCG | +			AMD_CG_SUPPORT_BIF_LS | +			AMD_CG_SUPPORT_HDP_MGCG | +			AMD_CG_SUPPORT_HDP_LS | +			AMD_CG_SUPPORT_DRM_MGCG | +			AMD_CG_SUPPORT_DRM_LS | +			AMD_CG_SUPPORT_ROM_MGCG | +			AMD_CG_SUPPORT_MC_MGCG | +			AMD_CG_SUPPORT_MC_LS | +			AMD_CG_SUPPORT_SDMA_MGCG | +			AMD_CG_SUPPORT_SDMA_LS; +		adev->pg_flags = AMD_PG_SUPPORT_SDMA | +				 AMD_PG_SUPPORT_MMHUB; +		adev->external_rev_id = 0x1; +		break;  	default:  		/* FIXME: not supported yet */  		return -EINVAL;  	} +	if (amdgpu_sriov_vf(adev)) { +		amdgpu_virt_init_setting(adev); +		xgpu_ai_mailbox_set_irq_funcs(adev); +	} +  	adev->firmware.load_type = amdgpu_ucode_get_load_type(adev, amdgpu_fw_load_type);  	amdgpu_get_pcie_info(adev); @@ -650,6 +720,9 @@ static int soc15_common_hw_init(void *handle)  	soc15_pcie_gen3_enable(adev);  	/* enable aspm */  	soc15_program_aspm(adev); +	/* setup nbio registers */ +	if (!(adev->flags & AMD_IS_APU)) +		nbio_v6_1_init_registers(adev);  	/* enable the doorbell aperture */  	soc15_enable_doorbell_aperture(adev, true); @@ -825,6 +898,20 @@ static int soc15_common_set_clockgating_state(void *handle,  		soc15_update_df_medium_grain_clock_gating(adev,  				state == AMD_CG_STATE_GATE ? true : false);  		break; +	case CHIP_RAVEN: +		nbio_v7_0_update_medium_grain_clock_gating(adev, +				state == AMD_CG_STATE_GATE ? true : false); +		nbio_v6_1_update_medium_grain_light_sleep(adev, +				state == AMD_CG_STATE_GATE ? true : false); +		soc15_update_hdp_light_sleep(adev, +				state == AMD_CG_STATE_GATE ? true : false); +		soc15_update_drm_clock_gating(adev, +				state == AMD_CG_STATE_GATE ? true : false); +		soc15_update_drm_light_sleep(adev, +				state == AMD_CG_STATE_GATE ? true : false); +		soc15_update_rom_medium_grain_clock_gating(adev, +				state == AMD_CG_STATE_GATE ? true : false); +		break;  	default:  		break;  	} |