diff options
58 files changed, 605 insertions, 279 deletions
| diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu.h b/drivers/gpu/drm/amd/amdgpu/amdgpu.h index f9c81bc21ba4..5993dd0fdd8e 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu.h +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu.h @@ -1024,6 +1024,7 @@ struct amdgpu_device {  	/* enable runtime pm on the device */  	bool                            runpm;  	bool                            in_runpm; +	bool                            has_pr3;  	bool                            pm_sysfs_en;  	bool                            ucode_sysfs_en; @@ -1230,6 +1231,7 @@ void amdgpu_device_program_register_sequence(struct amdgpu_device *adev,  					     const u32 *registers,  					     const u32 array_size); +bool amdgpu_device_supports_atpx(struct drm_device *dev);  bool amdgpu_device_supports_boco(struct drm_device *dev);  bool amdgpu_device_supports_baco(struct drm_device *dev);  bool amdgpu_device_is_peer_accessible(struct amdgpu_device *adev, @@ -1313,11 +1315,11 @@ int amdgpu_acpi_pcie_notify_device_ready(struct amdgpu_device *adev);  void amdgpu_acpi_get_backlight_caps(struct amdgpu_device *adev,  		struct amdgpu_dm_backlight_caps *caps); -bool amdgpu_acpi_is_s0ix_supported(void); +bool amdgpu_acpi_is_s0ix_supported(struct amdgpu_device *adev);  #else  static inline int amdgpu_acpi_init(struct amdgpu_device *adev) { return 0; }  static inline void amdgpu_acpi_fini(struct amdgpu_device *adev) { } -static inline bool amdgpu_acpi_is_s0ix_supported(void) { return false; } +static inline bool amdgpu_acpi_is_s0ix_supported(struct amdgpu_device *adev) { return false; }  #endif  int amdgpu_cs_find_mapping(struct amdgpu_cs_parser *parser, diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_acpi.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_acpi.c index 4f4fda53c08a..8155c54392c8 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_acpi.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_acpi.c @@ -901,10 +901,12 @@ void amdgpu_acpi_fini(struct amdgpu_device *adev)   *   * returns true if supported, false if not.   */ -bool amdgpu_acpi_is_s0ix_supported(void) +bool amdgpu_acpi_is_s0ix_supported(struct amdgpu_device *adev)  { -	if (acpi_gbl_FADT.flags & ACPI_FADT_LOW_POWER_S0) -		return true; +	if (acpi_gbl_FADT.flags & ACPI_FADT_LOW_POWER_S0) { +		if (adev->flags & AMD_IS_APU) +			return true; +	}  	return false;  } diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c index 7791d074bd32..2d991da2cead 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c @@ -1213,7 +1213,7 @@ int amdgpu_amdkfd_gpuvm_alloc_memory_of_gpu(  	ret = amdgpu_amdkfd_reserve_mem_limit(adev, size, alloc_domain, !!sg);  	if (ret) { -		pr_debug("Insufficient system memory\n"); +		pr_debug("Insufficient memory\n");  		goto err_reserve_limit;  	} diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c index 79dd85f71fab..7d2f7a2240b8 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c @@ -212,14 +212,14 @@ static DEVICE_ATTR(serial_number, S_IRUGO,  		amdgpu_device_get_serial_number, NULL);  /** - * amdgpu_device_supports_boco - Is the device a dGPU with HG/PX power control + * amdgpu_device_supports_atpx - Is the device a dGPU with HG/PX power control   *   * @dev: drm_device pointer   *   * Returns true if the device is a dGPU with HG/PX power control,   * otherwise return false.   */ -bool amdgpu_device_supports_boco(struct drm_device *dev) +bool amdgpu_device_supports_atpx(struct drm_device *dev)  {  	struct amdgpu_device *adev = drm_to_adev(dev); @@ -229,6 +229,23 @@ bool amdgpu_device_supports_boco(struct drm_device *dev)  }  /** + * amdgpu_device_supports_boco - Is the device a dGPU with ACPI power resources + * + * @dev: drm_device pointer + * + * Returns true if the device is a dGPU with HG/PX power control, + * otherwise return false. + */ +bool amdgpu_device_supports_boco(struct drm_device *dev) +{ +	struct amdgpu_device *adev = drm_to_adev(dev); + +	if (adev->has_pr3) +		return true; +	return false; +} + +/**   * amdgpu_device_supports_baco - Does the device support BACO   *   * @dev: drm_device pointer @@ -1398,7 +1415,7 @@ static void amdgpu_switcheroo_set_state(struct pci_dev *pdev,  	struct drm_device *dev = pci_get_drvdata(pdev);  	int r; -	if (amdgpu_device_supports_boco(dev) && state == VGA_SWITCHEROO_OFF) +	if (amdgpu_device_supports_atpx(dev) && state == VGA_SWITCHEROO_OFF)  		return;  	if (state == VGA_SWITCHEROO_ON) { @@ -2650,7 +2667,7 @@ static int amdgpu_device_ip_suspend_phase1(struct amdgpu_device *adev)  {  	int i, r; -	if (!amdgpu_acpi_is_s0ix_supported() || amdgpu_in_reset(adev)) { +	if (!amdgpu_acpi_is_s0ix_supported(adev) || amdgpu_in_reset(adev)) {  		amdgpu_device_set_pg_state(adev, AMD_PG_STATE_UNGATE);  		amdgpu_device_set_cg_state(adev, AMD_CG_STATE_UNGATE);  	} @@ -3177,7 +3194,7 @@ int amdgpu_device_init(struct amdgpu_device *adev,  	struct drm_device *ddev = adev_to_drm(adev);  	struct pci_dev *pdev = adev->pdev;  	int r, i; -	bool boco = false; +	bool atpx = false;  	u32 max_MBps;  	adev->shutdown = false; @@ -3349,15 +3366,15 @@ int amdgpu_device_init(struct amdgpu_device *adev,  	if ((adev->pdev->class >> 8) == PCI_CLASS_DISPLAY_VGA)  		vga_client_register(adev->pdev, adev, NULL, amdgpu_device_vga_set_decode); -	if (amdgpu_device_supports_boco(ddev)) -		boco = true; +	if (amdgpu_device_supports_atpx(ddev)) +		atpx = true;  	if (amdgpu_has_atpx() &&  	    (amdgpu_is_atpx_hybrid() ||  	     amdgpu_has_atpx_dgpu_power_cntl()) &&  	    !pci_is_thunderbolt_attached(adev->pdev))  		vga_switcheroo_register_client(adev->pdev, -					       &amdgpu_switcheroo_ops, boco); -	if (boco) +					       &amdgpu_switcheroo_ops, atpx); +	if (atpx)  		vga_switcheroo_init_domain_pm_ops(adev->dev, &adev->vga_pm_domain);  	if (amdgpu_emu_mode == 1) { @@ -3540,7 +3557,7 @@ fence_driver_init:  failed:  	amdgpu_vf_error_trans_all(adev); -	if (boco) +	if (atpx)  		vga_switcheroo_fini_domain_pm_ops(adev->dev);  failed_unmap: @@ -3604,7 +3621,7 @@ void amdgpu_device_fini(struct amdgpu_device *adev)  	     amdgpu_has_atpx_dgpu_power_cntl()) &&  	    !pci_is_thunderbolt_attached(adev->pdev))  		vga_switcheroo_unregister_client(adev->pdev); -	if (amdgpu_device_supports_boco(adev_to_drm(adev))) +	if (amdgpu_device_supports_atpx(adev_to_drm(adev)))  		vga_switcheroo_fini_domain_pm_ops(adev->dev);  	if ((adev->pdev->class >> 8) == PCI_CLASS_DISPLAY_VGA)  		vga_client_register(adev->pdev, NULL, NULL, NULL); @@ -3710,7 +3727,7 @@ int amdgpu_device_suspend(struct drm_device *dev, bool fbcon)  	amdgpu_fence_driver_suspend(adev); -	if (!amdgpu_acpi_is_s0ix_supported() || amdgpu_in_reset(adev)) +	if (!amdgpu_acpi_is_s0ix_supported(adev) || amdgpu_in_reset(adev))  		r = amdgpu_device_ip_suspend_phase2(adev);  	else  		amdgpu_gfx_state_change_set(adev, sGpuChangeState_D3Entry); @@ -3744,7 +3761,7 @@ int amdgpu_device_resume(struct drm_device *dev, bool fbcon)  	if (dev->switch_power_state == DRM_SWITCH_POWER_OFF)  		return 0; -	if (amdgpu_acpi_is_s0ix_supported()) +	if (amdgpu_acpi_is_s0ix_supported(adev))  		amdgpu_gfx_state_change_set(adev, sGpuChangeState_D0Entry);  	/* post card */ diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c index 31506a1678c3..72efd579ec5e 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c @@ -1340,7 +1340,7 @@ static int amdgpu_pmops_runtime_suspend(struct device *dev)  	}  	adev->in_runpm = true; -	if (amdgpu_device_supports_boco(drm_dev)) +	if (amdgpu_device_supports_atpx(drm_dev))  		drm_dev->switch_power_state = DRM_SWITCH_POWER_CHANGING;  	drm_kms_helper_poll_disable(drm_dev); @@ -1348,13 +1348,11 @@ static int amdgpu_pmops_runtime_suspend(struct device *dev)  	if (ret)  		return ret; -	if (amdgpu_device_supports_boco(drm_dev)) { +	if (amdgpu_device_supports_atpx(drm_dev)) {  		/* Only need to handle PCI state in the driver for ATPX  		 * PCI core handles it for _PR3.  		 */ -		if (amdgpu_is_atpx_hybrid()) { -			pci_ignore_hotplug(pdev); -		} else { +		if (!amdgpu_is_atpx_hybrid()) {  			amdgpu_device_cache_pci_state(pdev);  			pci_disable_device(pdev);  			pci_ignore_hotplug(pdev); @@ -1378,28 +1376,31 @@ static int amdgpu_pmops_runtime_resume(struct device *dev)  	if (!adev->runpm)  		return -EINVAL; -	if (amdgpu_device_supports_boco(drm_dev)) { +	if (amdgpu_device_supports_atpx(drm_dev)) {  		drm_dev->switch_power_state = DRM_SWITCH_POWER_CHANGING;  		/* Only need to handle PCI state in the driver for ATPX  		 * PCI core handles it for _PR3.  		 */ -		if (amdgpu_is_atpx_hybrid()) { -			pci_set_master(pdev); -		} else { +		if (!amdgpu_is_atpx_hybrid()) {  			pci_set_power_state(pdev, PCI_D0);  			amdgpu_device_load_pci_state(pdev);  			ret = pci_enable_device(pdev);  			if (ret)  				return ret; -			pci_set_master(pdev);  		} +		pci_set_master(pdev); +	} else if (amdgpu_device_supports_boco(drm_dev)) { +		/* Only need to handle PCI state in the driver for ATPX +		 * PCI core handles it for _PR3. +		 */ +		pci_set_master(pdev);  	} else if (amdgpu_device_supports_baco(drm_dev)) {  		amdgpu_device_baco_exit(drm_dev);  	}  	ret = amdgpu_device_resume(drm_dev, false);  	drm_kms_helper_poll_enable(drm_dev); -	if (amdgpu_device_supports_boco(drm_dev)) +	if (amdgpu_device_supports_atpx(drm_dev))  		drm_dev->switch_power_state = DRM_SWITCH_POWER_ON;  	adev->in_runpm = false;  	return 0; diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_gmc.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_gmc.c index 02af47ddddbc..c2ced5be6d7b 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_gmc.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_gmc.c @@ -496,13 +496,14 @@ void amdgpu_gmc_get_vbios_allocations(struct amdgpu_device *adev)  		break;  	} -	if (!amdgpu_device_ip_get_ip_block(adev, AMD_IP_BLOCK_TYPE_DCE)) +	if (!amdgpu_device_ip_get_ip_block(adev, AMD_IP_BLOCK_TYPE_DCE)) {  		size = 0; -	else +	} else {  		size = amdgpu_gmc_get_vbios_fb_size(adev); -	if (adev->mman.keep_stolen_vga_memory) -		size = max(size, (unsigned)AMDGPU_VBIOS_VGA_ALLOCATION); +		if (adev->mman.keep_stolen_vga_memory) +			size = max(size, (unsigned)AMDGPU_VBIOS_VGA_ALLOCATION); +	}  	/* set to 0 if the pre-OS buffer uses up most of vram */  	if ((adev->gmc.real_vram_size - size) < (8 * 1024 * 1024)) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c index fc12fc72366f..b16b32797624 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c @@ -133,6 +133,7 @@ void amdgpu_register_gpu_instance(struct amdgpu_device *adev)  int amdgpu_driver_load_kms(struct amdgpu_device *adev, unsigned long flags)  {  	struct drm_device *dev; +	struct pci_dev *parent;  	int r, acpi_status;  	dev = adev_to_drm(adev); @@ -144,6 +145,9 @@ int amdgpu_driver_load_kms(struct amdgpu_device *adev, unsigned long flags)  	    !pci_is_thunderbolt_attached(dev->pdev))  		flags |= AMD_IS_PX; +	parent = pci_upstream_bridge(adev->pdev); +	adev->has_pr3 = parent ? pci_pr3_present(parent) : false; +  	/* amdgpu_device_init should report only fatal error  	 * like memory allocation failure or iomapping failure,  	 * or memory manager initialization failure, it must @@ -156,9 +160,14 @@ int amdgpu_driver_load_kms(struct amdgpu_device *adev, unsigned long flags)  		goto out;  	} -	if (amdgpu_device_supports_boco(dev) && -	    (amdgpu_runtime_pm != 0)) { /* enable runpm by default for boco */ +	if (amdgpu_device_supports_atpx(dev) && +	    (amdgpu_runtime_pm != 0)) { /* enable runpm by default for atpx */ +		adev->runpm = true; +		dev_info(adev->dev, "Using ATPX for runtime pm\n"); +	} else if (amdgpu_device_supports_boco(dev) && +		   (amdgpu_runtime_pm != 0)) { /* enable runpm by default for boco */  		adev->runpm = true; +		dev_info(adev->dev, "Using BOCO for runtime pm\n");  	} else if (amdgpu_device_supports_baco(dev) &&  		   (amdgpu_runtime_pm != 0)) {  		switch (adev->asic_type) { @@ -180,6 +189,8 @@ int amdgpu_driver_load_kms(struct amdgpu_device *adev, unsigned long flags)  			adev->runpm = true;  			break;  		} +		if (adev->runpm) +			dev_info(adev->dev, "Using BACO for runtime pm\n");  	}  	/* Call ACPI methods: require modeset init @@ -192,7 +203,7 @@ int amdgpu_driver_load_kms(struct amdgpu_device *adev, unsigned long flags)  	if (adev->runpm) {  		/* only need to skip on ATPX */ -		if (amdgpu_device_supports_boco(dev) && +		if (amdgpu_device_supports_atpx(dev) &&  		    !amdgpu_is_atpx_hybrid())  			dev_pm_set_driver_flags(dev->dev, DPM_FLAG_NO_DIRECT_COMPLETE);  		pm_runtime_use_autosuspend(dev->dev); diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_trace.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_trace.h index 324d5e3f3579..6752d8b13118 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_trace.h +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_trace.h @@ -358,10 +358,11 @@ TRACE_EVENT(amdgpu_vm_update_ptes,  			}  	),  	TP_printk("pid:%u vm_ctx:0x%llx start:0x%010llx end:0x%010llx," -		  " flags:0x%llx, incr:%llu, dst:\n%s", __entry->pid, +		  " flags:0x%llx, incr:%llu, dst:\n%s%s", __entry->pid,  		  __entry->vm_ctx, __entry->start, __entry->end,  		  __entry->flags, __entry->incr,  __print_array( -		  __get_dynamic_array(dst), __entry->nptes, 8)) +		  __get_dynamic_array(dst), min(__entry->nptes, 32u), 8), +		  __entry->nptes > 32 ? "..." : "")  );  TRACE_EVENT(amdgpu_vm_set_ptes, diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c index 7c5b60e53482..8b989670ed66 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c @@ -240,7 +240,7 @@ int amdgpu_uvd_sw_init(struct amdgpu_device *adev)  		version_major = (le32_to_cpu(hdr->ucode_version) >> 24) & 0xff;  		version_minor = (le32_to_cpu(hdr->ucode_version) >> 8) & 0xff; -		DRM_INFO("Found UVD firmware Version: %hu.%hu Family ID: %hu\n", +		DRM_INFO("Found UVD firmware Version: %u.%u Family ID: %u\n",  			version_major, version_minor, family_id);  		/* @@ -267,7 +267,7 @@ int amdgpu_uvd_sw_init(struct amdgpu_device *adev)  		dec_minor = (le32_to_cpu(hdr->ucode_version) >> 8) & 0xff;  		enc_minor = (le32_to_cpu(hdr->ucode_version) >> 24) & 0x3f;  		enc_major = (le32_to_cpu(hdr->ucode_version) >> 30) & 0x3; -		DRM_INFO("Found UVD firmware ENC: %hu.%hu DEC: .%hu Family ID: %hu\n", +		DRM_INFO("Found UVD firmware ENC: %u.%u DEC: .%u Family ID: %u\n",  			enc_major, enc_minor, dec_minor, family_id);  		adev->uvd.max_handles = AMDGPU_MAX_UVD_HANDLES; diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c index 9791a4057e8b..0d5284b936e4 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c @@ -179,7 +179,7 @@ int amdgpu_vce_sw_init(struct amdgpu_device *adev, unsigned long size)  	version_major = (ucode_version >> 20) & 0xfff;  	version_minor = (ucode_version >> 8) & 0xfff;  	binary_id = ucode_version & 0xff; -	DRM_INFO("Found VCE firmware Version: %hhd.%hhd Binary ID: %hhd\n", +	DRM_INFO("Found VCE firmware Version: %d.%d Binary ID: %d\n",  		version_major, version_minor, binary_id);  	adev->vce.fw_version = ((version_major << 24) | (version_minor << 16) |  				(binary_id << 8)); diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c index 1c97244e0d74..4a77c7424dfc 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c @@ -181,7 +181,7 @@ int amdgpu_vcn_sw_init(struct amdgpu_device *adev)  		enc_major = fw_check;  		dec_ver = (le32_to_cpu(hdr->ucode_version) >> 24) & 0xf;  		vep = (le32_to_cpu(hdr->ucode_version) >> 28) & 0xf; -		DRM_INFO("Found VCN firmware Version ENC: %hu.%hu DEC: %hu VEP: %hu Revision: %hu\n", +		DRM_INFO("Found VCN firmware Version ENC: %u.%u DEC: %u VEP: %u Revision: %u\n",  			enc_major, enc_minor, dec_ver, vep, fw_rev);  	} else {  		unsigned int version_major, version_minor, family_id; @@ -189,7 +189,7 @@ int amdgpu_vcn_sw_init(struct amdgpu_device *adev)  		family_id = le32_to_cpu(hdr->ucode_version) & 0xff;  		version_major = (le32_to_cpu(hdr->ucode_version) >> 24) & 0xff;  		version_minor = (le32_to_cpu(hdr->ucode_version) >> 8) & 0xff; -		DRM_INFO("Found VCN firmware Version: %hu.%hu Family ID: %hu\n", +		DRM_INFO("Found VCN firmware Version: %u.%u Family ID: %u\n",  			version_major, version_minor, family_id);  	} diff --git a/drivers/gpu/drm/amd/amdgpu/mmhub_v2_0.c b/drivers/gpu/drm/amd/amdgpu/mmhub_v2_0.c index 092ff2c43658..f107385faba2 100644 --- a/drivers/gpu/drm/amd/amdgpu/mmhub_v2_0.c +++ b/drivers/gpu/drm/amd/amdgpu/mmhub_v2_0.c @@ -136,6 +136,7 @@ mmhub_v2_0_print_l2_protection_fault_status(struct amdgpu_device *adev,  		break;  	case CHIP_SIENNA_CICHLID:  	case CHIP_NAVY_FLOUNDER: +	case CHIP_DIMGREY_CAVEFISH:  		mmhub_cid = mmhub_client_ids_sienna_cichlid[cid][rw];  		break;  	default: diff --git a/drivers/gpu/drm/amd/amdgpu/mxgpu_ai.c b/drivers/gpu/drm/amd/amdgpu/mxgpu_ai.c index f5ce9a9f4cf5..7767ccca526b 100644 --- a/drivers/gpu/drm/amd/amdgpu/mxgpu_ai.c +++ b/drivers/gpu/drm/amd/amdgpu/mxgpu_ai.c @@ -187,7 +187,16 @@ static int xgpu_ai_send_access_requests(struct amdgpu_device *adev,  static int xgpu_ai_request_reset(struct amdgpu_device *adev)  { -	return xgpu_ai_send_access_requests(adev, IDH_REQ_GPU_RESET_ACCESS); +	int ret, i = 0; + +	while (i < AI_MAILBOX_POLL_MSG_REP_MAX) { +		ret = xgpu_ai_send_access_requests(adev, IDH_REQ_GPU_RESET_ACCESS); +		if (!ret) +			break; +		i++; +	} + +	return ret;  }  static int xgpu_ai_request_full_gpu_access(struct amdgpu_device *adev, diff --git a/drivers/gpu/drm/amd/amdgpu/mxgpu_ai.h b/drivers/gpu/drm/amd/amdgpu/mxgpu_ai.h index 83b453f5d717..50572635d0f8 100644 --- a/drivers/gpu/drm/amd/amdgpu/mxgpu_ai.h +++ b/drivers/gpu/drm/amd/amdgpu/mxgpu_ai.h @@ -25,8 +25,9 @@  #define __MXGPU_AI_H__  #define AI_MAILBOX_POLL_ACK_TIMEDOUT	500 -#define AI_MAILBOX_POLL_MSG_TIMEDOUT	12000 +#define AI_MAILBOX_POLL_MSG_TIMEDOUT	6000  #define AI_MAILBOX_POLL_FLR_TIMEDOUT	5000 +#define AI_MAILBOX_POLL_MSG_REP_MAX	11  enum idh_request {  	IDH_REQ_GPU_INIT_ACCESS = 1, diff --git a/drivers/gpu/drm/amd/amdgpu/mxgpu_nv.c b/drivers/gpu/drm/amd/amdgpu/mxgpu_nv.c index 666ed99cc14b..dd5c1e6ce009 100644 --- a/drivers/gpu/drm/amd/amdgpu/mxgpu_nv.c +++ b/drivers/gpu/drm/amd/amdgpu/mxgpu_nv.c @@ -200,7 +200,16 @@ static int xgpu_nv_send_access_requests(struct amdgpu_device *adev,  static int xgpu_nv_request_reset(struct amdgpu_device *adev)  { -	return xgpu_nv_send_access_requests(adev, IDH_REQ_GPU_RESET_ACCESS); +	int ret, i = 0; + +	while (i < NV_MAILBOX_POLL_MSG_REP_MAX) { +		ret = xgpu_nv_send_access_requests(adev, IDH_REQ_GPU_RESET_ACCESS); +		if (!ret) +			break; +		i++; +	} + +	return ret;  }  static int xgpu_nv_request_full_gpu_access(struct amdgpu_device *adev, diff --git a/drivers/gpu/drm/amd/amdgpu/mxgpu_nv.h b/drivers/gpu/drm/amd/amdgpu/mxgpu_nv.h index 52605e14a1a5..9f5808616174 100644 --- a/drivers/gpu/drm/amd/amdgpu/mxgpu_nv.h +++ b/drivers/gpu/drm/amd/amdgpu/mxgpu_nv.h @@ -27,6 +27,7 @@  #define NV_MAILBOX_POLL_ACK_TIMEDOUT	500  #define NV_MAILBOX_POLL_MSG_TIMEDOUT	6000  #define NV_MAILBOX_POLL_FLR_TIMEDOUT	5000 +#define NV_MAILBOX_POLL_MSG_REP_MAX	11  enum idh_request {  	IDH_REQ_GPU_INIT_ACCESS = 1, diff --git a/drivers/gpu/drm/amd/amdgpu/nv.c b/drivers/gpu/drm/amd/amdgpu/nv.c index ac02dd707c44..6bee3677394a 100644 --- a/drivers/gpu/drm/amd/amdgpu/nv.c +++ b/drivers/gpu/drm/amd/amdgpu/nv.c @@ -362,6 +362,7 @@ nv_asic_reset_method(struct amdgpu_device *adev)  	switch (adev->asic_type) {  	case CHIP_SIENNA_CICHLID:  	case CHIP_NAVY_FLOUNDER: +	case CHIP_DIMGREY_CAVEFISH:  		return AMD_RESET_METHOD_MODE1;  	default:  		if (smu_baco_is_support(smu)) diff --git a/drivers/gpu/drm/amd/amdgpu/sdma_v5_2.c b/drivers/gpu/drm/amd/amdgpu/sdma_v5_2.c index 39e17aae655f..f1ba36a094da 100644 --- a/drivers/gpu/drm/amd/amdgpu/sdma_v5_2.c +++ b/drivers/gpu/drm/amd/amdgpu/sdma_v5_2.c @@ -153,6 +153,9 @@ static int sdma_v5_2_init_microcode(struct amdgpu_device *adev)  	struct amdgpu_firmware_info *info = NULL;  	const struct common_firmware_header *header = NULL; +	if (amdgpu_sriov_vf(adev) && (adev->asic_type == CHIP_SIENNA_CICHLID)) +		return 0; +  	DRM_DEBUG("\n");  	switch (adev->asic_type) { @@ -807,6 +810,37 @@ static int sdma_v5_2_load_microcode(struct amdgpu_device *adev)  	return 0;  } +static int sdma_v5_2_soft_reset(void *handle) +{ +	struct amdgpu_device *adev = (struct amdgpu_device *)handle; +	u32 grbm_soft_reset; +	u32 tmp; +	int i; + +	for (i = 0; i < adev->sdma.num_instances; i++) { +		grbm_soft_reset = REG_SET_FIELD(0, +						GRBM_SOFT_RESET, SOFT_RESET_SDMA0, +						1); +		grbm_soft_reset <<= i; + +		tmp = RREG32_SOC15(GC, 0, mmGRBM_SOFT_RESET); +		tmp |= grbm_soft_reset; +		DRM_DEBUG("GRBM_SOFT_RESET=0x%08X\n", tmp); +		WREG32_SOC15(GC, 0, mmGRBM_SOFT_RESET, tmp); +		tmp = RREG32_SOC15(GC, 0, mmGRBM_SOFT_RESET); + +		udelay(50); + +		tmp &= ~grbm_soft_reset; +		WREG32_SOC15(GC, 0, mmGRBM_SOFT_RESET, tmp); +		tmp = RREG32_SOC15(GC, 0, mmGRBM_SOFT_RESET); + +		udelay(50); +	} + +	return 0; +} +  /**   * sdma_v5_2_start - setup and start the async dma engines   * @@ -838,6 +872,7 @@ static int sdma_v5_2_start(struct amdgpu_device *adev)  			msleep(1000);  	} +	sdma_v5_2_soft_reset(adev);  	/* unhalt the MEs */  	sdma_v5_2_enable(adev, true);  	/* enable sdma ring preemption */ @@ -1366,13 +1401,6 @@ static int sdma_v5_2_wait_for_idle(void *handle)  	return -ETIMEDOUT;  } -static int sdma_v5_2_soft_reset(void *handle) -{ -	/* todo */ - -	return 0; -} -  static int sdma_v5_2_ring_preempt_ib(struct amdgpu_ring *ring)  {  	int i, r = 0; diff --git a/drivers/gpu/drm/amd/amdkfd/Kconfig b/drivers/gpu/drm/amd/amdkfd/Kconfig index b3672d10ea54..e8fb10c41f16 100644 --- a/drivers/gpu/drm/amd/amdkfd/Kconfig +++ b/drivers/gpu/drm/amd/amdkfd/Kconfig @@ -1,6 +1,6 @@  # SPDX-License-Identifier: MIT  # -# Heterogenous system architecture configuration +# Heterogeneous system architecture configuration  #  config HSA_AMD diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.c b/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.c index f0a6f6665c81..e686ce2bf3b3 100644 --- a/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.c +++ b/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.c @@ -72,8 +72,8 @@ enum KFD_MQD_TYPE get_mqd_type_from_queue_type(enum kfd_queue_type type)  static bool is_pipe_enabled(struct device_queue_manager *dqm, int mec, int pipe)  {  	int i; -	int pipe_offset = mec * dqm->dev->shared_resources.num_pipe_per_mec -		+ pipe * dqm->dev->shared_resources.num_queue_per_pipe; +	int pipe_offset = (mec * dqm->dev->shared_resources.num_pipe_per_mec +		+ pipe) * dqm->dev->shared_resources.num_queue_per_pipe;  	/* queue is available for KFD usage if bit is 1 */  	for (i = 0; i <  dqm->dev->shared_resources.num_queue_per_pipe; ++i) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index c23896207e9d..2c4dbdeec46a 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -196,10 +196,6 @@ static int amdgpu_dm_encoder_init(struct drm_device *dev,  static int amdgpu_dm_connector_get_modes(struct drm_connector *connector); -static int amdgpu_dm_atomic_commit(struct drm_device *dev, -				   struct drm_atomic_state *state, -				   bool nonblock); -  static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state);  static int amdgpu_dm_atomic_check(struct drm_device *dev, @@ -2212,7 +2208,7 @@ static const struct drm_mode_config_funcs amdgpu_dm_mode_funcs = {  	.get_format_info = amd_get_format_info,  	.output_poll_changed = drm_fb_helper_output_poll_changed,  	.atomic_check = amdgpu_dm_atomic_check, -	.atomic_commit = amdgpu_dm_atomic_commit, +	.atomic_commit = drm_atomic_helper_commit,  };  static struct drm_mode_config_helper_funcs amdgpu_dm_mode_config_helperfuncs = { @@ -5124,9 +5120,8 @@ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,  	int preferred_refresh = 0;  #if defined(CONFIG_DRM_AMD_DC_DCN)  	struct dsc_dec_dpcd_caps dsc_caps; -#endif  	uint32_t link_bandwidth_kbps; - +#endif  	struct dc_sink *sink = NULL;  	if (aconnector == NULL) {  		DRM_ERROR("aconnector is NULL!\n"); @@ -5208,11 +5203,9 @@ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,  				      aconnector->dc_link->dpcd_caps.dsc_caps.dsc_basic_caps.raw,  				      aconnector->dc_link->dpcd_caps.dsc_caps.dsc_branch_decoder_caps.raw,  				      &dsc_caps); -#endif  		link_bandwidth_kbps = dc_link_bandwidth_kbps(aconnector->dc_link,  							     dc_link_get_link_cap(aconnector->dc_link)); -#if defined(CONFIG_DRM_AMD_DC_DCN)  		if (aconnector->dsc_settings.dsc_force_enable != DSC_CLK_FORCE_DISABLE && dsc_caps.is_dsc_supported) {  			/* Set DSC policy according to dsc_clock_en */  			dc_dsc_policy_set_enable_dsc_when_not_needed( @@ -5349,7 +5342,7 @@ dm_crtc_duplicate_state(struct drm_crtc *crtc)  }  #ifdef CONFIG_DEBUG_FS -int amdgpu_dm_crtc_atomic_set_property(struct drm_crtc *crtc, +static int amdgpu_dm_crtc_atomic_set_property(struct drm_crtc *crtc,  					    struct drm_crtc_state *crtc_state,  					    struct drm_property *property,  					    uint64_t val) @@ -5373,7 +5366,7 @@ int amdgpu_dm_crtc_atomic_set_property(struct drm_crtc *crtc,  	return 0;  } -int amdgpu_dm_crtc_atomic_get_property(struct drm_crtc *crtc, +static int amdgpu_dm_crtc_atomic_get_property(struct drm_crtc *crtc,  					    const struct drm_crtc_state *state,  					    struct drm_property *property,  					    uint64_t *val) @@ -8070,20 +8063,6 @@ static void amdgpu_dm_crtc_copy_transient_flags(struct drm_crtc_state *crtc_stat  	stream_state->mode_changed = drm_atomic_crtc_needs_modeset(crtc_state);  } -static int amdgpu_dm_atomic_commit(struct drm_device *dev, -				   struct drm_atomic_state *state, -				   bool nonblock) -{ -	/* -	 * Add check here for SoC's that support hardware cursor plane, to -	 * unset legacy_cursor_update -	 */ - -	return drm_atomic_helper_commit(dev, state, nonblock); - -	/*TODO Handle EINTR, reenable IRQ*/ -} -  /**   * amdgpu_dm_atomic_commit_tail() - AMDgpu DM's commit tail implementation.   * @state: The atomic state to commit diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h index 0b31779a0485..2ee6edb3df93 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h @@ -337,10 +337,29 @@ struct amdgpu_display_manager {  	const struct gpu_info_soc_bounding_box_v1_0 *soc_bounding_box;  #ifdef CONFIG_DEBUG_FS -	/* set the crc calculation window*/ +	/** +	 * @crc_win_x_start_property: +	 * +	 * X start of the crc calculation window +	 */  	struct drm_property *crc_win_x_start_property; +	/** +	 * @crc_win_y_start_property: +	 * +	 * Y start of the crc calculation window +	 */  	struct drm_property *crc_win_y_start_property; +	/** +	 * @crc_win_x_end_property: +	 * +	 * X end of the crc calculation window +	 */  	struct drm_property *crc_win_x_end_property; +	/** +	 * @crc_win_y_end_property: +	 * +	 * Y end of the crc calculation window +	 */  	struct drm_property *crc_win_y_end_property;  #endif  	/** diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c index ff6db26626ea..7b886a779a8c 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c @@ -81,6 +81,14 @@ const char *const *amdgpu_dm_crtc_get_crc_sources(struct drm_crtc *crtc,  	return pipe_crc_sources;  } +static void amdgpu_dm_set_crc_window_default(struct dm_crtc_state *dm_crtc_state) +{ +	dm_crtc_state->crc_window.x_start = 0; +	dm_crtc_state->crc_window.y_start = 0; +	dm_crtc_state->crc_window.x_end = 0; +	dm_crtc_state->crc_window.y_end = 0; +} +  bool amdgpu_dm_crc_window_is_default(struct dm_crtc_state *dm_crtc_state)  {  	bool ret = true; @@ -141,7 +149,10 @@ int amdgpu_dm_crtc_configure_crc_source(struct drm_crtc *crtc,  	mutex_lock(&adev->dm.dc_lock);  	/* Enable CRTC CRC generation if necessary. */ -	if (dm_is_crc_source_crtc(source)) { +	if (dm_is_crc_source_crtc(source) || source == AMDGPU_DM_PIPE_CRC_SOURCE_NONE) { +		if (!enable) +			amdgpu_dm_set_crc_window_default(dm_crtc_state); +  		if (!amdgpu_dm_crc_window_is_default(dm_crtc_state)) {  			crc_window = &tmp_window; diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c index 6f4fe8fce6b7..d00b02553d62 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c @@ -746,24 +746,24 @@ static struct wm_table ddr4_wm_table_rn = {  			.wm_inst = WM_B,  			.wm_type = WM_TYPE_PSTATE_CHG,  			.pstate_latency_us = 11.72, -			.sr_exit_time_us = 10.12, -			.sr_enter_plus_exit_time_us = 11.48, +			.sr_exit_time_us = 11.12, +			.sr_enter_plus_exit_time_us = 12.48,  			.valid = true,  		},  		{  			.wm_inst = WM_C,  			.wm_type = WM_TYPE_PSTATE_CHG,  			.pstate_latency_us = 11.72, -			.sr_exit_time_us = 10.12, -			.sr_enter_plus_exit_time_us = 11.48, +			.sr_exit_time_us = 11.12, +			.sr_enter_plus_exit_time_us = 12.48,  			.valid = true,  		},  		{  			.wm_inst = WM_D,  			.wm_type = WM_TYPE_PSTATE_CHG,  			.pstate_latency_us = 11.72, -			.sr_exit_time_us = 10.12, -			.sr_enter_plus_exit_time_us = 11.48, +			.sr_exit_time_us = 11.12, +			.sr_enter_plus_exit_time_us = 12.48,  			.valid = true,  		},  	} diff --git a/drivers/gpu/drm/amd/display/dc/core/dc.c b/drivers/gpu/drm/amd/display/dc/core/dc.c index 58eb0d69873a..7339d9855ec8 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc.c @@ -2625,6 +2625,26 @@ static void commit_planes_for_stream(struct dc *dc,  		}  	} +	if (update_type != UPDATE_TYPE_FAST) { +		// If changing VTG FP2: wait until back in vactive to program FP2 +		// Need to ensure that pipe unlock happens soon after to minimize race condition +		for (i = 0; i < dc->res_pool->pipe_count; i++) { +			struct pipe_ctx *pipe_ctx = &context->res_ctx.pipe_ctx[i]; + +			if (pipe_ctx->top_pipe || pipe_ctx->stream != stream) +				continue; + +			if (!pipe_ctx->update_flags.bits.global_sync) +				continue; + +			pipe_ctx->stream_res.tg->funcs->wait_for_state(pipe_ctx->stream_res.tg, CRTC_STATE_VBLANK); +			pipe_ctx->stream_res.tg->funcs->wait_for_state(pipe_ctx->stream_res.tg, CRTC_STATE_VACTIVE); + +			pipe_ctx->stream_res.tg->funcs->set_vtg_params( +					pipe_ctx->stream_res.tg, &pipe_ctx->stream->timing, true); +		} +	} +  	if ((update_type != UPDATE_TYPE_FAST) && dc->hwss.interdependent_update_lock)  		dc->hwss.interdependent_update_lock(dc, context, false);  	else diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index a901baf2aaef..9e1071b2181f 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -3267,9 +3267,6 @@ void core_link_enable_stream(  			}  		} -#if defined(CONFIG_DRM_AMD_DC_DCN3_0) -#endif -  		/* turn off otg test pattern if enable */  		if (pipe_ctx->stream_res.tg->funcs->set_test_pattern)  			pipe_ctx->stream_res.tg->funcs->set_test_pattern(pipe_ctx->stream_res.tg, diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index b8f1e2d33423..3aedadb34548 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -42,7 +42,7 @@  #include "inc/hw/dmcu.h"  #include "dml/display_mode_lib.h" -#define DC_VER "3.2.115" +#define DC_VER "3.2.116"  #define MAX_SURFACES 3  #define MAX_PLANES 6 diff --git a/drivers/gpu/drm/amd/display/dc/dce/dce_link_encoder.c b/drivers/gpu/drm/amd/display/dc/dce/dce_link_encoder.c index b409f6b2bfd8..210466b2d863 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dce_link_encoder.c +++ b/drivers/gpu/drm/amd/display/dc/dce/dce_link_encoder.c @@ -119,7 +119,8 @@ static const struct link_encoder_funcs dce110_lnk_enc_funcs = {  	.disable_hpd = dce110_link_encoder_disable_hpd,  	.is_dig_enabled = dce110_is_dig_enabled,  	.destroy = dce110_link_encoder_destroy, -	.get_max_link_cap = dce110_link_encoder_get_max_link_cap +	.get_max_link_cap = dce110_link_encoder_get_max_link_cap, +	.get_dig_frontend = dce110_get_dig_frontend,  };  static enum bp_result link_transmitter_control( @@ -235,6 +236,44 @@ static void set_link_training_complete(  } +unsigned int dce110_get_dig_frontend(struct link_encoder *enc) +{ +	struct dce110_link_encoder *enc110 = TO_DCE110_LINK_ENC(enc); +	u32 value; +	enum engine_id result; + +	REG_GET(DIG_BE_CNTL, DIG_FE_SOURCE_SELECT, &value); + +	switch (value) { +	case DCE110_DIG_FE_SOURCE_SELECT_DIGA: +		result = ENGINE_ID_DIGA; +		break; +	case DCE110_DIG_FE_SOURCE_SELECT_DIGB: +		result = ENGINE_ID_DIGB; +		break; +	case DCE110_DIG_FE_SOURCE_SELECT_DIGC: +		result = ENGINE_ID_DIGC; +		break; +	case DCE110_DIG_FE_SOURCE_SELECT_DIGD: +		result = ENGINE_ID_DIGD; +		break; +	case DCE110_DIG_FE_SOURCE_SELECT_DIGE: +		result = ENGINE_ID_DIGE; +		break; +	case DCE110_DIG_FE_SOURCE_SELECT_DIGF: +		result = ENGINE_ID_DIGF; +		break; +	case DCE110_DIG_FE_SOURCE_SELECT_DIGG: +		result = ENGINE_ID_DIGG; +		break; +	default: +		// invalid source select DIG +		result = ENGINE_ID_UNKNOWN; +	} + +	return result; +} +  void dce110_link_encoder_set_dp_phy_pattern_training_pattern(  	struct link_encoder *enc,  	uint32_t index) @@ -1665,7 +1704,8 @@ static const struct link_encoder_funcs dce60_lnk_enc_funcs = {  	.disable_hpd = dce110_link_encoder_disable_hpd,  	.is_dig_enabled = dce110_is_dig_enabled,  	.destroy = dce110_link_encoder_destroy, -	.get_max_link_cap = dce110_link_encoder_get_max_link_cap +	.get_max_link_cap = dce110_link_encoder_get_max_link_cap, +	.get_dig_frontend = dce110_get_dig_frontend  };  void dce60_link_encoder_construct( diff --git a/drivers/gpu/drm/amd/display/dc/dce/dce_link_encoder.h b/drivers/gpu/drm/amd/display/dc/dce/dce_link_encoder.h index cb714a48b171..fc6ade824c23 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dce_link_encoder.h +++ b/drivers/gpu/drm/amd/display/dc/dce/dce_link_encoder.h @@ -295,6 +295,8 @@ void dce110_link_encoder_connect_dig_be_to_fe(  	enum engine_id engine,  	bool connect); +unsigned int dce110_get_dig_frontend(struct link_encoder *enc); +  void dce110_link_encoder_set_dp_phy_pattern_training_pattern(  	struct link_encoder *enc,  	uint32_t index); diff --git a/drivers/gpu/drm/amd/display/dc/dce120/dce120_timing_generator.c b/drivers/gpu/drm/amd/display/dc/dce120/dce120_timing_generator.c index 82bc4e192bbf..915fbb8e8168 100644 --- a/drivers/gpu/drm/amd/display/dc/dce120/dce120_timing_generator.c +++ b/drivers/gpu/drm/amd/display/dc/dce120/dce120_timing_generator.c @@ -1268,7 +1268,7 @@ void dce120_timing_generator_construct(  	tg110->min_h_front_porch = 0;  	tg110->min_h_back_porch = 0; -	tg110->min_h_sync_width = 8; +	tg110->min_h_sync_width = 4;  	tg110->min_v_sync_width = 1;  	tg110->min_v_blank = 3;  } diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hubbub.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hubbub.c index 75637c291e75..6f42d10dd772 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hubbub.c +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hubbub.c @@ -124,11 +124,11 @@ bool hubbub1_verify_allow_pstate_change_high(  	 * still not asserted, we are probably stuck and going to hang  	 *  	 * TODO: Figure out why it takes ~100us on linux -	 * pstate takes around ~100us on linux. Unknown currently as to -	 * why it takes that long on linux +	 * pstate takes around ~100us (up to 200us) on linux. Unknown currently +	 * as to why it takes that long on linux  	 */  	const unsigned int pstate_wait_timeout_us = 200; -	const unsigned int pstate_wait_expected_timeout_us = 40; +	const unsigned int pstate_wait_expected_timeout_us = 180;  	static unsigned int max_sampled_pstate_wait_us; /* data collection */  	static bool forced_pstate_allow; /* help with revert wa */ diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c index 9f7d6b087553..cfc130e2d6fd 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c @@ -2736,7 +2736,7 @@ static void dcn10_program_all_pipe_in_tree(  				pipe_ctx->pipe_dlg_param.vupdate_width);  		pipe_ctx->stream_res.tg->funcs->set_vtg_params( -				pipe_ctx->stream_res.tg, &pipe_ctx->stream->timing); +				pipe_ctx->stream_res.tg, &pipe_ctx->stream->timing, true);  		if (hws->funcs.setup_vupdate_interrupt)  			hws->funcs.setup_vupdate_interrupt(dc, pipe_ctx); diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_optc.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_optc.c index a125d3f05c81..f033397a84e9 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_optc.c +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_optc.c @@ -272,7 +272,7 @@ void optc1_program_timing(  			vupdate_offset,  			vupdate_width); -	optc->funcs->set_vtg_params(optc, dc_crtc_timing); +	optc->funcs->set_vtg_params(optc, dc_crtc_timing, true);  	/* TODO  	 * patched_crtc_timing.flags.HORZ_COUNT_BY_TWO == 1 @@ -312,7 +312,7 @@ void optc1_program_timing(  }  void optc1_set_vtg_params(struct timing_generator *optc, -		const struct dc_crtc_timing *dc_crtc_timing) +		const struct dc_crtc_timing *dc_crtc_timing, bool program_fp2)  {  	struct dc_crtc_timing patched_crtc_timing;  	uint32_t asic_blank_end; @@ -348,9 +348,12 @@ void optc1_set_vtg_params(struct timing_generator *optc,  		}  	} -	REG_UPDATE_2(CONTROL, -			VTG0_FP2, v_fp2, -			VTG0_VCOUNT_INIT, v_init); +	if (program_fp2) +		REG_UPDATE_2(CONTROL, +				VTG0_FP2, v_fp2, +				VTG0_VCOUNT_INIT, v_init); +	else +		REG_UPDATE(CONTROL, VTG0_VCOUNT_INIT, v_init);  }  void optc1_set_blank_data_double_buffer(struct timing_generator *optc, bool enable) @@ -1540,7 +1543,7 @@ void dcn10_timing_generator_init(struct optc *optc1)  	optc1->min_h_blank = 32;  	optc1->min_v_blank = 3;  	optc1->min_v_blank_interlace = 5; -	optc1->min_h_sync_width = 8; +	optc1->min_h_sync_width = 4;  	optc1->min_v_sync_width = 1;  } diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_optc.h b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_optc.h index 344eb487219e..b12bd9aae52f 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_optc.h +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_optc.h @@ -700,6 +700,6 @@ bool optc1_get_crc(struct timing_generator *optc,  bool optc1_is_two_pixels_per_containter(const struct dc_crtc_timing *timing);  void optc1_set_vtg_params(struct timing_generator *optc, -		const struct dc_crtc_timing *dc_crtc_timing); +		const struct dc_crtc_timing *dc_crtc_timing, bool program_fp2);  #endif /* __DC_TIMING_GENERATOR_DCN10_H__ */ diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_stream_encoder.h b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_stream_encoder.h index 9e38c37c1d73..76b334644f9e 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_stream_encoder.h +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_stream_encoder.h @@ -81,7 +81,9 @@  	SRI(DP_MSE_RATE_UPDATE, DP, id), \  	SRI(DP_PIXEL_FORMAT, DP, id), \  	SRI(DP_SEC_CNTL, DP, id), \ +	SRI(DP_SEC_CNTL1, DP, id), \  	SRI(DP_SEC_CNTL2, DP, id), \ +	SRI(DP_SEC_CNTL5, DP, id), \  	SRI(DP_SEC_CNTL6, DP, id), \  	SRI(DP_STEER_FIFO, DP, id), \  	SRI(DP_VID_M, DP, id), \ @@ -126,7 +128,9 @@ struct dcn10_stream_enc_registers {  	uint32_t DP_MSE_RATE_UPDATE;  	uint32_t DP_PIXEL_FORMAT;  	uint32_t DP_SEC_CNTL; +	uint32_t DP_SEC_CNTL1;  	uint32_t DP_SEC_CNTL2; +	uint32_t DP_SEC_CNTL5;  	uint32_t DP_SEC_CNTL6;  	uint32_t DP_STEER_FIFO;  	uint32_t DP_VID_M; @@ -411,6 +415,8 @@ struct dcn10_stream_enc_registers {  	type DP_SEC_GSP3_ENABLE;\  	type DP_SEC_GSP4_ENABLE;\  	type DP_SEC_GSP5_ENABLE;\ +	type DP_SEC_GSP5_LINE_NUM;\ +	type DP_SEC_GSP5_LINE_REFERENCE;\  	type DP_SEC_GSP6_ENABLE;\  	type DP_SEC_GSP7_ENABLE;\  	type DP_SEC_GSP7_PPS;\ diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c index abcb06044e6e..31a477194d3b 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c @@ -1595,7 +1595,7 @@ static void dcn20_program_pipe(  				pipe_ctx->pipe_dlg_param.vupdate_width);  		pipe_ctx->stream_res.tg->funcs->set_vtg_params( -				pipe_ctx->stream_res.tg, &pipe_ctx->stream->timing); +				pipe_ctx->stream_res.tg, &pipe_ctx->stream->timing, false);  		if (hws->funcs.setup_vupdate_interrupt)  			hws->funcs.setup_vupdate_interrupt(dc, pipe_ctx); @@ -1695,14 +1695,6 @@ void dcn20_program_front_end_for_ctx(  				&& context->res_ctx.pipe_ctx[i].stream)  			hws->funcs.blank_pixel_data(dc, &context->res_ctx.pipe_ctx[i], true); -	/* wait for outstanding pending changes before adding or removing planes */ -	for (i = 0; i < dc->res_pool->pipe_count; i++) { -		if (context->res_ctx.pipe_ctx[i].update_flags.bits.disable || -				context->res_ctx.pipe_ctx[i].update_flags.bits.enable) { -			dc->hwss.wait_for_pending_cleared(dc, context); -			break; -		} -	}  	/* Disconnect mpcc */  	for (i = 0; i < dc->res_pool->pipe_count; i++) @@ -1856,7 +1848,7 @@ bool dcn20_update_bandwidth(  					pipe_ctx->pipe_dlg_param.vupdate_width);  			pipe_ctx->stream_res.tg->funcs->set_vtg_params( -					pipe_ctx->stream_res.tg, &pipe_ctx->stream->timing); +					pipe_ctx->stream_res.tg, &pipe_ctx->stream->timing, false);  			if (pipe_ctx->prev_odm_pipe == NULL)  				hws->funcs.blank_pixel_data(dc, pipe_ctx, blank); @@ -2251,11 +2243,11 @@ void dcn20_get_mpctree_visual_confirm_color(  {  	const struct tg_color pipe_colors[6] = {  			{MAX_TG_COLOR_VALUE, 0, 0}, // red -			{MAX_TG_COLOR_VALUE, 0, MAX_TG_COLOR_VALUE}, // yellow -			{0, MAX_TG_COLOR_VALUE, 0}, // blue +			{MAX_TG_COLOR_VALUE, MAX_TG_COLOR_VALUE / 4, 0}, // orange +			{MAX_TG_COLOR_VALUE, MAX_TG_COLOR_VALUE, 0}, // yellow +			{0, MAX_TG_COLOR_VALUE, 0}, // green +			{0, 0, MAX_TG_COLOR_VALUE}, // blue  			{MAX_TG_COLOR_VALUE / 2, 0, MAX_TG_COLOR_VALUE / 2}, // purple -			{0, 0, MAX_TG_COLOR_VALUE}, // green -			{MAX_TG_COLOR_VALUE, MAX_TG_COLOR_VALUE * 2 / 3, 0}, // orange  	};  	struct pipe_ctx *top_pipe = pipe_ctx; @@ -2280,14 +2272,11 @@ void dcn20_update_mpcc(struct dc *dc, struct pipe_ctx *pipe_ctx)  	// input to MPCC is always RGB, by default leave black_color at 0  	if (dc->debug.visual_confirm == VISUAL_CONFIRM_HDR) { -		hws->funcs.get_hdr_visual_confirm_color( -				pipe_ctx, &blnd_cfg.black_color); +		hws->funcs.get_hdr_visual_confirm_color(pipe_ctx, &blnd_cfg.black_color);  	} else if (dc->debug.visual_confirm == VISUAL_CONFIRM_SURFACE) { -		hws->funcs.get_surface_visual_confirm_color( -				pipe_ctx, &blnd_cfg.black_color); +		hws->funcs.get_surface_visual_confirm_color(pipe_ctx, &blnd_cfg.black_color);  	} else if (dc->debug.visual_confirm == VISUAL_CONFIRM_MPCTREE) { -		dcn20_get_mpctree_visual_confirm_color( -				pipe_ctx, &blnd_cfg.black_color); +		dcn20_get_mpctree_visual_confirm_color(pipe_ctx, &blnd_cfg.black_color);  	}  	if (per_pixel_alpha) diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_stream_encoder.h b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_stream_encoder.h index d2a805bd4573..9a881e639709 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_stream_encoder.h +++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_stream_encoder.h @@ -83,6 +83,8 @@  	SE_SF(DIG0_HDMI_METADATA_PACKET_CONTROL, HDMI_METADATA_PACKET_LINE, mask_sh),\  	SE_SF(DIG0_DIG_FE_CNTL, DOLBY_VISION_EN, mask_sh),\  	SE_SF(DP0_DP_PIXEL_FORMAT, DP_PIXEL_COMBINE, mask_sh),\ +	SE_SF(DP0_DP_SEC_CNTL1, DP_SEC_GSP5_LINE_REFERENCE, mask_sh),\ +	SE_SF(DP0_DP_SEC_CNTL5, DP_SEC_GSP5_LINE_NUM, mask_sh),\  	SE_SF(DP0_DP_SEC_FRAMING4, DP_SST_SDP_SPLITTING, mask_sh)  void dcn20_stream_encoder_construct( diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.h b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.h index b7efa777ec73..e44a37491c1e 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.h +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.h @@ -32,5 +32,6 @@ struct dccg *dccg21_create(  	const struct dccg_shift *dccg_shift,  	const struct dccg_mask *dccg_mask); +void dccg21_update_dpp_dto(struct dccg *dccg, int dpp_inst, int req_dppclk);  #endif /* __DCN21_DCCG_H__ */ diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dio_link_encoder.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dio_link_encoder.c index 2ae159e2dd6e..46ea39f5ef8d 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dio_link_encoder.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dio_link_encoder.c @@ -51,7 +51,7 @@  	(enc10->link_regs->index) -static bool dcn30_link_encoder_validate_output_with_stream( +bool dcn30_link_encoder_validate_output_with_stream(  	struct link_encoder *enc,  	const struct dc_stream_state *stream)  { diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dio_link_encoder.h b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dio_link_encoder.h index 2fbf879cd327..f2d90f2b8bf1 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dio_link_encoder.h +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dio_link_encoder.h @@ -78,4 +78,8 @@ void dcn30_link_encoder_construct(  void enc3_hw_init(struct link_encoder *enc); +bool dcn30_link_encoder_validate_output_with_stream( +	struct link_encoder *enc, +	const struct dc_stream_state *stream); +  #endif /* __DC_LINK_ENCODER__DCN30_H__ */ diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c index 283995ab9eeb..3deb3fb1724d 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c @@ -668,7 +668,7 @@ void dcn30_update_info_frame(struct pipe_ctx *pipe_ctx)  	is_hdmi_tmds = dc_is_hdmi_tmds_signal(pipe_ctx->stream->signal);  	is_dp = dc_is_dp_signal(pipe_ctx->stream->signal); -	if (!is_hdmi_tmds) +	if (!is_hdmi_tmds && !is_dp)  		return;  	if (is_hdmi_tmds) diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_optc.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_optc.c index b1f228fc119a..3ba3991ee612 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_optc.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_optc.c @@ -350,7 +350,7 @@ void dcn30_timing_generator_init(struct optc *optc1)  	optc1->min_h_blank = 32;  	optc1->min_v_blank = 3;  	optc1->min_v_blank_interlace = 5; -	optc1->min_h_sync_width = 8; +	optc1->min_h_sync_width = 4;  	optc1->min_v_sync_width = 1;  } diff --git a/drivers/gpu/drm/amd/display/dc/inc/hw/timing_generator.h b/drivers/gpu/drm/amd/display/dc/inc/hw/timing_generator.h index 12d5718caea8..f7632fe25976 100644 --- a/drivers/gpu/drm/amd/display/dc/inc/hw/timing_generator.h +++ b/drivers/gpu/drm/amd/display/dc/inc/hw/timing_generator.h @@ -271,7 +271,7 @@ struct timing_generator_funcs {  			struct dc_crtc_timing *hw_crtc_timing);  	void (*set_vtg_params)(struct timing_generator *optc, -			const struct dc_crtc_timing *dc_crtc_timing); +			const struct dc_crtc_timing *dc_crtc_timing, bool program_fp2);  	void (*set_dsc_config)(struct timing_generator *optc,  			       enum optc_dsc_mode dsc_mode, diff --git a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h index b20a39f488ae..f512bda96917 100644 --- a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h +++ b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h @@ -47,10 +47,10 @@  /* Firmware versioning. */  #ifdef DMUB_EXPOSE_VERSION -#define DMUB_FW_VERSION_GIT_HASH 0x931573111 +#define DMUB_FW_VERSION_GIT_HASH 0xa18e25995  #define DMUB_FW_VERSION_MAJOR 0  #define DMUB_FW_VERSION_MINOR 0 -#define DMUB_FW_VERSION_REVISION 45 +#define DMUB_FW_VERSION_REVISION 46  #define DMUB_FW_VERSION_TEST 0  #define DMUB_FW_VERSION_VBIOS 0  #define DMUB_FW_VERSION_HOTFIX 0 @@ -514,12 +514,20 @@ enum dp_aux_request_action {  enum aux_return_code_type {  	AUX_RET_SUCCESS = 0, +	AUX_RET_ERROR_UNKNOWN, +	AUX_RET_ERROR_INVALID_REPLY,  	AUX_RET_ERROR_TIMEOUT, -	AUX_RET_ERROR_NO_DATA, +	AUX_RET_ERROR_HPD_DISCON, +	AUX_RET_ERROR_ENGINE_ACQUIRE,  	AUX_RET_ERROR_INVALID_OPERATION,  	AUX_RET_ERROR_PROTOCOL_ERROR,  }; +enum aux_channel_type { +	AUX_CHANNEL_LEGACY_DDC, +	AUX_CHANNEL_DPIA +}; +  /* DP AUX command */  struct aux_transaction_parameters {  	uint8_t is_i2c_over_aux; @@ -532,9 +540,10 @@ struct aux_transaction_parameters {  struct dmub_cmd_dp_aux_control_data {  	uint32_t handle; -	uint8_t port_index; +	uint8_t instance;  	uint8_t sw_crc_enabled;  	uint16_t timeout; +	enum aux_channel_type type;  	struct aux_transaction_parameters dpaux;  }; @@ -558,7 +567,7 @@ struct aux_reply_data {  struct aux_reply_control_data {  	uint32_t handle; -	uint8_t phy_port_index; +	uint8_t instance;  	uint8_t result;  	uint16_t pad;  }; @@ -581,7 +590,7 @@ enum dp_hpd_status {  };  struct dp_hpd_data { -	uint8_t phy_port_index; +	uint8_t instance;  	uint8_t hpd_type;  	uint8_t hpd_status;  	uint8_t pad; @@ -732,27 +741,30 @@ enum dmub_cmd_abm_type {  struct abm_config_table {  	/* Parameters for crgb conversion */  	uint16_t crgb_thresh[NUM_POWER_FN_SEGS];                 // 0B -	uint16_t crgb_offset[NUM_POWER_FN_SEGS];                 // 15B -	uint16_t crgb_slope[NUM_POWER_FN_SEGS];                  // 31B +	uint16_t crgb_offset[NUM_POWER_FN_SEGS];                 // 16B +	uint16_t crgb_slope[NUM_POWER_FN_SEGS];                  // 32B  	/* Parameters for custom curve */ -	uint16_t backlight_thresholds[NUM_BL_CURVE_SEGS];        // 47B -	uint16_t backlight_offsets[NUM_BL_CURVE_SEGS];           // 79B - -	uint16_t ambient_thresholds_lux[NUM_AMBI_LEVEL];         // 111B -	uint16_t min_abm_backlight;                              // 121B - -	uint8_t min_reduction[NUM_AMBI_LEVEL][NUM_AGGR_LEVEL];   // 123B -	uint8_t max_reduction[NUM_AMBI_LEVEL][NUM_AGGR_LEVEL];   // 143B -	uint8_t bright_pos_gain[NUM_AMBI_LEVEL][NUM_AGGR_LEVEL]; // 163B -	uint8_t dark_pos_gain[NUM_AMBI_LEVEL][NUM_AGGR_LEVEL];   // 183B -	uint8_t hybrid_factor[NUM_AGGR_LEVEL];                   // 203B -	uint8_t contrast_factor[NUM_AGGR_LEVEL];                 // 207B -	uint8_t deviation_gain[NUM_AGGR_LEVEL];                  // 211B -	uint8_t min_knee[NUM_AGGR_LEVEL];                        // 215B -	uint8_t max_knee[NUM_AGGR_LEVEL];                        // 219B -	uint8_t iir_curve[NUM_AMBI_LEVEL];                       // 223B -	uint8_t pad3[3];                                         // 228B +	uint16_t backlight_thresholds[NUM_BL_CURVE_SEGS];        // 48B +	uint16_t backlight_offsets[NUM_BL_CURVE_SEGS];           // 78B + +	uint16_t ambient_thresholds_lux[NUM_AMBI_LEVEL];         // 112B +	uint16_t min_abm_backlight;                              // 122B + +	uint8_t min_reduction[NUM_AMBI_LEVEL][NUM_AGGR_LEVEL];   // 124B +	uint8_t max_reduction[NUM_AMBI_LEVEL][NUM_AGGR_LEVEL];   // 144B +	uint8_t bright_pos_gain[NUM_AMBI_LEVEL][NUM_AGGR_LEVEL]; // 164B +	uint8_t dark_pos_gain[NUM_AMBI_LEVEL][NUM_AGGR_LEVEL];   // 184B +	uint8_t hybrid_factor[NUM_AGGR_LEVEL];                   // 204B +	uint8_t contrast_factor[NUM_AGGR_LEVEL];                 // 208B +	uint8_t deviation_gain[NUM_AGGR_LEVEL];                  // 212B +	uint8_t min_knee[NUM_AGGR_LEVEL];                        // 216B +	uint8_t max_knee[NUM_AGGR_LEVEL];                        // 220B +	uint8_t iir_curve[NUM_AMBI_LEVEL];                       // 224B +	uint8_t pad3[3];                                         // 229B + +	uint16_t blRampReduction[NUM_AGGR_LEVEL];                // 232B +	uint16_t blRampStart[NUM_AGGR_LEVEL];                    // 240B  };  struct dmub_cmd_abm_set_pipe_data { diff --git a/drivers/gpu/drm/amd/display/modules/color/color_gamma.c b/drivers/gpu/drm/amd/display/modules/color/color_gamma.c index eced40a2fce4..5c67e12b2e55 100644 --- a/drivers/gpu/drm/amd/display/modules/color/color_gamma.c +++ b/drivers/gpu/drm/amd/display/modules/color/color_gamma.c @@ -30,6 +30,14 @@  #include "opp.h"  #include "color_gamma.h" +/* When calculating LUT values the first region and at least one subsequent + * region are calculated with full precision. These defines are a demarcation + * of where the second region starts and ends. + * These are hardcoded values to avoid recalculating them in loops. + */ +#define PRECISE_LUT_REGION_START 224 +#define PRECISE_LUT_REGION_END 239 +  static struct hw_x_point coordinates_x[MAX_HW_POINTS + 2];  // these are helpers for calculations to reduce stack usage @@ -346,7 +354,13 @@ static struct fixed31_32 translate_from_linear_space(  					dc_fixpt_recip(args->gamma));  		}  		scratch_1 = dc_fixpt_add(one, args->a3); -		if (cal_buffer->buffer_index < 16) +		/* In the first region (first 16 points) and in the +		 * region delimited by START/END we calculate with +		 * full precision to avoid error accumulation.  +		 */ +		if ((cal_buffer->buffer_index >= PRECISE_LUT_REGION_START && +			cal_buffer->buffer_index <= PRECISE_LUT_REGION_END) || +			(cal_buffer->buffer_index < 16))  			scratch_2 = dc_fixpt_pow(args->arg,  					dc_fixpt_recip(args->gamma));  		else @@ -397,9 +411,7 @@ static struct fixed31_32 translate_from_linear_space_long(  					dc_fixpt_recip(args->gamma))),  					args->a2);  	else -		return dc_fixpt_mul( -			args->arg, -			args->a1); +		return dc_fixpt_mul(args->arg, args->a1);  }  static struct fixed31_32 calculate_gamma22(struct fixed31_32 arg, bool use_eetf, struct calculate_buffer *cal_buffer) @@ -717,7 +729,6 @@ static struct fixed31_32 calculate_mapped_value(  		BREAK_TO_DEBUGGER();  		result = dc_fixpt_zero;  	} else { -		BREAK_TO_DEBUGGER();  		result = dc_fixpt_one;  	} @@ -976,6 +987,7 @@ static bool build_freesync_hdr(struct pwl_float_data_ex *rgb_regamma,  		cal_buffer->buffer_index = 0; // see var definition for more info  	rgb += 32; // first 32 points have problems with fixed point, too small  	coord_x += 32; +  	for (i = 32; i <= hw_points_num; i++) {  		if (!is_clipped) {  			if (use_eetf) { diff --git a/drivers/gpu/drm/amd/include/atomfirmware.h b/drivers/gpu/drm/amd/include/atomfirmware.h index c38635992101..3cb8d4c5c1a3 100644 --- a/drivers/gpu/drm/amd/include/atomfirmware.h +++ b/drivers/gpu/drm/amd/include/atomfirmware.h @@ -499,6 +499,7 @@ enum atombios_firmware_capability  	ATOM_FIRMWARE_CAP_HWEMU_UMC_CFG = 0x00000100,  	ATOM_FIRMWARE_CAP_SRAM_ECC      = 0x00000200,  	ATOM_FIRMWARE_CAP_ENABLE_2STAGE_BIST_TRAINING  = 0x00000400, +	ATOM_FIRMWARE_CAP_ENABLE_2ND_USB20PORT = 0x0008000,  };  enum atom_cooling_solution_id{ diff --git a/drivers/gpu/drm/amd/pm/inc/amdgpu_smu.h b/drivers/gpu/drm/amd/pm/inc/amdgpu_smu.h index 89be49a43500..4bdbcce7092d 100644 --- a/drivers/gpu/drm/amd/pm/inc/amdgpu_smu.h +++ b/drivers/gpu/drm/amd/pm/inc/amdgpu_smu.h @@ -227,6 +227,7 @@ struct smu_bios_boot_up_values  	uint32_t			content_revision;  	uint32_t			fclk;  	uint32_t			lclk; +	uint32_t			firmware_caps;  };  enum smu_table_id diff --git a/drivers/gpu/drm/amd/pm/inc/smu_types.h b/drivers/gpu/drm/amd/pm/inc/smu_types.h index 4a6d1381df16..720d15612fe1 100644 --- a/drivers/gpu/drm/amd/pm/inc/smu_types.h +++ b/drivers/gpu/drm/amd/pm/inc/smu_types.h @@ -178,7 +178,7 @@  	__SMU_DUMMY_MAP(SET_DRIVER_DUMMY_TABLE_DRAM_ADDR_LOW), \  	__SMU_DUMMY_MAP(GET_UMC_FW_WA), \  	__SMU_DUMMY_MAP(Mode1Reset), \ -	__SMU_DUMMY_MAP(Spare),                          \ +	__SMU_DUMMY_MAP(RlcPowerNotify),                 \  	__SMU_DUMMY_MAP(SetHardMinIspiclkByFreq),        \  	__SMU_DUMMY_MAP(SetHardMinIspxclkByFreq),        \  	__SMU_DUMMY_MAP(SetSoftMinSocclkByFreq),         \ @@ -209,6 +209,8 @@         __SMU_DUMMY_MAP(SetSoftMinCclk),                     \         __SMU_DUMMY_MAP(SetSoftMaxCclk),                     \  	__SMU_DUMMY_MAP(SetGpoFeaturePMask),             \ +	__SMU_DUMMY_MAP(DisallowGpo),                    \ +	__SMU_DUMMY_MAP(Enable2ndUSB20Port),             \  #undef __SMU_DUMMY_MAP  #define __SMU_DUMMY_MAP(type)	SMU_MSG_##type diff --git a/drivers/gpu/drm/amd/pm/inc/smu_v11_0_7_ppsmc.h b/drivers/gpu/drm/amd/pm/inc/smu_v11_0_7_ppsmc.h index 35dd6072cc45..d2e10a724560 100644 --- a/drivers/gpu/drm/amd/pm/inc/smu_v11_0_7_ppsmc.h +++ b/drivers/gpu/drm/amd/pm/inc/smu_v11_0_7_ppsmc.h @@ -134,6 +134,10 @@  #define PPSMC_MSG_SetGpoFeaturePMask             0x45  #define PPSMC_MSG_SetSMBUSInterrupt              0x46 -#define PPSMC_Message_Count                      0x47 +#define PPSMC_MSG_DisallowGpo                    0x56 + +#define PPSMC_MSG_Enable2ndUSB20Port             0x57 + +#define PPSMC_Message_Count                      0x58  #endif diff --git a/drivers/gpu/drm/amd/pm/inc/smu_v11_5_ppsmc.h b/drivers/gpu/drm/amd/pm/inc/smu_v11_5_ppsmc.h index 7e69b3bd311b..55d7892e4e0e 100644 --- a/drivers/gpu/drm/amd/pm/inc/smu_v11_5_ppsmc.h +++ b/drivers/gpu/drm/amd/pm/inc/smu_v11_5_ppsmc.h @@ -41,7 +41,7 @@  #define PPSMC_MSG_PowerUpIspByTile                     0x7  #define PPSMC_MSG_PowerDownVcn                         0x8 // VCN is power gated by default  #define PPSMC_MSG_PowerUpVcn                           0x9 -#define PPSMC_MSG_spare                                0xA +#define PPSMC_MSG_RlcPowerNotify                       0xA  #define PPSMC_MSG_SetHardMinVcn                        0xB // For wireless display  #define PPSMC_MSG_SetSoftMinGfxclk                     0xC //Sets SoftMin for GFXCLK. Arg is in MHz  #define PPSMC_MSG_ActiveProcessNotify                  0xD diff --git a/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c b/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c index cf999b7a2164..8b867a6d52b5 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c +++ b/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c @@ -847,12 +847,10 @@ static int smu_sw_init(void *handle)  	smu->smu_dpm.dpm_level = AMD_DPM_FORCED_LEVEL_AUTO;  	smu->smu_dpm.requested_dpm_level = AMD_DPM_FORCED_LEVEL_AUTO; -	if (!amdgpu_sriov_vf(adev) || (adev->asic_type != CHIP_NAVI12)) { -		ret = smu_init_microcode(smu); -		if (ret) { -			dev_err(adev->dev, "Failed to load smu firmware!\n"); -			return ret; -		} +	ret = smu_init_microcode(smu); +	if (ret) { +		dev_err(adev->dev, "Failed to load smu firmware!\n"); +		return ret;  	}  	ret = smu_smc_table_sw_init(smu); diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu11/sienna_cichlid_ppt.c b/drivers/gpu/drm/amd/pm/swsmu/smu11/sienna_cichlid_ppt.c index 3f20f77afdd2..9608745d732f 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/smu11/sienna_cichlid_ppt.c +++ b/drivers/gpu/drm/amd/pm/swsmu/smu11/sienna_cichlid_ppt.c @@ -128,6 +128,8 @@ static struct cmn2asic_msg_mapping sienna_cichlid_message_map[SMU_MSG_MAX_COUNT]  	MSG_MAP(Mode1Reset,                     PPSMC_MSG_Mode1Reset,		       0),  	MSG_MAP(SetMGpuFanBoostLimitRpm,	PPSMC_MSG_SetMGpuFanBoostLimitRpm,     0),  	MSG_MAP(SetGpoFeaturePMask,		PPSMC_MSG_SetGpoFeaturePMask,          0), +	MSG_MAP(DisallowGpo,			PPSMC_MSG_DisallowGpo,                 0), +	MSG_MAP(Enable2ndUSB20Port,		PPSMC_MSG_Enable2ndUSB20Port,          0),  };  static struct cmn2asic_mapping sienna_cichlid_clk_map[SMU_CLK_COUNT] = { @@ -302,6 +304,9 @@ static int sienna_cichlid_check_powerplay_table(struct smu_context *smu)  		table_context->power_play_table;  	struct smu_baco_context *smu_baco = &smu->smu_baco; +	if (powerplay_table->platform_caps & SMU_11_0_7_PP_PLATFORM_CAP_HARDWAREDC) +		smu->dc_controlled_by_gpio = true; +  	if (powerplay_table->platform_caps & SMU_11_0_7_PP_PLATFORM_CAP_BACO ||  	    powerplay_table->platform_caps & SMU_11_0_7_PP_PLATFORM_CAP_MACO)  		smu_baco->platform_support = true; @@ -377,7 +382,7 @@ static int sienna_cichlid_tables_init(struct smu_context *smu)  		       PAGE_SIZE, AMDGPU_GEM_DOMAIN_VRAM);  	SMU_TABLE_INIT(tables, SMU_TABLE_WATERMARKS, sizeof(Watermarks_t),  		       PAGE_SIZE, AMDGPU_GEM_DOMAIN_VRAM); -	SMU_TABLE_INIT(tables, SMU_TABLE_SMU_METRICS, sizeof(SmuMetrics_t), +	SMU_TABLE_INIT(tables, SMU_TABLE_SMU_METRICS, sizeof(SmuMetricsExternal_t),  		       PAGE_SIZE, AMDGPU_GEM_DOMAIN_VRAM);  	SMU_TABLE_INIT(tables, SMU_TABLE_I2C_COMMANDS, sizeof(SwI2cRequest_t),  		       PAGE_SIZE, AMDGPU_GEM_DOMAIN_VRAM); @@ -386,10 +391,10 @@ static int sienna_cichlid_tables_init(struct smu_context *smu)  	SMU_TABLE_INIT(tables, SMU_TABLE_PMSTATUSLOG, SMU11_TOOL_SIZE,  		       PAGE_SIZE, AMDGPU_GEM_DOMAIN_VRAM);  	SMU_TABLE_INIT(tables, SMU_TABLE_ACTIVITY_MONITOR_COEFF, -		       sizeof(DpmActivityMonitorCoeffInt_t), PAGE_SIZE, +		       sizeof(DpmActivityMonitorCoeffIntExternal_t), PAGE_SIZE,  	               AMDGPU_GEM_DOMAIN_VRAM); -	smu_table->metrics_table = kzalloc(sizeof(SmuMetrics_t), GFP_KERNEL); +	smu_table->metrics_table = kzalloc(sizeof(SmuMetricsExternal_t), GFP_KERNEL);  	if (!smu_table->metrics_table)  		goto err0_out;  	smu_table->metrics_time = 0; @@ -418,7 +423,8 @@ static int sienna_cichlid_get_smu_metrics_data(struct smu_context *smu,  					       uint32_t *value)  {  	struct smu_table_context *smu_table= &smu->smu_table; -	SmuMetrics_t *metrics = (SmuMetrics_t *)smu_table->metrics_table; +	SmuMetrics_t *metrics = +		&(((SmuMetricsExternal_t *)(smu_table->metrics_table))->SmuMetrics);  	int ret = 0;  	mutex_lock(&smu->metrics_lock); @@ -1065,12 +1071,18 @@ static int sienna_cichlid_populate_umd_state_clk(struct smu_context *smu)  	pstate_table->gfxclk_pstate.min = gfx_table->min;  	pstate_table->gfxclk_pstate.peak = gfx_table->max; +	if (gfx_table->max >= SIENNA_CICHLID_UMD_PSTATE_PROFILING_GFXCLK) +		pstate_table->gfxclk_pstate.standard = SIENNA_CICHLID_UMD_PSTATE_PROFILING_GFXCLK;  	pstate_table->uclk_pstate.min = mem_table->min;  	pstate_table->uclk_pstate.peak = mem_table->max; +	if (mem_table->max >= SIENNA_CICHLID_UMD_PSTATE_PROFILING_MEMCLK) +		pstate_table->uclk_pstate.standard = SIENNA_CICHLID_UMD_PSTATE_PROFILING_MEMCLK;  	pstate_table->socclk_pstate.min = soc_table->min;  	pstate_table->socclk_pstate.peak = soc_table->max; +	if (soc_table->max >= SIENNA_CICHLID_UMD_PSTATE_PROFILING_SOCCLK) +		pstate_table->socclk_pstate.standard = SIENNA_CICHLID_UMD_PSTATE_PROFILING_SOCCLK;  	return 0;  } @@ -1156,7 +1168,9 @@ static int sienna_cichlid_get_fan_parameters(struct smu_context *smu)  static int sienna_cichlid_get_power_profile_mode(struct smu_context *smu, char *buf)  { -	DpmActivityMonitorCoeffInt_t activity_monitor; +	DpmActivityMonitorCoeffIntExternal_t activity_monitor_external; +	DpmActivityMonitorCoeffInt_t *activity_monitor = +		&(activity_monitor_external.DpmActivityMonitorCoeffInt);  	uint32_t i, size = 0;  	int16_t workload_type = 0;  	static const char *profile_name[] = { @@ -1198,7 +1212,7 @@ static int sienna_cichlid_get_power_profile_mode(struct smu_context *smu, char *  		result = smu_cmn_update_table(smu,  					  SMU_TABLE_ACTIVITY_MONITOR_COEFF, workload_type, -					  (void *)(&activity_monitor), false); +					  (void *)(&activity_monitor_external), false);  		if (result) {  			dev_err(smu->adev->dev, "[%s] Failed to get activity monitor!", __func__);  			return result; @@ -1211,43 +1225,43 @@ static int sienna_cichlid_get_power_profile_mode(struct smu_context *smu, char *  			" ",  			0,  			"GFXCLK", -			activity_monitor.Gfx_FPS, -			activity_monitor.Gfx_MinFreqStep, -			activity_monitor.Gfx_MinActiveFreqType, -			activity_monitor.Gfx_MinActiveFreq, -			activity_monitor.Gfx_BoosterFreqType, -			activity_monitor.Gfx_BoosterFreq, -			activity_monitor.Gfx_PD_Data_limit_c, -			activity_monitor.Gfx_PD_Data_error_coeff, -			activity_monitor.Gfx_PD_Data_error_rate_coeff); +			activity_monitor->Gfx_FPS, +			activity_monitor->Gfx_MinFreqStep, +			activity_monitor->Gfx_MinActiveFreqType, +			activity_monitor->Gfx_MinActiveFreq, +			activity_monitor->Gfx_BoosterFreqType, +			activity_monitor->Gfx_BoosterFreq, +			activity_monitor->Gfx_PD_Data_limit_c, +			activity_monitor->Gfx_PD_Data_error_coeff, +			activity_monitor->Gfx_PD_Data_error_rate_coeff);  		size += sprintf(buf + size, "%19s %d(%13s) %7d %7d %7d %7d %7d %7d %7d %7d %7d\n",  			" ",  			1,  			"SOCCLK", -			activity_monitor.Fclk_FPS, -			activity_monitor.Fclk_MinFreqStep, -			activity_monitor.Fclk_MinActiveFreqType, -			activity_monitor.Fclk_MinActiveFreq, -			activity_monitor.Fclk_BoosterFreqType, -			activity_monitor.Fclk_BoosterFreq, -			activity_monitor.Fclk_PD_Data_limit_c, -			activity_monitor.Fclk_PD_Data_error_coeff, -			activity_monitor.Fclk_PD_Data_error_rate_coeff); +			activity_monitor->Fclk_FPS, +			activity_monitor->Fclk_MinFreqStep, +			activity_monitor->Fclk_MinActiveFreqType, +			activity_monitor->Fclk_MinActiveFreq, +			activity_monitor->Fclk_BoosterFreqType, +			activity_monitor->Fclk_BoosterFreq, +			activity_monitor->Fclk_PD_Data_limit_c, +			activity_monitor->Fclk_PD_Data_error_coeff, +			activity_monitor->Fclk_PD_Data_error_rate_coeff);  		size += sprintf(buf + size, "%19s %d(%13s) %7d %7d %7d %7d %7d %7d %7d %7d %7d\n",  			" ",  			2,  			"MEMLK", -			activity_monitor.Mem_FPS, -			activity_monitor.Mem_MinFreqStep, -			activity_monitor.Mem_MinActiveFreqType, -			activity_monitor.Mem_MinActiveFreq, -			activity_monitor.Mem_BoosterFreqType, -			activity_monitor.Mem_BoosterFreq, -			activity_monitor.Mem_PD_Data_limit_c, -			activity_monitor.Mem_PD_Data_error_coeff, -			activity_monitor.Mem_PD_Data_error_rate_coeff); +			activity_monitor->Mem_FPS, +			activity_monitor->Mem_MinFreqStep, +			activity_monitor->Mem_MinActiveFreqType, +			activity_monitor->Mem_MinActiveFreq, +			activity_monitor->Mem_BoosterFreqType, +			activity_monitor->Mem_BoosterFreq, +			activity_monitor->Mem_PD_Data_limit_c, +			activity_monitor->Mem_PD_Data_error_coeff, +			activity_monitor->Mem_PD_Data_error_rate_coeff);  	}  	return size; @@ -1255,7 +1269,10 @@ static int sienna_cichlid_get_power_profile_mode(struct smu_context *smu, char *  static int sienna_cichlid_set_power_profile_mode(struct smu_context *smu, long *input, uint32_t size)  { -	DpmActivityMonitorCoeffInt_t activity_monitor; + +	DpmActivityMonitorCoeffIntExternal_t activity_monitor_external; +	DpmActivityMonitorCoeffInt_t *activity_monitor = +		&(activity_monitor_external.DpmActivityMonitorCoeffInt);  	int workload_type, ret = 0;  	smu->power_profile_mode = input[size]; @@ -1269,7 +1286,7 @@ static int sienna_cichlid_set_power_profile_mode(struct smu_context *smu, long *  		ret = smu_cmn_update_table(smu,  				       SMU_TABLE_ACTIVITY_MONITOR_COEFF, WORKLOAD_PPLIB_CUSTOM_BIT, -				       (void *)(&activity_monitor), false); +				       (void *)(&activity_monitor_external), false);  		if (ret) {  			dev_err(smu->adev->dev, "[%s] Failed to get activity monitor!", __func__);  			return ret; @@ -1277,43 +1294,43 @@ static int sienna_cichlid_set_power_profile_mode(struct smu_context *smu, long *  		switch (input[0]) {  		case 0: /* Gfxclk */ -			activity_monitor.Gfx_FPS = input[1]; -			activity_monitor.Gfx_MinFreqStep = input[2]; -			activity_monitor.Gfx_MinActiveFreqType = input[3]; -			activity_monitor.Gfx_MinActiveFreq = input[4]; -			activity_monitor.Gfx_BoosterFreqType = input[5]; -			activity_monitor.Gfx_BoosterFreq = input[6]; -			activity_monitor.Gfx_PD_Data_limit_c = input[7]; -			activity_monitor.Gfx_PD_Data_error_coeff = input[8]; -			activity_monitor.Gfx_PD_Data_error_rate_coeff = input[9]; +			activity_monitor->Gfx_FPS = input[1]; +			activity_monitor->Gfx_MinFreqStep = input[2]; +			activity_monitor->Gfx_MinActiveFreqType = input[3]; +			activity_monitor->Gfx_MinActiveFreq = input[4]; +			activity_monitor->Gfx_BoosterFreqType = input[5]; +			activity_monitor->Gfx_BoosterFreq = input[6]; +			activity_monitor->Gfx_PD_Data_limit_c = input[7]; +			activity_monitor->Gfx_PD_Data_error_coeff = input[8]; +			activity_monitor->Gfx_PD_Data_error_rate_coeff = input[9];  			break;  		case 1: /* Socclk */ -			activity_monitor.Fclk_FPS = input[1]; -			activity_monitor.Fclk_MinFreqStep = input[2]; -			activity_monitor.Fclk_MinActiveFreqType = input[3]; -			activity_monitor.Fclk_MinActiveFreq = input[4]; -			activity_monitor.Fclk_BoosterFreqType = input[5]; -			activity_monitor.Fclk_BoosterFreq = input[6]; -			activity_monitor.Fclk_PD_Data_limit_c = input[7]; -			activity_monitor.Fclk_PD_Data_error_coeff = input[8]; -			activity_monitor.Fclk_PD_Data_error_rate_coeff = input[9]; +			activity_monitor->Fclk_FPS = input[1]; +			activity_monitor->Fclk_MinFreqStep = input[2]; +			activity_monitor->Fclk_MinActiveFreqType = input[3]; +			activity_monitor->Fclk_MinActiveFreq = input[4]; +			activity_monitor->Fclk_BoosterFreqType = input[5]; +			activity_monitor->Fclk_BoosterFreq = input[6]; +			activity_monitor->Fclk_PD_Data_limit_c = input[7]; +			activity_monitor->Fclk_PD_Data_error_coeff = input[8]; +			activity_monitor->Fclk_PD_Data_error_rate_coeff = input[9];  			break;  		case 2: /* Memlk */ -			activity_monitor.Mem_FPS = input[1]; -			activity_monitor.Mem_MinFreqStep = input[2]; -			activity_monitor.Mem_MinActiveFreqType = input[3]; -			activity_monitor.Mem_MinActiveFreq = input[4]; -			activity_monitor.Mem_BoosterFreqType = input[5]; -			activity_monitor.Mem_BoosterFreq = input[6]; -			activity_monitor.Mem_PD_Data_limit_c = input[7]; -			activity_monitor.Mem_PD_Data_error_coeff = input[8]; -			activity_monitor.Mem_PD_Data_error_rate_coeff = input[9]; +			activity_monitor->Mem_FPS = input[1]; +			activity_monitor->Mem_MinFreqStep = input[2]; +			activity_monitor->Mem_MinActiveFreqType = input[3]; +			activity_monitor->Mem_MinActiveFreq = input[4]; +			activity_monitor->Mem_BoosterFreqType = input[5]; +			activity_monitor->Mem_BoosterFreq = input[6]; +			activity_monitor->Mem_PD_Data_limit_c = input[7]; +			activity_monitor->Mem_PD_Data_error_coeff = input[8]; +			activity_monitor->Mem_PD_Data_error_rate_coeff = input[9];  			break;  		}  		ret = smu_cmn_update_table(smu,  				       SMU_TABLE_ACTIVITY_MONITOR_COEFF, WORKLOAD_PPLIB_CUSTOM_BIT, -				       (void *)(&activity_monitor), true); +				       (void *)(&activity_monitor_external), true);  		if (ret) {  			dev_err(smu->adev->dev, "[%s] Failed to set activity monitor!", __func__);  			return ret; @@ -2582,52 +2599,54 @@ static ssize_t sienna_cichlid_get_gpu_metrics(struct smu_context *smu,  	struct smu_table_context *smu_table = &smu->smu_table;  	struct gpu_metrics_v1_0 *gpu_metrics =  		(struct gpu_metrics_v1_0 *)smu_table->gpu_metrics_table; -	SmuMetrics_t metrics; +	SmuMetricsExternal_t metrics_external; +	SmuMetrics_t *metrics = +		&(metrics_external.SmuMetrics);  	int ret = 0;  	ret = smu_cmn_get_metrics_table(smu, -					&metrics, +					&metrics_external,  					true);  	if (ret)  		return ret;  	smu_v11_0_init_gpu_metrics_v1_0(gpu_metrics); -	gpu_metrics->temperature_edge = metrics.TemperatureEdge; -	gpu_metrics->temperature_hotspot = metrics.TemperatureHotspot; -	gpu_metrics->temperature_mem = metrics.TemperatureMem; -	gpu_metrics->temperature_vrgfx = metrics.TemperatureVrGfx; -	gpu_metrics->temperature_vrsoc = metrics.TemperatureVrSoc; -	gpu_metrics->temperature_vrmem = metrics.TemperatureVrMem0; +	gpu_metrics->temperature_edge = metrics->TemperatureEdge; +	gpu_metrics->temperature_hotspot = metrics->TemperatureHotspot; +	gpu_metrics->temperature_mem = metrics->TemperatureMem; +	gpu_metrics->temperature_vrgfx = metrics->TemperatureVrGfx; +	gpu_metrics->temperature_vrsoc = metrics->TemperatureVrSoc; +	gpu_metrics->temperature_vrmem = metrics->TemperatureVrMem0; -	gpu_metrics->average_gfx_activity = metrics.AverageGfxActivity; -	gpu_metrics->average_umc_activity = metrics.AverageUclkActivity; -	gpu_metrics->average_mm_activity = metrics.VcnActivityPercentage; +	gpu_metrics->average_gfx_activity = metrics->AverageGfxActivity; +	gpu_metrics->average_umc_activity = metrics->AverageUclkActivity; +	gpu_metrics->average_mm_activity = metrics->VcnActivityPercentage; -	gpu_metrics->average_socket_power = metrics.AverageSocketPower; -	gpu_metrics->energy_accumulator = metrics.EnergyAccumulator; +	gpu_metrics->average_socket_power = metrics->AverageSocketPower; +	gpu_metrics->energy_accumulator = metrics->EnergyAccumulator; -	if (metrics.AverageGfxActivity <= SMU_11_0_7_GFX_BUSY_THRESHOLD) -		gpu_metrics->average_gfxclk_frequency = metrics.AverageGfxclkFrequencyPostDs; +	if (metrics->AverageGfxActivity <= SMU_11_0_7_GFX_BUSY_THRESHOLD) +		gpu_metrics->average_gfxclk_frequency = metrics->AverageGfxclkFrequencyPostDs;  	else -		gpu_metrics->average_gfxclk_frequency = metrics.AverageGfxclkFrequencyPreDs; -	gpu_metrics->average_uclk_frequency = metrics.AverageUclkFrequencyPostDs; -	gpu_metrics->average_vclk0_frequency = metrics.AverageVclk0Frequency; -	gpu_metrics->average_dclk0_frequency = metrics.AverageDclk0Frequency; -	gpu_metrics->average_vclk1_frequency = metrics.AverageVclk1Frequency; -	gpu_metrics->average_dclk1_frequency = metrics.AverageDclk1Frequency; +		gpu_metrics->average_gfxclk_frequency = metrics->AverageGfxclkFrequencyPreDs; +	gpu_metrics->average_uclk_frequency = metrics->AverageUclkFrequencyPostDs; +	gpu_metrics->average_vclk0_frequency = metrics->AverageVclk0Frequency; +	gpu_metrics->average_dclk0_frequency = metrics->AverageDclk0Frequency; +	gpu_metrics->average_vclk1_frequency = metrics->AverageVclk1Frequency; +	gpu_metrics->average_dclk1_frequency = metrics->AverageDclk1Frequency; -	gpu_metrics->current_gfxclk = metrics.CurrClock[PPCLK_GFXCLK]; -	gpu_metrics->current_socclk = metrics.CurrClock[PPCLK_SOCCLK]; -	gpu_metrics->current_uclk = metrics.CurrClock[PPCLK_UCLK]; -	gpu_metrics->current_vclk0 = metrics.CurrClock[PPCLK_VCLK_0]; -	gpu_metrics->current_dclk0 = metrics.CurrClock[PPCLK_DCLK_0]; -	gpu_metrics->current_vclk1 = metrics.CurrClock[PPCLK_VCLK_1]; -	gpu_metrics->current_dclk1 = metrics.CurrClock[PPCLK_DCLK_1]; +	gpu_metrics->current_gfxclk = metrics->CurrClock[PPCLK_GFXCLK]; +	gpu_metrics->current_socclk = metrics->CurrClock[PPCLK_SOCCLK]; +	gpu_metrics->current_uclk = metrics->CurrClock[PPCLK_UCLK]; +	gpu_metrics->current_vclk0 = metrics->CurrClock[PPCLK_VCLK_0]; +	gpu_metrics->current_dclk0 = metrics->CurrClock[PPCLK_DCLK_0]; +	gpu_metrics->current_vclk1 = metrics->CurrClock[PPCLK_VCLK_1]; +	gpu_metrics->current_dclk1 = metrics->CurrClock[PPCLK_DCLK_1]; -	gpu_metrics->throttle_status = metrics.ThrottlerStatus; +	gpu_metrics->throttle_status = metrics->ThrottlerStatus; -	gpu_metrics->current_fan_speed = metrics.CurrFanSpeed; +	gpu_metrics->current_fan_speed = metrics->CurrFanSpeed;  	gpu_metrics->pcie_link_width =  			smu_v11_0_get_current_pcie_link_width(smu); @@ -2650,23 +2669,82 @@ static int sienna_cichlid_enable_mgpu_fan_boost(struct smu_context *smu)  static int sienna_cichlid_gpo_control(struct smu_context *smu,  				      bool enablement)  { +	uint32_t smu_version;  	int ret = 0; +  	if (smu_cmn_feature_is_supported(smu, SMU_FEATURE_DPM_GFX_GPO_BIT)) { -		if (enablement) -			ret = smu_cmn_send_smc_msg_with_param(smu, -							SMU_MSG_SetGpoFeaturePMask, -							GFX_GPO_PACE_MASK | GFX_GPO_DEM_MASK, -							NULL); -		else -			ret = smu_cmn_send_smc_msg_with_param(smu, -							SMU_MSG_SetGpoFeaturePMask, -							0, -							NULL); +		ret = smu_cmn_get_smc_version(smu, NULL, &smu_version); +		if (ret) +			return ret; + +		if (enablement) { +			if (smu_version < 0x003a2500) { +				ret = smu_cmn_send_smc_msg_with_param(smu, +								      SMU_MSG_SetGpoFeaturePMask, +								      GFX_GPO_PACE_MASK | GFX_GPO_DEM_MASK, +								      NULL); +			} else { +				ret = smu_cmn_send_smc_msg_with_param(smu, +								      SMU_MSG_DisallowGpo, +								      0, +								      NULL); +			} +		} else { +			if (smu_version < 0x003a2500) { +				ret = smu_cmn_send_smc_msg_with_param(smu, +								      SMU_MSG_SetGpoFeaturePMask, +								      0, +								      NULL); +			} else { +				ret = smu_cmn_send_smc_msg_with_param(smu, +								      SMU_MSG_DisallowGpo, +								      1, +								      NULL); +			} +		}  	}  	return ret;  } + +static int sienna_cichlid_notify_2nd_usb20_port(struct smu_context *smu) +{ +	uint32_t smu_version; +	int ret = 0; + +	ret = smu_cmn_get_smc_version(smu, NULL, &smu_version); +	if (ret) +		return ret; + +	/* +	 * Message SMU_MSG_Enable2ndUSB20Port is supported by 58.45 +	 * onwards PMFWs. +	 */ +	if (smu_version < 0x003A2D00) +		return 0; + +	return smu_cmn_send_smc_msg_with_param(smu, +					       SMU_MSG_Enable2ndUSB20Port, +					       smu->smu_table.boot_values.firmware_caps & ATOM_FIRMWARE_CAP_ENABLE_2ND_USB20PORT ? +					       1 : 0, +					       NULL); +} + +static int sienna_cichlid_system_features_control(struct smu_context *smu, +						  bool en) +{ +	int ret = 0; + +	if (en) { +		ret = sienna_cichlid_notify_2nd_usb20_port(smu); +		if (ret) +			return ret; +	} + +	return smu_v11_0_system_features_control(smu, en); +} +  static const struct pptable_funcs sienna_cichlid_ppt_funcs = {  	.get_allowed_feature_mask = sienna_cichlid_get_allowed_feature_mask,  	.set_default_dpm_table = sienna_cichlid_set_default_dpm_table, @@ -2707,7 +2785,7 @@ static const struct pptable_funcs sienna_cichlid_ppt_funcs = {  	.set_driver_table_location = smu_v11_0_set_driver_table_location,  	.set_tool_table_location = smu_v11_0_set_tool_table_location,  	.notify_memory_pool_location = smu_v11_0_notify_memory_pool_location, -	.system_features_control = smu_v11_0_system_features_control, +	.system_features_control = sienna_cichlid_system_features_control,  	.send_smc_msg_with_param = smu_cmn_send_smc_msg_with_param,  	.send_smc_msg = smu_cmn_send_smc_msg,  	.init_display_count = NULL, @@ -2740,6 +2818,7 @@ static const struct pptable_funcs sienna_cichlid_ppt_funcs = {  	.get_dpm_ultimate_freq = sienna_cichlid_get_dpm_ultimate_freq,  	.set_soft_freq_limited_range = smu_v11_0_set_soft_freq_limited_range,  	.run_btc = sienna_cichlid_run_btc, +	.set_power_source = smu_v11_0_set_power_source,  	.get_pp_feature_mask = smu_cmn_get_pp_feature_mask,  	.set_pp_feature_mask = smu_cmn_set_pp_feature_mask,  	.get_gpu_metrics = sienna_cichlid_get_gpu_metrics, diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu11/sienna_cichlid_ppt.h b/drivers/gpu/drm/amd/pm/swsmu/smu11/sienna_cichlid_ppt.h index 57e120c440ea..38cd0ece24f6 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/smu11/sienna_cichlid_ppt.h +++ b/drivers/gpu/drm/amd/pm/swsmu/smu11/sienna_cichlid_ppt.h @@ -29,6 +29,10 @@ typedef enum {    POWER_SOURCE_COUNT,  } POWER_SOURCE_e; +#define SIENNA_CICHLID_UMD_PSTATE_PROFILING_GFXCLK    1825 +#define SIENNA_CICHLID_UMD_PSTATE_PROFILING_SOCCLK    960 +#define SIENNA_CICHLID_UMD_PSTATE_PROFILING_MEMCLK    1000 +  extern void sienna_cichlid_set_ppt_funcs(struct smu_context *smu);  #endif diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c b/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c index 624065d3c079..b279dbbbce6b 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c +++ b/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c @@ -91,6 +91,11 @@ int smu_v11_0_init_microcode(struct smu_context *smu)  	const struct common_firmware_header *header;  	struct amdgpu_firmware_info *ucode = NULL; +	if (amdgpu_sriov_vf(adev) && +			((adev->asic_type == CHIP_NAVI12) || +			 (adev->asic_type == CHIP_SIENNA_CICHLID))) +		return 0; +  	switch (adev->asic_type) {  	case CHIP_ARCTURUS:  		chip_name = "arcturus"; @@ -554,6 +559,7 @@ int smu_v11_0_get_vbios_bootup_values(struct smu_context *smu)  		smu->smu_table.boot_values.vdd_gfx = v_3_1->bootup_vddgfx_mv;  		smu->smu_table.boot_values.cooling_id = v_3_1->coolingsolution_id;  		smu->smu_table.boot_values.pp_table_id = 0; +		smu->smu_table.boot_values.firmware_caps = v_3_1->firmware_capability;  		break;  	case 3:  	default: @@ -569,6 +575,7 @@ int smu_v11_0_get_vbios_bootup_values(struct smu_context *smu)  		smu->smu_table.boot_values.vdd_gfx = v_3_3->bootup_vddgfx_mv;  		smu->smu_table.boot_values.cooling_id = v_3_3->coolingsolution_id;  		smu->smu_table.boot_values.pp_table_id = v_3_3->pplib_pptable_id; +		smu->smu_table.boot_values.firmware_caps = v_3_3->firmware_capability;  	}  	smu->smu_table.boot_values.format_revision = header->format_revision; @@ -929,9 +936,13 @@ int smu_v11_0_get_current_power_limit(struct smu_context *smu,  	if (power_src < 0)  		return -EINVAL; +	/* +	 * BIT 24-31: ControllerId (only PPT0 is supported for now) +	 * BIT 16-23: PowerSource +	 */  	ret = smu_cmn_send_smc_msg_with_param(smu,  					  SMU_MSG_GetPptLimit, -					  power_src << 16, +					  (0 << 24) | (power_src << 16),  					  power_limit);  	if (ret)  		dev_err(smu->adev->dev, "[%s] get PPT limit failed!", __func__); @@ -941,6 +952,7 @@ int smu_v11_0_get_current_power_limit(struct smu_context *smu,  int smu_v11_0_set_power_limit(struct smu_context *smu, uint32_t n)  { +	int power_src;  	int ret = 0;  	if (!smu_cmn_feature_is_enabled(smu, SMU_FEATURE_PPT_BIT)) { @@ -948,6 +960,22 @@ int smu_v11_0_set_power_limit(struct smu_context *smu, uint32_t n)  		return -EOPNOTSUPP;  	} +	power_src = smu_cmn_to_asic_specific_index(smu, +					CMN2ASIC_MAPPING_PWR, +					smu->adev->pm.ac_power ? +					SMU_POWER_SOURCE_AC : +					SMU_POWER_SOURCE_DC); +	if (power_src < 0) +		return -EINVAL; + +	/* +	 * BIT 24-31: ControllerId (only PPT0 is supported for now) +	 * BIT 16-23: PowerSource +	 * BIT 0-15: PowerLimit +	 */ +	n &= 0xFFFF; +	n |= 0 << 24; +	n |= (power_src) << 16;  	ret = smu_cmn_send_smc_msg_with_param(smu, SMU_MSG_SetPptLimit, n, NULL);  	if (ret) {  		dev_err(smu->adev->dev, "[%s] Set power limit Failed!\n", __func__); @@ -2064,6 +2092,22 @@ int smu_v11_0_deep_sleep_control(struct smu_context *smu,  		}  	} +	if (smu_cmn_feature_is_supported(smu, SMU_FEATURE_DS_UCLK_BIT)) { +		ret = smu_cmn_feature_set_enabled(smu, SMU_FEATURE_DS_UCLK_BIT, enablement); +		if (ret) { +			dev_err(adev->dev, "Failed to %s UCLK DS!\n", enablement ? "enable" : "disable"); +			return ret; +		} +	} + +	if (smu_cmn_feature_is_supported(smu, SMU_FEATURE_DS_FCLK_BIT)) { +		ret = smu_cmn_feature_set_enabled(smu, SMU_FEATURE_DS_FCLK_BIT, enablement); +		if (ret) { +			dev_err(adev->dev, "Failed to %s FCLK DS!\n", enablement ? "enable" : "disable"); +			return ret; +		} +	} +  	if (smu_cmn_feature_is_supported(smu, SMU_FEATURE_DS_SOCCLK_BIT)) {  		ret = smu_cmn_feature_set_enabled(smu, SMU_FEATURE_DS_SOCCLK_BIT, enablement);  		if (ret) { diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu11/vangogh_ppt.c b/drivers/gpu/drm/amd/pm/swsmu/smu11/vangogh_ppt.c index a81e5c823211..9bccf2ad038c 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/smu11/vangogh_ppt.c +++ b/drivers/gpu/drm/amd/pm/swsmu/smu11/vangogh_ppt.c @@ -64,7 +64,7 @@ static struct cmn2asic_msg_mapping vangogh_message_map[SMU_MSG_MAX_COUNT] = {  	MSG_MAP(PowerUpIspByTile,               PPSMC_MSG_PowerUpIspByTile,		0),  	MSG_MAP(PowerDownVcn,                   PPSMC_MSG_PowerDownVcn,			0),  	MSG_MAP(PowerUpVcn,                     PPSMC_MSG_PowerUpVcn,			0), -	MSG_MAP(Spare,                          PPSMC_MSG_spare,				0), +	MSG_MAP(RlcPowerNotify,                 PPSMC_MSG_RlcPowerNotify,		0),  	MSG_MAP(SetHardMinVcn,                  PPSMC_MSG_SetHardMinVcn,		0),  	MSG_MAP(SetSoftMinGfxclk,               PPSMC_MSG_SetSoftMinGfxclk,		0),  	MSG_MAP(ActiveProcessNotify,            PPSMC_MSG_ActiveProcessNotify,		0), @@ -722,6 +722,12 @@ static int vangogh_set_fine_grain_gfx_freq_parameters(struct smu_context *smu)  	return 0;  } +static int vangogh_system_features_control(struct smu_context *smu, bool en) +{ +	return smu_cmn_send_smc_msg_with_param(smu, SMU_MSG_RlcPowerNotify, +					en ? RLC_STATUS_NORMAL : RLC_STATUS_OFF, NULL); +} +  static const struct pptable_funcs vangogh_ppt_funcs = {  	.check_fw_status = smu_v11_0_check_fw_status, @@ -749,6 +755,7 @@ static const struct pptable_funcs vangogh_ppt_funcs = {  	.print_clk_levels = vangogh_print_fine_grain_clk,  	.set_default_dpm_table = vangogh_set_default_dpm_tables,  	.set_fine_grain_gfx_freq_parameters = vangogh_set_fine_grain_gfx_freq_parameters, +	.system_features_control = vangogh_system_features_control,  };  void vangogh_set_ppt_funcs(struct smu_context *smu) diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu11/vangogh_ppt.h b/drivers/gpu/drm/amd/pm/swsmu/smu11/vangogh_ppt.h index 8756766296cd..eab455493076 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/smu11/vangogh_ppt.h +++ b/drivers/gpu/drm/amd/pm/swsmu/smu11/vangogh_ppt.h @@ -32,4 +32,8 @@ extern void vangogh_set_ppt_funcs(struct smu_context *smu);  #define VANGOGH_UMD_PSTATE_SOCCLK       678  #define VANGOGH_UMD_PSTATE_FCLK         800 +/* RLC Power Status */ +#define RLC_STATUS_OFF          0 +#define RLC_STATUS_NORMAL       1 +  #endif diff --git a/drivers/gpu/drm/radeon/radeon_uvd.c b/drivers/gpu/drm/radeon/radeon_uvd.c index 57fb3eb3a4b4..39c1c339be7b 100644 --- a/drivers/gpu/drm/radeon/radeon_uvd.c +++ b/drivers/gpu/drm/radeon/radeon_uvd.c @@ -155,7 +155,7 @@ int radeon_uvd_init(struct radeon_device *rdev)  			family_id = le32_to_cpu(hdr->ucode_version) & 0xff;  			version_major = (le32_to_cpu(hdr->ucode_version) >> 24) & 0xff;  			version_minor = (le32_to_cpu(hdr->ucode_version) >> 8) & 0xff; -			DRM_INFO("Found UVD firmware Version: %hu.%hu Family ID: %hu\n", +			DRM_INFO("Found UVD firmware Version: %u.%u Family ID: %u\n",  				 version_major, version_minor, family_id);  			/* diff --git a/drivers/gpu/drm/radeon/radeon_vce.c b/drivers/gpu/drm/radeon/radeon_vce.c index 5e8006444704..a450497368b2 100644 --- a/drivers/gpu/drm/radeon/radeon_vce.c +++ b/drivers/gpu/drm/radeon/radeon_vce.c @@ -122,7 +122,7 @@ int radeon_vce_init(struct radeon_device *rdev)  	if (sscanf(c, "%2u]", &rdev->vce.fb_version) != 1)  		return -EINVAL; -	DRM_INFO("Found VCE firmware/feedback version %hhd.%hhd.%hhd / %d!\n", +	DRM_INFO("Found VCE firmware/feedback version %d.%d.%d / %d!\n",  		 start, mid, end, rdev->vce.fb_version);  	rdev->vce.fw_version = (start << 24) | (mid << 16) | (end << 8); | 
