diff options
Diffstat (limited to 'drivers/gpu/drm/amd/amdgpu')
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu.h | 11 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_acpi.c | 2 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 132 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_display.c | 89 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_display.h | 3 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c | 35 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_fb.c | 2 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c | 4 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_object.c | 7 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c | 2 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c | 10 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/dce_v10_0.c | 9 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/dce_v11_0.c | 9 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/dce_v6_0.c | 8 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/dce_v8_0.c | 9 | ||||
| -rw-r--r-- | drivers/gpu/drm/amd/amdgpu/dce_virtual.c | 15 | 
16 files changed, 210 insertions, 137 deletions
| diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu.h b/drivers/gpu/drm/amd/amdgpu/amdgpu.h index b6879d97c9c9..29885febc0b0 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu.h +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu.h @@ -180,6 +180,7 @@ extern uint amdgpu_smu_memory_pool_size;  extern uint amdgpu_dc_feature_mask;  extern uint amdgpu_dc_debug_mask;  extern uint amdgpu_dm_abm_level; +extern int amdgpu_backlight;  extern struct amdgpu_mgpu_info mgpu_info;  extern int amdgpu_ras_enable;  extern uint amdgpu_ras_mask; @@ -1006,13 +1007,9 @@ struct amdgpu_device {  	/* s3/s4 mask */  	bool                            in_suspend; -	bool				in_hibernate; - -	/* -	 * The combination flag in_poweroff_reboot_com used to identify the poweroff -	 * and reboot opt in the s0i3 system-wide suspend. -	 */ -	bool 				in_poweroff_reboot_com; +	bool				in_s3; +	bool				in_s4; +	bool				in_s0ix;  	atomic_t 			in_gpu_reset;  	enum pp_mp1_state               mp1_state; diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_acpi.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_acpi.c index 36a741d63ddc..2e9b16fb3fcd 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_acpi.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_acpi.c @@ -903,7 +903,7 @@ void amdgpu_acpi_fini(struct amdgpu_device *adev)   */  bool amdgpu_acpi_is_s0ix_supported(struct amdgpu_device *adev)  { -#if defined(CONFIG_AMD_PMC) +#if defined(CONFIG_AMD_PMC) || defined(CONFIG_AMD_PMC_MODULE)  	if (acpi_gbl_FADT.flags & ACPI_FADT_LOW_POWER_S0) {  		if (adev->flags & AMD_IS_APU)  			return true; diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c index 6447cd6ca5a8..8a5a8ff5d362 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c @@ -2371,6 +2371,10 @@ static int amdgpu_device_set_cg_state(struct amdgpu_device *adev,  		i = state == AMD_CG_STATE_GATE ? j : adev->num_ip_blocks - j - 1;  		if (!adev->ip_blocks[i].status.late_initialized)  			continue; +		/* skip CG for GFX on S0ix */ +		if (adev->in_s0ix && +		    adev->ip_blocks[i].version->type == AMD_IP_BLOCK_TYPE_GFX) +			continue;  		/* skip CG for VCE/UVD, it's handled specially */  		if (adev->ip_blocks[i].version->type != AMD_IP_BLOCK_TYPE_UVD &&  		    adev->ip_blocks[i].version->type != AMD_IP_BLOCK_TYPE_VCE && @@ -2402,6 +2406,10 @@ static int amdgpu_device_set_pg_state(struct amdgpu_device *adev, enum amd_power  		i = state == AMD_PG_STATE_GATE ? j : adev->num_ip_blocks - j - 1;  		if (!adev->ip_blocks[i].status.late_initialized)  			continue; +		/* skip PG for GFX on S0ix */ +		if (adev->in_s0ix && +		    adev->ip_blocks[i].version->type == AMD_IP_BLOCK_TYPE_GFX) +			continue;  		/* skip CG for VCE/UVD, it's handled specially */  		if (adev->ip_blocks[i].version->type != AMD_IP_BLOCK_TYPE_UVD &&  		    adev->ip_blocks[i].version->type != AMD_IP_BLOCK_TYPE_VCE && @@ -2678,11 +2686,8 @@ static int amdgpu_device_ip_suspend_phase1(struct amdgpu_device *adev)  {  	int i, r; -	if (adev->in_poweroff_reboot_com || -	    !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); -	} +	amdgpu_device_set_pg_state(adev, AMD_PG_STATE_UNGATE); +	amdgpu_device_set_cg_state(adev, AMD_CG_STATE_UNGATE);  	for (i = adev->num_ip_blocks - 1; i >= 0; i--) {  		if (!adev->ip_blocks[i].status.valid) @@ -2722,6 +2727,9 @@ static int amdgpu_device_ip_suspend_phase2(struct amdgpu_device *adev)  {  	int i, r; +	if (adev->in_s0ix) +		amdgpu_gfx_state_change_set(adev, sGpuChangeState_D3Entry); +  	for (i = adev->num_ip_blocks - 1; i >= 0; i--) {  		if (!adev->ip_blocks[i].status.valid)  			continue; @@ -2734,6 +2742,17 @@ static int amdgpu_device_ip_suspend_phase2(struct amdgpu_device *adev)  			adev->ip_blocks[i].status.hw = false;  			continue;  		} + +		/* skip suspend of gfx and psp for S0ix +		 * gfx is in gfxoff state, so on resume it will exit gfxoff just +		 * like at runtime. PSP is also part of the always on hardware +		 * so no need to suspend it. +		 */ +		if (adev->in_s0ix && +		    (adev->ip_blocks[i].version->type == AMD_IP_BLOCK_TYPE_PSP || +		     adev->ip_blocks[i].version->type == AMD_IP_BLOCK_TYPE_GFX)) +			continue; +  		/* XXX handle errors */  		r = adev->ip_blocks[i].version->funcs->suspend(adev);  		/* XXX handle errors */ @@ -3673,14 +3692,9 @@ void amdgpu_device_fini(struct amdgpu_device *adev)   */  int amdgpu_device_suspend(struct drm_device *dev, bool fbcon)  { -	struct amdgpu_device *adev; -	struct drm_crtc *crtc; -	struct drm_connector *connector; -	struct drm_connector_list_iter iter; +	struct amdgpu_device *adev = drm_to_adev(dev);  	int r; -	adev = drm_to_adev(dev); -  	if (dev->switch_power_state == DRM_SWITCH_POWER_OFF)  		return 0; @@ -3692,61 +3706,19 @@ int amdgpu_device_suspend(struct drm_device *dev, bool fbcon)  	cancel_delayed_work_sync(&adev->delayed_init_work); -	if (!amdgpu_device_has_dc_support(adev)) { -		/* turn off display hw */ -		drm_modeset_lock_all(dev); -		drm_connector_list_iter_begin(dev, &iter); -		drm_for_each_connector_iter(connector, &iter) -			drm_helper_connector_dpms(connector, -						  DRM_MODE_DPMS_OFF); -		drm_connector_list_iter_end(&iter); -		drm_modeset_unlock_all(dev); -			/* unpin the front buffers and cursors */ -		list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { -			struct amdgpu_crtc *amdgpu_crtc = to_amdgpu_crtc(crtc); -			struct drm_framebuffer *fb = crtc->primary->fb; -			struct amdgpu_bo *robj; - -			if (amdgpu_crtc->cursor_bo && !adev->enable_virtual_display) { -				struct amdgpu_bo *aobj = gem_to_amdgpu_bo(amdgpu_crtc->cursor_bo); -				r = amdgpu_bo_reserve(aobj, true); -				if (r == 0) { -					amdgpu_bo_unpin(aobj); -					amdgpu_bo_unreserve(aobj); -				} -			} - -			if (fb == NULL || fb->obj[0] == NULL) { -				continue; -			} -			robj = gem_to_amdgpu_bo(fb->obj[0]); -			/* don't unpin kernel fb objects */ -			if (!amdgpu_fbdev_robj_is_fb(adev, robj)) { -				r = amdgpu_bo_reserve(robj, true); -				if (r == 0) { -					amdgpu_bo_unpin(robj); -					amdgpu_bo_unreserve(robj); -				} -			} -		} -	} -  	amdgpu_ras_suspend(adev);  	r = amdgpu_device_ip_suspend_phase1(adev); -	amdgpu_amdkfd_suspend(adev, adev->in_runpm); +	if (!adev->in_s0ix) +		amdgpu_amdkfd_suspend(adev, adev->in_runpm);  	/* evict vram memory */  	amdgpu_bo_evict_vram(adev);  	amdgpu_fence_driver_suspend(adev); -	if (adev->in_poweroff_reboot_com || -	    !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); +	r = amdgpu_device_ip_suspend_phase2(adev);  	/* evict remaining vram memory  	 * This second call to evict vram is to evict the gart page table  	 * using the CPU. @@ -3768,16 +3740,13 @@ int amdgpu_device_suspend(struct drm_device *dev, bool fbcon)   */  int amdgpu_device_resume(struct drm_device *dev, bool fbcon)  { -	struct drm_connector *connector; -	struct drm_connector_list_iter iter;  	struct amdgpu_device *adev = drm_to_adev(dev); -	struct drm_crtc *crtc;  	int r = 0;  	if (dev->switch_power_state == DRM_SWITCH_POWER_OFF)  		return 0; -	if (amdgpu_acpi_is_s0ix_supported(adev)) +	if (adev->in_s0ix)  		amdgpu_gfx_state_change_set(adev, sGpuChangeState_D0Entry);  	/* post card */ @@ -3802,50 +3771,17 @@ int amdgpu_device_resume(struct drm_device *dev, bool fbcon)  	queue_delayed_work(system_wq, &adev->delayed_init_work,  			   msecs_to_jiffies(AMDGPU_RESUME_MS)); -	if (!amdgpu_device_has_dc_support(adev)) { -		/* pin cursors */ -		list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { -			struct amdgpu_crtc *amdgpu_crtc = to_amdgpu_crtc(crtc); - -			if (amdgpu_crtc->cursor_bo && !adev->enable_virtual_display) { -				struct amdgpu_bo *aobj = gem_to_amdgpu_bo(amdgpu_crtc->cursor_bo); -				r = amdgpu_bo_reserve(aobj, true); -				if (r == 0) { -					r = amdgpu_bo_pin(aobj, AMDGPU_GEM_DOMAIN_VRAM); -					if (r != 0) -						dev_err(adev->dev, "Failed to pin cursor BO (%d)\n", r); -					amdgpu_crtc->cursor_addr = amdgpu_bo_gpu_offset(aobj); -					amdgpu_bo_unreserve(aobj); -				} -			} -		} +	if (!adev->in_s0ix) { +		r = amdgpu_amdkfd_resume(adev, adev->in_runpm); +		if (r) +			return r;  	} -	r = amdgpu_amdkfd_resume(adev, adev->in_runpm); -	if (r) -		return r;  	/* Make sure IB tests flushed */  	flush_delayed_work(&adev->delayed_init_work); -	/* blat the mode back in */ -	if (fbcon) { -		if (!amdgpu_device_has_dc_support(adev)) { -			/* pre DCE11 */ -			drm_helper_resume_force_mode(dev); - -			/* turn on display hw */ -			drm_modeset_lock_all(dev); - -			drm_connector_list_iter_begin(dev, &iter); -			drm_for_each_connector_iter(connector, &iter) -				drm_helper_connector_dpms(connector, -							  DRM_MODE_DPMS_ON); -			drm_connector_list_iter_end(&iter); - -			drm_modeset_unlock_all(dev); -		} +	if (fbcon)  		amdgpu_fbdev_set_suspend(adev, 0); -	}  	drm_kms_helper_poll_enable(dev); diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_display.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_display.c index 48cb33e5b382..f753e04fee99 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_display.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_display.c @@ -1310,3 +1310,92 @@ bool amdgpu_crtc_get_scanout_position(struct drm_crtc *crtc,  	return amdgpu_display_get_crtc_scanoutpos(dev, pipe, 0, vpos, hpos,  						  stime, etime, mode);  } + +int amdgpu_display_suspend_helper(struct amdgpu_device *adev) +{ +	struct drm_device *dev = adev_to_drm(adev); +	struct drm_crtc *crtc; +	struct drm_connector *connector; +	struct drm_connector_list_iter iter; +	int r; + +	/* turn off display hw */ +	drm_modeset_lock_all(dev); +	drm_connector_list_iter_begin(dev, &iter); +	drm_for_each_connector_iter(connector, &iter) +		drm_helper_connector_dpms(connector, +					  DRM_MODE_DPMS_OFF); +	drm_connector_list_iter_end(&iter); +	drm_modeset_unlock_all(dev); +	/* unpin the front buffers and cursors */ +	list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { +		struct amdgpu_crtc *amdgpu_crtc = to_amdgpu_crtc(crtc); +		struct drm_framebuffer *fb = crtc->primary->fb; +		struct amdgpu_bo *robj; + +		if (amdgpu_crtc->cursor_bo && !adev->enable_virtual_display) { +			struct amdgpu_bo *aobj = gem_to_amdgpu_bo(amdgpu_crtc->cursor_bo); +			r = amdgpu_bo_reserve(aobj, true); +			if (r == 0) { +				amdgpu_bo_unpin(aobj); +				amdgpu_bo_unreserve(aobj); +			} +		} + +		if (fb == NULL || fb->obj[0] == NULL) { +			continue; +		} +		robj = gem_to_amdgpu_bo(fb->obj[0]); +		/* don't unpin kernel fb objects */ +		if (!amdgpu_fbdev_robj_is_fb(adev, robj)) { +			r = amdgpu_bo_reserve(robj, true); +			if (r == 0) { +				amdgpu_bo_unpin(robj); +				amdgpu_bo_unreserve(robj); +			} +		} +	} +	return r; +} + +int amdgpu_display_resume_helper(struct amdgpu_device *adev) +{ +	struct drm_device *dev = adev_to_drm(adev); +	struct drm_connector *connector; +	struct drm_connector_list_iter iter; +	struct drm_crtc *crtc; +	int r; + +	/* pin cursors */ +	list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { +		struct amdgpu_crtc *amdgpu_crtc = to_amdgpu_crtc(crtc); + +		if (amdgpu_crtc->cursor_bo && !adev->enable_virtual_display) { +			struct amdgpu_bo *aobj = gem_to_amdgpu_bo(amdgpu_crtc->cursor_bo); +			r = amdgpu_bo_reserve(aobj, true); +			if (r == 0) { +				r = amdgpu_bo_pin(aobj, AMDGPU_GEM_DOMAIN_VRAM); +				if (r != 0) +					dev_err(adev->dev, "Failed to pin cursor BO (%d)\n", r); +				amdgpu_crtc->cursor_addr = amdgpu_bo_gpu_offset(aobj); +				amdgpu_bo_unreserve(aobj); +			} +		} +	} + +	drm_helper_resume_force_mode(dev); + +	/* turn on display hw */ +	drm_modeset_lock_all(dev); + +	drm_connector_list_iter_begin(dev, &iter); +	drm_for_each_connector_iter(connector, &iter) +		drm_helper_connector_dpms(connector, +					  DRM_MODE_DPMS_ON); +	drm_connector_list_iter_end(&iter); + +	drm_modeset_unlock_all(dev); + +	return 0; +} + diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_display.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_display.h index dc7b7d116549..7b6d83e2b13c 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_display.h +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_display.h @@ -47,4 +47,7 @@ amdgpu_display_user_framebuffer_create(struct drm_device *dev,  const struct drm_format_info *  amdgpu_lookup_format_info(u32 format, uint64_t modifier); +int amdgpu_display_suspend_helper(struct amdgpu_device *adev); +int amdgpu_display_resume_helper(struct amdgpu_device *adev); +  #endif diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c index 4575192d9b08..e92e7dea71da 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c @@ -781,6 +781,10 @@ uint amdgpu_dm_abm_level;  MODULE_PARM_DESC(abmlevel, "ABM level (0 = off (default), 1-4 = backlight reduction level) ");  module_param_named(abmlevel, amdgpu_dm_abm_level, uint, 0444); +int amdgpu_backlight = -1; +MODULE_PARM_DESC(backlight, "Backlight control (0 = pwm, 1 = aux, -1 auto (default))"); +module_param_named(backlight, amdgpu_backlight, bint, 0444); +  /**   * DOC: tmz (int)   * Trusted Memory Zone (TMZ) is a method to protect data being written @@ -1103,6 +1107,7 @@ static const struct pci_device_id pciidlist[] = {  	{0x1002, 0x73A3, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SIENNA_CICHLID},  	{0x1002, 0x73AB, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SIENNA_CICHLID},  	{0x1002, 0x73AE, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SIENNA_CICHLID}, +	{0x1002, 0x73AF, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SIENNA_CICHLID},  	{0x1002, 0x73BF, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SIENNA_CICHLID},  	/* Van Gogh */ @@ -1270,24 +1275,35 @@ amdgpu_pci_shutdown(struct pci_dev *pdev)  	 */  	if (!amdgpu_passthrough(adev))  		adev->mp1_state = PP_MP1_STATE_UNLOAD; -	adev->in_poweroff_reboot_com = true;  	amdgpu_device_ip_suspend(adev); -	adev->in_poweroff_reboot_com = false;  	adev->mp1_state = PP_MP1_STATE_NONE;  }  static int amdgpu_pmops_suspend(struct device *dev)  {  	struct drm_device *drm_dev = dev_get_drvdata(dev); +	struct amdgpu_device *adev = drm_to_adev(drm_dev); +	int r; -	return amdgpu_device_suspend(drm_dev, true); +	if (amdgpu_acpi_is_s0ix_supported(adev)) +		adev->in_s0ix = true; +	adev->in_s3 = true; +	r = amdgpu_device_suspend(drm_dev, true); +	adev->in_s3 = false; + +	return r;  }  static int amdgpu_pmops_resume(struct device *dev)  {  	struct drm_device *drm_dev = dev_get_drvdata(dev); +	struct amdgpu_device *adev = drm_to_adev(drm_dev); +	int r; -	return amdgpu_device_resume(drm_dev, true); +	r = amdgpu_device_resume(drm_dev, true); +	if (amdgpu_acpi_is_s0ix_supported(adev)) +		adev->in_s0ix = false; +	return r;  }  static int amdgpu_pmops_freeze(struct device *dev) @@ -1296,9 +1312,9 @@ static int amdgpu_pmops_freeze(struct device *dev)  	struct amdgpu_device *adev = drm_to_adev(drm_dev);  	int r; -	adev->in_hibernate = true; +	adev->in_s4 = true;  	r = amdgpu_device_suspend(drm_dev, true); -	adev->in_hibernate = false; +	adev->in_s4 = false;  	if (r)  		return r;  	return amdgpu_asic_reset(adev); @@ -1314,13 +1330,8 @@ static int amdgpu_pmops_thaw(struct device *dev)  static int amdgpu_pmops_poweroff(struct device *dev)  {  	struct drm_device *drm_dev = dev_get_drvdata(dev); -	struct amdgpu_device *adev = drm_to_adev(drm_dev); -	int r; -	adev->in_poweroff_reboot_com = true; -	r =  amdgpu_device_suspend(drm_dev, true); -	adev->in_poweroff_reboot_com = false; -	return r; +	return amdgpu_device_suspend(drm_dev, true);  }  static int amdgpu_pmops_restore(struct device *dev) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_fb.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_fb.c index 51cd49c6f38f..24010cacf7d0 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_fb.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_fb.c @@ -146,7 +146,7 @@ static int amdgpufb_create_pinned_object(struct amdgpu_fbdev *rfbdev,  	size = mode_cmd->pitches[0] * height;  	aligned_size = ALIGN(size, PAGE_SIZE);  	ret = amdgpu_gem_object_create(adev, aligned_size, 0, domain, flags, -				       ttm_bo_type_kernel, NULL, &gobj); +				       ttm_bo_type_device, NULL, &gobj);  	if (ret) {  		pr_err("failed to allocate framebuffer (%d)\n", aligned_size);  		return -ENOMEM; diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c index 64beb3399604..a4e2cf7cada1 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_kms.c @@ -778,9 +778,9 @@ int amdgpu_info_ioctl(struct drm_device *dev, void *data, struct drm_file *filp)  			dev_info->high_va_offset = AMDGPU_GMC_HOLE_END;  			dev_info->high_va_max = AMDGPU_GMC_HOLE_END | vm_size;  		} -		dev_info->virtual_address_alignment = max((int)PAGE_SIZE, AMDGPU_GPU_PAGE_SIZE); +		dev_info->virtual_address_alignment = max_t(u32, PAGE_SIZE, AMDGPU_GPU_PAGE_SIZE);  		dev_info->pte_fragment_size = (1 << adev->vm_manager.fragment_size) * AMDGPU_GPU_PAGE_SIZE; -		dev_info->gart_page_size = AMDGPU_GPU_PAGE_SIZE; +		dev_info->gart_page_size = max_t(u32, PAGE_SIZE, AMDGPU_GPU_PAGE_SIZE);  		dev_info->cu_active_number = adev->gfx.cu_info.number;  		dev_info->cu_ao_mask = adev->gfx.cu_info.ao_cu_mask;  		dev_info->ce_ram_size = adev->gfx.ce_ram_size; diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c index 4b29b8205442..072050429a2f 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c @@ -1028,13 +1028,10 @@ int amdgpu_bo_evict_vram(struct amdgpu_device *adev)  {  	struct ttm_resource_manager *man; -	/* late 2.6.33 fix IGP hibernate - we need pm ops to do this correct */ -#ifndef CONFIG_HIBERNATION -	if (adev->flags & AMD_IS_APU) { -		/* Useless to evict on IGP chips */ +	if (adev->in_s3 && (adev->flags & AMD_IS_APU)) { +		/* No need to evict vram on APUs for suspend to ram */  		return 0;  	} -#endif  	man = ttm_manager_type(&adev->mman.bdev, TTM_PL_VRAM);  	return ttm_resource_manager_evict_all(&adev->mman.bdev, man); diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c index 9fd2157b133a..5efa331e3ee8 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c @@ -906,7 +906,7 @@ static int amdgpu_ttm_tt_pin_userptr(struct ttm_bo_device *bdev,  	/* Allocate an SG array and squash pages into it */  	r = sg_alloc_table_from_pages(ttm->sg, ttm->pages, ttm->num_pages, 0, -				      ttm->num_pages << PAGE_SHIFT, +				      (u64)ttm->num_pages << PAGE_SHIFT,  				      GFP_KERNEL);  	if (r)  		goto release_sg; diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c index ad91c0c3c423..7d2c8b169827 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c @@ -2197,8 +2197,8 @@ int amdgpu_vm_bo_map(struct amdgpu_device *adev,  	uint64_t eaddr;  	/* validate the parameters */ -	if (saddr & AMDGPU_GPU_PAGE_MASK || offset & AMDGPU_GPU_PAGE_MASK || -	    size == 0 || size & AMDGPU_GPU_PAGE_MASK) +	if (saddr & ~PAGE_MASK || offset & ~PAGE_MASK || +	    size == 0 || size & ~PAGE_MASK)  		return -EINVAL;  	/* make sure object fit at this offset */ @@ -2263,8 +2263,8 @@ int amdgpu_vm_bo_replace_map(struct amdgpu_device *adev,  	int r;  	/* validate the parameters */ -	if (saddr & AMDGPU_GPU_PAGE_MASK || offset & AMDGPU_GPU_PAGE_MASK || -	    size == 0 || size & AMDGPU_GPU_PAGE_MASK) +	if (saddr & ~PAGE_MASK || offset & ~PAGE_MASK || +	    size == 0 || size & ~PAGE_MASK)  		return -EINVAL;  	/* make sure object fit at this offset */ @@ -2409,7 +2409,7 @@ int amdgpu_vm_bo_clear_mappings(struct amdgpu_device *adev,  			after->start = eaddr + 1;  			after->last = tmp->last;  			after->offset = tmp->offset; -			after->offset += after->start - tmp->start; +			after->offset += (after->start - tmp->start) << PAGE_SHIFT;  			after->flags = tmp->flags;  			after->bo_va = tmp->bo_va;  			list_add(&after->list, &tmp->bo_va->invalids); diff --git a/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c b/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c index 7944781e1086..19abb740a169 100644 --- a/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c +++ b/drivers/gpu/drm/amd/amdgpu/dce_v10_0.c @@ -2897,6 +2897,11 @@ static int dce_v10_0_hw_fini(void *handle)  static int dce_v10_0_suspend(void *handle)  {  	struct amdgpu_device *adev = (struct amdgpu_device *)handle; +	int r; + +	r = amdgpu_display_suspend_helper(adev); +	if (r) +		return r;  	adev->mode_info.bl_level =  		amdgpu_atombios_encoder_get_backlight_level_from_reg(adev); @@ -2921,8 +2926,10 @@ static int dce_v10_0_resume(void *handle)  		amdgpu_display_backlight_set_level(adev, adev->mode_info.bl_encoder,  						    bl_level);  	} +	if (ret) +		return ret; -	return ret; +	return amdgpu_display_resume_helper(adev);  }  static bool dce_v10_0_is_idle(void *handle) diff --git a/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c b/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c index 1b6ff0470011..320ec35bfd37 100644 --- a/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c +++ b/drivers/gpu/drm/amd/amdgpu/dce_v11_0.c @@ -3027,6 +3027,11 @@ static int dce_v11_0_hw_fini(void *handle)  static int dce_v11_0_suspend(void *handle)  {  	struct amdgpu_device *adev = (struct amdgpu_device *)handle; +	int r; + +	r = amdgpu_display_suspend_helper(adev); +	if (r) +		return r;  	adev->mode_info.bl_level =  		amdgpu_atombios_encoder_get_backlight_level_from_reg(adev); @@ -3051,8 +3056,10 @@ static int dce_v11_0_resume(void *handle)  		amdgpu_display_backlight_set_level(adev, adev->mode_info.bl_encoder,  						    bl_level);  	} +	if (ret) +		return ret; -	return ret; +	return amdgpu_display_resume_helper(adev);  }  static bool dce_v11_0_is_idle(void *handle) diff --git a/drivers/gpu/drm/amd/amdgpu/dce_v6_0.c b/drivers/gpu/drm/amd/amdgpu/dce_v6_0.c index 83a88385b762..13322000ebd6 100644 --- a/drivers/gpu/drm/amd/amdgpu/dce_v6_0.c +++ b/drivers/gpu/drm/amd/amdgpu/dce_v6_0.c @@ -2770,7 +2770,11 @@ static int dce_v6_0_hw_fini(void *handle)  static int dce_v6_0_suspend(void *handle)  {  	struct amdgpu_device *adev = (struct amdgpu_device *)handle; +	int r; +	r = amdgpu_display_suspend_helper(adev); +	if (r) +		return r;  	adev->mode_info.bl_level =  		amdgpu_atombios_encoder_get_backlight_level_from_reg(adev); @@ -2794,8 +2798,10 @@ static int dce_v6_0_resume(void *handle)  		amdgpu_display_backlight_set_level(adev, adev->mode_info.bl_encoder,  						    bl_level);  	} +	if (ret) +		return ret; -	return ret; +	return amdgpu_display_resume_helper(adev);  }  static bool dce_v6_0_is_idle(void *handle) diff --git a/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c b/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c index 224b30214427..04ebf02e5b8c 100644 --- a/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c +++ b/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c @@ -2796,6 +2796,11 @@ static int dce_v8_0_hw_fini(void *handle)  static int dce_v8_0_suspend(void *handle)  {  	struct amdgpu_device *adev = (struct amdgpu_device *)handle; +	int r; + +	r = amdgpu_display_suspend_helper(adev); +	if (r) +		return r;  	adev->mode_info.bl_level =  		amdgpu_atombios_encoder_get_backlight_level_from_reg(adev); @@ -2820,8 +2825,10 @@ static int dce_v8_0_resume(void *handle)  		amdgpu_display_backlight_set_level(adev, adev->mode_info.bl_encoder,  						    bl_level);  	} +	if (ret) +		return ret; -	return ret; +	return amdgpu_display_resume_helper(adev);  }  static bool dce_v8_0_is_idle(void *handle) diff --git a/drivers/gpu/drm/amd/amdgpu/dce_virtual.c b/drivers/gpu/drm/amd/amdgpu/dce_virtual.c index 9810af712cc0..5c11144da051 100644 --- a/drivers/gpu/drm/amd/amdgpu/dce_virtual.c +++ b/drivers/gpu/drm/amd/amdgpu/dce_virtual.c @@ -39,6 +39,7 @@  #include "dce_v11_0.h"  #include "dce_virtual.h"  #include "ivsrcid/ivsrcid_vislands30.h" +#include "amdgpu_display.h"  #define DCE_VIRTUAL_VBLANK_PERIOD 16666666 @@ -491,12 +492,24 @@ static int dce_virtual_hw_fini(void *handle)  static int dce_virtual_suspend(void *handle)  { +	struct amdgpu_device *adev = (struct amdgpu_device *)handle; +	int r; + +	r = amdgpu_display_suspend_helper(adev); +	if (r) +		return r;  	return dce_virtual_hw_fini(handle);  }  static int dce_virtual_resume(void *handle)  { -	return dce_virtual_hw_init(handle); +	struct amdgpu_device *adev = (struct amdgpu_device *)handle; +	int r; + +	r = dce_virtual_hw_init(handle); +	if (r) +		return r; +	return amdgpu_display_resume_helper(adev);  }  static bool dce_virtual_is_idle(void *handle) |