2014-11-14 08:52:28 -08:00
/*
* Copyright © 2014 Intel Corporation
*
* Permission is hereby granted , free of charge , to any person obtaining a
* copy of this software and associated documentation files ( the " Software " ) ,
* to deal in the Software without restriction , including without limitation
* the rights to use , copy , modify , merge , publish , distribute , sublicense ,
* and / or sell copies of the Software , and to permit persons to whom the
* Software is furnished to do so , subject to the following conditions :
*
* The above copyright notice and this permission notice ( including the next
* paragraph ) shall be included in all copies or substantial portions of the
* Software .
*
* THE SOFTWARE IS PROVIDED " AS IS " , WITHOUT WARRANTY OF ANY KIND , EXPRESS OR
* IMPLIED , INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY ,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT . IN NO EVENT SHALL
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM , DAMAGES OR OTHER
* LIABILITY , WHETHER IN AN ACTION OF CONTRACT , TORT OR OTHERWISE , ARISING
* FROM , OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE .
*/
2014-11-14 08:52:29 -08:00
/**
* DOC : Panel Self Refresh ( PSR / SRD )
*
* Since Haswell Display controller supports Panel Self - Refresh on display
* panels witch have a remote frame buffer ( RFB ) implemented according to PSR
* spec in eDP1 .3 . PSR feature allows the display to go to lower standby states
* when system is idle but display is on as it eliminates display refresh
* request to DDR memory completely as long as the frame buffer for that
* display is unchanged .
*
* Panel Self Refresh must be supported by both Hardware ( source ) and
* Panel ( sink ) .
*
* PSR saves power by caching the framebuffer in the panel RFB , which allows us
* to power down the link and memory controller . For DSI panels the same idea
* is called " manual mode " .
*
* The implementation uses the hardware - based PSR support which automatically
* enters / exits self - refresh mode . The hardware takes care of sending the
* required DP aux message and could even retrain the link ( that part isn ' t
* enabled yet though ) . The hardware also keeps track of any frontbuffer
* changes to know when to exit self - refresh mode again . Unfortunately that
* part doesn ' t work too well , hence why the i915 PSR support uses the
* software frontbuffer tracking to make sure it doesn ' t miss a screen
* update . For this integration intel_psr_invalidate ( ) and intel_psr_flush ( )
* get called by the frontbuffer tracking code . Note that because of locking
* issues the self - refresh re - enable code is done from a work queue , which
* must be correctly synchronized / cancelled when shutting down the pipe . "
*/
2014-11-14 08:52:28 -08:00
# include <drm/drmP.h>
# include "intel_drv.h"
# include "i915_drv.h"
2018-02-23 14:15:15 -08:00
static inline enum intel_display_power_domain
psr_aux_domain ( struct intel_dp * intel_dp )
{
/* CNL HW requires corresponding AUX IOs to be powered up for PSR.
* However , for non - A AUX ports the corresponding non - EDP transcoders
* would have already enabled power well 2 and DC_OFF . This means we can
* acquire a wider POWER_DOMAIN_AUX_ { B , C , D , F } reference instead of a
* specific AUX_IO reference without powering up any extra wells .
* Note that PSR is enabled only on Port A even though this function
* returns the correct domain for other ports too .
*/
return intel_dp - > aux_ch = = AUX_CH_A ? POWER_DOMAIN_AUX_IO_A :
intel_dp - > aux_power_domain ;
}
static void psr_aux_io_power_get ( struct intel_dp * intel_dp )
{
struct intel_digital_port * intel_dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_i915_private * dev_priv = to_i915 ( intel_dig_port - > base . base . dev ) ;
if ( INTEL_GEN ( dev_priv ) < 10 )
return ;
intel_display_power_get ( dev_priv , psr_aux_domain ( intel_dp ) ) ;
}
static void psr_aux_io_power_put ( struct intel_dp * intel_dp )
{
struct intel_digital_port * intel_dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_i915_private * dev_priv = to_i915 ( intel_dig_port - > base . base . dev ) ;
if ( INTEL_GEN ( dev_priv ) < 10 )
return ;
intel_display_power_put ( dev_priv , psr_aux_domain ( intel_dp ) ) ;
}
2018-04-04 18:37:17 -07:00
void intel_psr_irq_control ( struct drm_i915_private * dev_priv , bool debug )
{
u32 debug_mask , mask ;
/* No PSR interrupts on VLV/CHV */
if ( IS_VALLEYVIEW ( dev_priv ) | | IS_CHERRYVIEW ( dev_priv ) )
return ;
mask = EDP_PSR_ERROR ( TRANSCODER_EDP ) ;
debug_mask = EDP_PSR_POST_EXIT ( TRANSCODER_EDP ) |
EDP_PSR_PRE_ENTRY ( TRANSCODER_EDP ) ;
if ( INTEL_GEN ( dev_priv ) > = 8 ) {
mask | = EDP_PSR_ERROR ( TRANSCODER_A ) |
EDP_PSR_ERROR ( TRANSCODER_B ) |
EDP_PSR_ERROR ( TRANSCODER_C ) ;
debug_mask | = EDP_PSR_POST_EXIT ( TRANSCODER_A ) |
EDP_PSR_PRE_ENTRY ( TRANSCODER_A ) |
EDP_PSR_POST_EXIT ( TRANSCODER_B ) |
EDP_PSR_PRE_ENTRY ( TRANSCODER_B ) |
EDP_PSR_POST_EXIT ( TRANSCODER_C ) |
EDP_PSR_PRE_ENTRY ( TRANSCODER_C ) ;
}
if ( debug )
mask | = debug_mask ;
WRITE_ONCE ( dev_priv - > psr . debug , debug ) ;
I915_WRITE ( EDP_PSR_IMR , ~ mask ) ;
}
void intel_psr_irq_handler ( struct drm_i915_private * dev_priv , u32 psr_iir )
{
u32 transcoders = BIT ( TRANSCODER_EDP ) ;
enum transcoder cpu_transcoder ;
2018-04-03 14:24:20 -07:00
ktime_t time_ns = ktime_get ( ) ;
2018-04-04 18:37:17 -07:00
if ( INTEL_GEN ( dev_priv ) > = 8 )
transcoders | = BIT ( TRANSCODER_A ) |
BIT ( TRANSCODER_B ) |
BIT ( TRANSCODER_C ) ;
for_each_cpu_transcoder_masked ( dev_priv , cpu_transcoder , transcoders ) {
/* FIXME: Exit PSR and link train manually when this happens. */
if ( psr_iir & EDP_PSR_ERROR ( cpu_transcoder ) )
DRM_DEBUG_KMS ( " [transcoder %s] PSR aux error \n " ,
transcoder_name ( cpu_transcoder ) ) ;
2018-04-03 14:24:20 -07:00
if ( psr_iir & EDP_PSR_PRE_ENTRY ( cpu_transcoder ) ) {
dev_priv - > psr . last_entry_attempt = time_ns ;
2018-04-04 18:37:17 -07:00
DRM_DEBUG_KMS ( " [transcoder %s] PSR entry attempt in 2 vblanks \n " ,
transcoder_name ( cpu_transcoder ) ) ;
2018-04-03 14:24:20 -07:00
}
2018-04-04 18:37:17 -07:00
2018-04-03 14:24:20 -07:00
if ( psr_iir & EDP_PSR_POST_EXIT ( cpu_transcoder ) ) {
dev_priv - > psr . last_exit = time_ns ;
2018-04-04 18:37:17 -07:00
DRM_DEBUG_KMS ( " [transcoder %s] PSR exit completed \n " ,
transcoder_name ( cpu_transcoder ) ) ;
2018-04-03 14:24:20 -07:00
}
2018-04-04 18:37:17 -07:00
}
}
2018-03-28 15:30:40 -07:00
static bool intel_dp_get_y_coord_required ( struct intel_dp * intel_dp )
2018-02-23 14:15:17 -08:00
{
uint8_t psr_caps = 0 ;
if ( drm_dp_dpcd_readb ( & intel_dp - > aux , DP_PSR_CAPS , & psr_caps ) ! = 1 )
return false ;
return psr_caps & DP_PSR2_SU_Y_COORDINATE_REQUIRED ;
}
static bool intel_dp_get_colorimetry_status ( struct intel_dp * intel_dp )
{
uint8_t dprx = 0 ;
if ( drm_dp_dpcd_readb ( & intel_dp - > aux , DP_DPRX_FEATURE_ENUMERATION_LIST ,
& dprx ) ! = 1 )
return false ;
return dprx & DP_VSC_SDP_EXT_FOR_COLORIMETRY_SUPPORTED ;
}
static bool intel_dp_get_alpm_status ( struct intel_dp * intel_dp )
{
uint8_t alpm_caps = 0 ;
if ( drm_dp_dpcd_readb ( & intel_dp - > aux , DP_RECEIVER_ALPM_CAP ,
& alpm_caps ) ! = 1 )
return false ;
return alpm_caps & DP_ALPM_CAP ;
}
2018-03-28 15:30:44 -07:00
static u8 intel_dp_get_sink_sync_latency ( struct intel_dp * intel_dp )
{
u8 val = 0 ;
if ( drm_dp_dpcd_readb ( & intel_dp - > aux ,
DP_SYNCHRONIZATION_LATENCY_IN_SINK , & val ) = = 1 )
val & = DP_MAX_RESYNC_FRAME_COUNT_MASK ;
else
DRM_ERROR ( " Unable to get sink synchronization latency \n " ) ;
return val ;
}
2018-02-23 14:15:17 -08:00
void intel_psr_init_dpcd ( struct intel_dp * intel_dp )
{
struct drm_i915_private * dev_priv =
to_i915 ( dp_to_dig_port ( intel_dp ) - > base . base . dev ) ;
drm_dp_dpcd_read ( & intel_dp - > aux , DP_PSR_SUPPORT , intel_dp - > psr_dpcd ,
sizeof ( intel_dp - > psr_dpcd ) ) ;
2018-03-28 15:30:40 -07:00
if ( intel_dp - > psr_dpcd [ 0 ] ) {
2018-02-23 14:15:17 -08:00
dev_priv - > psr . sink_support = true ;
DRM_DEBUG_KMS ( " Detected EDP PSR Panel. \n " ) ;
}
if ( INTEL_GEN ( dev_priv ) > = 9 & &
2018-03-28 15:30:40 -07:00
( intel_dp - > psr_dpcd [ 0 ] = = DP_PSR2_WITH_Y_COORD_IS_SUPPORTED ) ) {
/*
* All panels that supports PSR version 03 h ( PSR2 +
* Y - coordinate ) can handle Y - coordinates in VSC but we are
* only sure that it is going to be used when required by the
* panel . This way panel is capable to do selective update
* without a aux frame sync .
*
* To support PSR version 02 h and PSR version 03 h without
* Y - coordinate requirement panels we would need to enable
* GTC first .
*/
2018-03-28 15:30:42 -07:00
dev_priv - > psr . sink_psr2_support =
intel_dp_get_y_coord_required ( intel_dp ) ;
DRM_DEBUG_KMS ( " PSR2 %s on sink " , dev_priv - > psr . sink_psr2_support
? " supported " : " not supported " ) ;
2018-02-23 14:15:17 -08:00
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . sink_psr2_support ) {
2018-02-23 14:15:17 -08:00
dev_priv - > psr . colorimetry_support =
intel_dp_get_colorimetry_status ( intel_dp ) ;
dev_priv - > psr . alpm =
intel_dp_get_alpm_status ( intel_dp ) ;
2018-03-28 15:30:44 -07:00
dev_priv - > psr . sink_sync_latency =
intel_dp_get_sink_sync_latency ( intel_dp ) ;
2018-02-23 14:15:17 -08:00
}
}
}
2014-11-19 07:37:00 -08:00
static bool vlv_is_psr_active_on_pipe ( struct drm_device * dev , int pipe )
{
2016-07-04 11:34:36 +01:00
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
2014-11-19 07:37:00 -08:00
uint32_t val ;
val = I915_READ ( VLV_PSRSTAT ( pipe ) ) &
VLV_EDP_PSR_CURR_STATE_MASK ;
return ( val = = VLV_EDP_PSR_ACTIVE_NORFB_UP ) | |
( val = = VLV_EDP_PSR_ACTIVE_SF_UPDATE ) ;
}
2017-08-18 16:49:56 +03:00
static void vlv_psr_setup_vsc ( struct intel_dp * intel_dp ,
const struct intel_crtc_state * crtc_state )
2014-11-19 07:37:00 -08:00
{
2017-08-18 16:49:56 +03:00
struct intel_crtc * crtc = to_intel_crtc ( crtc_state - > base . crtc ) ;
struct drm_i915_private * dev_priv = to_i915 ( crtc - > base . dev ) ;
2014-11-19 07:37:00 -08:00
uint32_t val ;
/* VLV auto-generate VSC package as per EDP 1.3 spec, Table 3.10 */
2017-08-18 16:49:56 +03:00
val = I915_READ ( VLV_VSCSDP ( crtc - > pipe ) ) ;
2014-11-19 07:37:00 -08:00
val & = ~ VLV_EDP_PSR_SDP_FREQ_MASK ;
val | = VLV_EDP_PSR_SDP_FREQ_EVFRAME ;
2017-08-18 16:49:56 +03:00
I915_WRITE ( VLV_VSCSDP ( crtc - > pipe ) , val ) ;
2014-11-19 07:37:00 -08:00
}
2017-09-07 16:00:35 -07:00
static void hsw_psr_setup_vsc ( struct intel_dp * intel_dp ,
const struct intel_crtc_state * crtc_state )
2015-04-02 11:02:44 +05:30
{
2017-01-02 17:00:55 +05:30
struct intel_digital_port * intel_dig_port = dp_to_dig_port ( intel_dp ) ;
2017-08-18 16:49:56 +03:00
struct drm_i915_private * dev_priv = to_i915 ( intel_dig_port - > base . base . dev ) ;
struct edp_vsc_psr psr_vsc ;
2015-04-02 11:02:44 +05:30
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . psr2_enabled ) {
2017-09-07 16:00:35 -07:00
/* Prepare VSC Header for SU as per EDP 1.4 spec, Table 6.11 */
memset ( & psr_vsc , 0 , sizeof ( psr_vsc ) ) ;
psr_vsc . sdp_header . HB0 = 0 ;
psr_vsc . sdp_header . HB1 = 0x7 ;
2018-03-28 15:30:40 -07:00
if ( dev_priv - > psr . colorimetry_support ) {
2017-09-07 16:00:35 -07:00
psr_vsc . sdp_header . HB2 = 0x5 ;
psr_vsc . sdp_header . HB3 = 0x13 ;
2018-03-28 15:30:40 -07:00
} else {
2017-09-07 16:00:35 -07:00
psr_vsc . sdp_header . HB2 = 0x4 ;
psr_vsc . sdp_header . HB3 = 0xe ;
}
2017-01-02 17:00:55 +05:30
} else {
2017-09-07 16:00:35 -07:00
/* Prepare VSC packet as per EDP 1.3 spec, Table 3.10 */
memset ( & psr_vsc , 0 , sizeof ( psr_vsc ) ) ;
psr_vsc . sdp_header . HB0 = 0 ;
psr_vsc . sdp_header . HB1 = 0x7 ;
psr_vsc . sdp_header . HB2 = 0x2 ;
psr_vsc . sdp_header . HB3 = 0x8 ;
2017-01-02 17:00:55 +05:30
}
2017-10-13 22:40:51 +03:00
intel_dig_port - > write_infoframe ( & intel_dig_port - > base . base , crtc_state ,
DP_SDP_VSC , & psr_vsc , sizeof ( psr_vsc ) ) ;
2015-04-02 11:02:44 +05:30
}
2014-11-19 07:37:00 -08:00
static void vlv_psr_enable_sink ( struct intel_dp * intel_dp )
{
drm_dp_dpcd_writeb ( & intel_dp - > aux , DP_PSR_EN_CFG ,
2015-03-27 17:21:32 +05:30
DP_PSR_ENABLE | DP_PSR_MAIN_LINK_ACTIVE ) ;
2014-11-19 07:37:00 -08:00
}
2018-03-12 20:46:45 -07:00
static void hsw_psr_setup_aux ( struct intel_dp * intel_dp )
2014-11-14 08:52:28 -08:00
{
struct intel_digital_port * dig_port = dp_to_dig_port ( intel_dp ) ;
2018-03-12 20:46:46 -07:00
struct drm_i915_private * dev_priv = to_i915 ( dig_port - > base . base . dev ) ;
u32 aux_clock_divider , aux_ctl ;
int i ;
2014-11-14 08:52:28 -08:00
static const uint8_t aux_msg [ ] = {
[ 0 ] = DP_AUX_NATIVE_WRITE < < 4 ,
[ 1 ] = DP_SET_POWER > > 8 ,
[ 2 ] = DP_SET_POWER & 0xff ,
[ 3 ] = 1 - 1 ,
[ 4 ] = DP_SET_POWER_D0 ,
} ;
2018-03-12 20:46:46 -07:00
u32 psr_aux_mask = EDP_PSR_AUX_CTL_TIME_OUT_MASK |
EDP_PSR_AUX_CTL_MESSAGE_SIZE_MASK |
EDP_PSR_AUX_CTL_PRECHARGE_2US_MASK |
EDP_PSR_AUX_CTL_BIT_CLOCK_2X_MASK ;
2014-11-14 08:52:28 -08:00
BUILD_BUG_ON ( sizeof ( aux_msg ) > 20 ) ;
2018-03-12 20:46:45 -07:00
for ( i = 0 ; i < sizeof ( aux_msg ) ; i + = 4 )
2018-03-12 20:46:46 -07:00
I915_WRITE ( EDP_PSR_AUX_DATA ( i > > 2 ) ,
2018-03-12 20:46:45 -07:00
intel_dp_pack_aux ( & aux_msg [ i ] , sizeof ( aux_msg ) - i ) ) ;
2018-03-12 20:46:46 -07:00
aux_clock_divider = intel_dp - > get_aux_clock_divider ( intel_dp , 0 ) ;
/* Start with bits set for DDI_AUX_CTL register */
2018-03-12 20:46:45 -07:00
aux_ctl = intel_dp - > get_aux_send_ctl ( intel_dp , 0 , sizeof ( aux_msg ) ,
aux_clock_divider ) ;
2018-03-12 20:46:46 -07:00
/* Select only valid bits for SRD_AUX_CTL */
aux_ctl & = psr_aux_mask ;
I915_WRITE ( EDP_PSR_AUX_CTL , aux_ctl ) ;
2018-03-12 20:46:45 -07:00
}
static void hsw_psr_enable_sink ( struct intel_dp * intel_dp )
{
struct intel_digital_port * dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = dig_port - > base . base . dev ;
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
2018-03-28 15:30:45 -07:00
u8 dpcd_val = DP_PSR_ENABLE ;
2018-03-12 20:46:45 -07:00
2017-01-02 17:00:58 +05:30
/* Enable ALPM at sink for psr2 */
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . psr2_enabled & & dev_priv - > psr . alpm )
2017-01-02 17:00:58 +05:30
drm_dp_dpcd_writeb ( & intel_dp - > aux ,
DP_RECEIVER_ALPM_CONFIG ,
DP_ALPM_ENABLE ) ;
2018-03-28 15:30:45 -07:00
if ( dev_priv - > psr . psr2_enabled )
dpcd_val | = DP_PSR_ENABLE_PSR2 ;
2016-05-18 18:47:14 +02:00
if ( dev_priv - > psr . link_standby )
2018-03-28 15:30:45 -07:00
dpcd_val | = DP_PSR_MAIN_LINK_ACTIVE ;
drm_dp_dpcd_writeb ( & intel_dp - > aux , DP_PSR_EN_CFG , dpcd_val ) ;
2016-05-18 18:47:14 +02:00
2018-03-12 20:46:46 -07:00
drm_dp_dpcd_writeb ( & intel_dp - > aux , DP_SET_POWER , DP_SET_POWER_D0 ) ;
2014-11-14 08:52:28 -08:00
}
2017-08-18 16:49:56 +03:00
static void vlv_psr_enable_source ( struct intel_dp * intel_dp ,
const struct intel_crtc_state * crtc_state )
2014-11-19 07:37:00 -08:00
{
struct intel_digital_port * dig_port = dp_to_dig_port ( intel_dp ) ;
2017-08-18 16:49:56 +03:00
struct drm_i915_private * dev_priv = to_i915 ( dig_port - > base . base . dev ) ;
struct intel_crtc * crtc = to_intel_crtc ( crtc_state - > base . crtc ) ;
2014-11-19 07:37:00 -08:00
2017-09-12 11:30:59 -07:00
/* Transition from PSR_state 0 (disabled) to PSR_state 1 (inactive) */
2017-08-18 16:49:56 +03:00
I915_WRITE ( VLV_PSRCTL ( crtc - > pipe ) ,
2014-11-19 07:37:00 -08:00
VLV_EDP_PSR_MODE_SW_TIMER |
VLV_EDP_PSR_SRC_TRANSMITTER_STATE |
VLV_EDP_PSR_ENABLE ) ;
}
2014-11-19 07:37:47 -08:00
static void vlv_psr_activate ( struct intel_dp * intel_dp )
{
struct intel_digital_port * dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = dig_port - > base . base . dev ;
2016-07-04 11:34:36 +01:00
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
2014-11-19 07:37:47 -08:00
struct drm_crtc * crtc = dig_port - > base . base . crtc ;
enum pipe pipe = to_intel_crtc ( crtc ) - > pipe ;
2017-09-12 11:30:59 -07:00
/*
* Let ' s do the transition from PSR_state 1 ( inactive ) to
* PSR_state 2 ( transition to active - static frame transmission ) .
* Then Hardware is responsible for the transition to
* PSR_state 3 ( active - no Remote Frame Buffer ( RFB ) update ) .
2014-11-19 07:37:47 -08:00
*/
I915_WRITE ( VLV_PSRCTL ( pipe ) , I915_READ ( VLV_PSRCTL ( pipe ) ) |
VLV_EDP_PSR_ACTIVE_ENTRY ) ;
}
2017-09-07 16:00:33 -07:00
static void hsw_activate_psr1 ( struct intel_dp * intel_dp )
2014-11-14 08:52:28 -08:00
{
struct intel_digital_port * dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = dig_port - > base . base . dev ;
2016-07-04 11:34:36 +01:00
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
2015-04-02 11:02:44 +05:30
2014-11-14 08:52:28 -08:00
uint32_t max_sleep_time = 0x1f ;
2016-09-07 17:42:31 -07:00
/*
* Let ' s respect VBT in case VBT asks a higher idle_frame value .
* Let ' s use 6 as the minimum to cover all known cases including
* the off - by - one issue that HW has in some cases . Also there are
* cases where sink should be able to train
* with the 5 or 6 idle patterns .
2014-11-14 08:52:31 -08:00
*/
2016-09-07 17:42:31 -07:00
uint32_t idle_frames = max ( 6 , dev_priv - > vbt . psr . idle_frames ) ;
2016-05-18 18:47:11 +02:00
uint32_t val = EDP_PSR_ENABLE ;
val | = max_sleep_time < < EDP_PSR_MAX_SLEEP_TIME_SHIFT ;
val | = idle_frames < < EDP_PSR_IDLE_FRAME_SHIFT ;
2015-12-11 16:31:31 -08:00
2016-10-13 11:03:01 +01:00
if ( IS_HASWELL ( dev_priv ) )
2015-12-11 16:31:31 -08:00
val | = EDP_PSR_MIN_LINK_ENTRY_TIME_8_LINES ;
2014-11-14 08:52:28 -08:00
2016-02-01 12:02:07 -08:00
if ( dev_priv - > psr . link_standby )
val | = EDP_PSR_LINK_STANDBY ;
2016-05-18 18:47:11 +02:00
if ( dev_priv - > vbt . psr . tp1_wakeup_time > 5 )
val | = EDP_PSR_TP1_TIME_2500us ;
else if ( dev_priv - > vbt . psr . tp1_wakeup_time > 1 )
val | = EDP_PSR_TP1_TIME_500us ;
else if ( dev_priv - > vbt . psr . tp1_wakeup_time > 0 )
val | = EDP_PSR_TP1_TIME_100us ;
else
val | = EDP_PSR_TP1_TIME_0us ;
if ( dev_priv - > vbt . psr . tp2_tp3_wakeup_time > 5 )
val | = EDP_PSR_TP2_TP3_TIME_2500us ;
else if ( dev_priv - > vbt . psr . tp2_tp3_wakeup_time > 1 )
val | = EDP_PSR_TP2_TP3_TIME_500us ;
else if ( dev_priv - > vbt . psr . tp2_tp3_wakeup_time > 0 )
val | = EDP_PSR_TP2_TP3_TIME_100us ;
else
val | = EDP_PSR_TP2_TP3_TIME_0us ;
if ( intel_dp_source_supports_hbr2 ( intel_dp ) & &
drm_dp_tps3_supported ( intel_dp - > dpcd ) )
val | = EDP_PSR_TP1_TP3_SEL ;
else
val | = EDP_PSR_TP1_TP2_SEL ;
2017-08-08 14:51:34 -07:00
val | = I915_READ ( EDP_PSR_CTL ) & EDP_PSR_RESTORE_PSR_ACTIVE_CTX_MASK ;
2016-05-18 18:47:11 +02:00
I915_WRITE ( EDP_PSR_CTL , val ) ;
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
}
2016-05-18 18:47:11 +02:00
2017-09-07 16:00:33 -07:00
static void hsw_activate_psr2 ( struct intel_dp * intel_dp )
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
{
struct intel_digital_port * dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = dig_port - > base . base . dev ;
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
/*
* Let ' s respect VBT in case VBT asks a higher idle_frame value .
* Let ' s use 6 as the minimum to cover all known cases including
* the off - by - one issue that HW has in some cases . Also there are
* cases where sink should be able to train
* with the 5 or 6 idle patterns .
*/
uint32_t idle_frames = max ( 6 , dev_priv - > vbt . psr . idle_frames ) ;
2018-03-28 15:30:44 -07:00
u32 val = idle_frames < < EDP_PSR2_IDLE_FRAME_SHIFT ;
2016-05-18 18:47:11 +02:00
/* FIXME: selective update is probably totally broken because it doesn't
* mesh at all with our frontbuffer tracking . And the hw alone isn ' t
* good enough . */
2018-03-28 15:30:41 -07:00
val | = EDP_PSR2_ENABLE | EDP_SU_TRACK_ENABLE ;
if ( INTEL_GEN ( dev_priv ) > = 10 | | IS_GEMINILAKE ( dev_priv ) ) {
val | = EDP_Y_COORDINATE_VALID | EDP_Y_COORDINATE_ENABLE ;
}
2017-09-26 15:29:13 +05:30
2018-03-28 15:30:44 -07:00
val | = EDP_PSR2_FRAME_BEFORE_SU ( dev_priv - > psr . sink_sync_latency + 1 ) ;
2016-05-18 18:47:11 +02:00
if ( dev_priv - > vbt . psr . tp2_tp3_wakeup_time > 5 )
val | = EDP_PSR2_TP2_TIME_2500 ;
else if ( dev_priv - > vbt . psr . tp2_tp3_wakeup_time > 1 )
val | = EDP_PSR2_TP2_TIME_500 ;
else if ( dev_priv - > vbt . psr . tp2_tp3_wakeup_time > 0 )
val | = EDP_PSR2_TP2_TIME_100 ;
else
val | = EDP_PSR2_TP2_TIME_50 ;
2015-04-02 11:02:44 +05:30
2016-05-18 18:47:11 +02:00
I915_WRITE ( EDP_PSR2_CTL , val ) ;
2014-11-14 08:52:28 -08:00
}
2017-09-07 16:00:33 -07:00
static void hsw_psr_activate ( struct intel_dp * intel_dp )
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
{
struct intel_digital_port * dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = dig_port - > base . base . dev ;
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
2017-09-07 16:00:33 -07:00
/* On HSW+ after we enable PSR on source it will activate it
* as soon as it match configure idle_frame count . So
* we just actually enable it here on activation time .
*/
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
/* psr1 and psr2 are mutually exclusive.*/
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . psr2_enabled )
2017-09-07 16:00:33 -07:00
hsw_activate_psr2 ( intel_dp ) ;
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
else
2017-09-07 16:00:33 -07:00
hsw_activate_psr1 ( intel_dp ) ;
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
}
2018-02-27 13:29:13 -08:00
static bool intel_psr2_config_valid ( struct intel_dp * intel_dp ,
struct intel_crtc_state * crtc_state )
{
struct intel_digital_port * dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_i915_private * dev_priv = to_i915 ( dig_port - > base . base . dev ) ;
2018-03-06 12:33:55 -08:00
int crtc_hdisplay = crtc_state - > base . adjusted_mode . crtc_hdisplay ;
int crtc_vdisplay = crtc_state - > base . adjusted_mode . crtc_vdisplay ;
int psr_max_h = 0 , psr_max_v = 0 ;
2018-02-27 13:29:13 -08:00
/*
* FIXME psr2_support is messed up . It ' s both computed
* dynamically during PSR enable , and extracted from sink
* caps during eDP detection .
*/
2018-03-28 15:30:42 -07:00
if ( ! dev_priv - > psr . sink_psr2_support )
2018-02-27 13:29:13 -08:00
return false ;
2018-03-06 12:33:55 -08:00
if ( INTEL_GEN ( dev_priv ) > = 10 | | IS_GEMINILAKE ( dev_priv ) ) {
psr_max_h = 4096 ;
psr_max_v = 2304 ;
} else if ( IS_GEN9 ( dev_priv ) ) {
psr_max_h = 3640 ;
psr_max_v = 2304 ;
}
if ( crtc_hdisplay > psr_max_h | | crtc_vdisplay > psr_max_v ) {
DRM_DEBUG_KMS ( " PSR2 not enabled, resolution %dx%d > max supported %dx%d \n " ,
crtc_hdisplay , crtc_vdisplay ,
psr_max_h , psr_max_v ) ;
2018-02-27 13:29:13 -08:00
return false ;
}
return true ;
}
2017-10-12 16:02:01 +03:00
void intel_psr_compute_config ( struct intel_dp * intel_dp ,
struct intel_crtc_state * crtc_state )
2014-11-14 08:52:28 -08:00
{
struct intel_digital_port * dig_port = dp_to_dig_port ( intel_dp ) ;
2017-10-12 16:02:01 +03:00
struct drm_i915_private * dev_priv = to_i915 ( dig_port - > base . base . dev ) ;
2016-05-18 11:34:38 +03:00
const struct drm_display_mode * adjusted_mode =
2017-10-12 16:02:01 +03:00
& crtc_state - > base . adjusted_mode ;
2016-05-18 11:34:38 +03:00
int psr_setup_time ;
2014-11-14 08:52:28 -08:00
2018-01-03 13:38:23 -08:00
if ( ! CAN_PSR ( dev_priv ) )
2017-10-12 16:02:01 +03:00
return ;
if ( ! i915_modparams . enable_psr ) {
DRM_DEBUG_KMS ( " PSR disable by flag \n " ) ;
return ;
}
2014-11-14 08:52:28 -08:00
2016-02-01 12:02:06 -08:00
/*
* HSW spec explicitly says PSR is tied to port A .
* BDW + platforms with DDI implementation of PSR have different
* PSR registers per transcoder and we only implement transcoder EDP
* ones . Since by Display design transcoder EDP is tied to port A
* we can safely escape based on the port A .
*/
2017-11-09 17:24:34 +02:00
if ( HAS_DDI ( dev_priv ) & & dig_port - > base . port ! = PORT_A ) {
2016-02-01 12:02:06 -08:00
DRM_DEBUG_KMS ( " PSR condition failed: Port not supported \n " ) ;
2017-10-12 16:02:01 +03:00
return ;
2014-11-14 08:52:28 -08:00
}
2016-10-14 10:13:44 +01:00
if ( ( IS_VALLEYVIEW ( dev_priv ) | | IS_CHERRYVIEW ( dev_priv ) ) & &
2016-02-01 12:02:08 -08:00
! dev_priv - > psr . link_standby ) {
DRM_ERROR ( " PSR condition failed: Link off requested but not supported on this platform \n " ) ;
2017-10-12 16:02:01 +03:00
return ;
2016-02-01 12:02:08 -08:00
}
2016-10-13 11:03:01 +01:00
if ( IS_HASWELL ( dev_priv ) & &
2017-10-12 16:02:01 +03:00
I915_READ ( HSW_STEREO_3D_CTL ( crtc_state - > cpu_transcoder ) ) &
2015-01-12 10:14:29 -08:00
S3D_ENABLE ) {
2014-11-14 08:52:28 -08:00
DRM_DEBUG_KMS ( " PSR condition failed: Stereo 3D is Enabled \n " ) ;
2017-10-12 16:02:01 +03:00
return ;
2014-11-14 08:52:28 -08:00
}
2016-10-13 11:03:01 +01:00
if ( IS_HASWELL ( dev_priv ) & &
2016-05-18 11:34:38 +03:00
adjusted_mode - > flags & DRM_MODE_FLAG_INTERLACE ) {
2014-11-14 08:52:28 -08:00
DRM_DEBUG_KMS ( " PSR condition failed: Interlaced is Enabled \n " ) ;
2017-10-12 16:02:01 +03:00
return ;
2014-11-14 08:52:28 -08:00
}
2016-05-18 11:34:38 +03:00
psr_setup_time = drm_dp_psr_setup_time ( intel_dp - > psr_dpcd ) ;
if ( psr_setup_time < 0 ) {
DRM_DEBUG_KMS ( " PSR condition failed: Invalid PSR setup time (0x%02x) \n " ,
intel_dp - > psr_dpcd [ 1 ] ) ;
2017-10-12 16:02:01 +03:00
return ;
2016-05-18 11:34:38 +03:00
}
if ( intel_usecs_to_scanlines ( adjusted_mode , psr_setup_time ) >
adjusted_mode - > crtc_vtotal - adjusted_mode - > crtc_vdisplay - 1 ) {
DRM_DEBUG_KMS ( " PSR condition failed: PSR setup time (%d us) too long \n " ,
psr_setup_time ) ;
2017-10-12 16:02:01 +03:00
return ;
}
2018-02-26 19:27:23 -08:00
if ( ! ( intel_dp - > edp_dpcd [ 1 ] & DP_EDP_SET_POWER_CAP ) ) {
DRM_DEBUG_KMS ( " PSR condition failed: panel lacks power state control \n " ) ;
return ;
}
2017-10-12 16:02:01 +03:00
crtc_state - > has_psr = true ;
2018-02-27 13:29:13 -08:00
crtc_state - > has_psr2 = intel_psr2_config_valid ( intel_dp , crtc_state ) ;
DRM_DEBUG_KMS ( " Enabling PSR%s \n " , crtc_state - > has_psr2 ? " 2 " : " " ) ;
2014-11-14 08:52:28 -08:00
}
2014-11-19 07:37:00 -08:00
static void intel_psr_activate ( struct intel_dp * intel_dp )
2014-11-14 08:52:28 -08:00
{
struct intel_digital_port * intel_dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = intel_dig_port - > base . base . dev ;
2016-07-04 11:34:36 +01:00
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
2014-11-14 08:52:28 -08:00
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . psr2_enabled )
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
WARN_ON ( I915_READ ( EDP_PSR2_CTL ) & EDP_PSR2_ENABLE ) ;
else
WARN_ON ( I915_READ ( EDP_PSR_CTL ) & EDP_PSR_ENABLE ) ;
2014-11-14 08:52:28 -08:00
WARN_ON ( dev_priv - > psr . active ) ;
lockdep_assert_held ( & dev_priv - > psr . lock ) ;
2017-09-07 16:00:34 -07:00
dev_priv - > psr . activate ( intel_dp ) ;
2014-11-14 08:52:28 -08:00
dev_priv - > psr . active = true ;
}
2017-09-07 16:00:36 -07:00
static void hsw_psr_enable_source ( struct intel_dp * intel_dp ,
const struct intel_crtc_state * crtc_state )
{
struct intel_digital_port * dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = dig_port - > base . base . dev ;
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
enum transcoder cpu_transcoder = crtc_state - > cpu_transcoder ;
2018-02-23 14:15:15 -08:00
psr_aux_io_power_get ( intel_dp ) ;
2018-03-12 20:46:46 -07:00
/* Only HSW and BDW have PSR AUX registers that need to be setup. SKL+
* use hardcoded values PSR AUX transactions
*/
if ( IS_HASWELL ( dev_priv ) | | IS_BROADWELL ( dev_priv ) )
hsw_psr_setup_aux ( intel_dp ) ;
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . psr2_enabled ) {
2018-03-28 15:30:41 -07:00
u32 chicken = I915_READ ( CHICKEN_TRANS ( cpu_transcoder ) ) ;
if ( INTEL_GEN ( dev_priv ) = = 9 & & ! IS_GEMINILAKE ( dev_priv ) )
chicken | = ( PSR2_VSC_ENABLE_PROG_HEADER
| PSR2_ADD_VERTICAL_LINE_COUNT ) ;
else
chicken & = ~ VSC_DATA_SEL_SOFTWARE_CONTROL ;
2017-09-07 16:00:36 -07:00
I915_WRITE ( CHICKEN_TRANS ( cpu_transcoder ) , chicken ) ;
2017-12-20 12:10:21 -08:00
I915_WRITE ( EDP_PSR_DEBUG ,
2017-09-07 16:00:36 -07:00
EDP_PSR_DEBUG_MASK_MEMUP |
EDP_PSR_DEBUG_MASK_HPD |
EDP_PSR_DEBUG_MASK_LPSP |
EDP_PSR_DEBUG_MASK_MAX_SLEEP |
EDP_PSR_DEBUG_MASK_DISP_REG_WRITE ) ;
} else {
/*
* Per Spec : Avoid continuous PSR exit by masking MEMUP
* and HPD . also mask LPSP to avoid dependency on other
* drivers that might block runtime_pm besides
* preventing other hw tracking issues now we can rely
* on frontbuffer tracking .
*/
2017-12-20 12:10:21 -08:00
I915_WRITE ( EDP_PSR_DEBUG ,
2017-09-07 16:00:36 -07:00
EDP_PSR_DEBUG_MASK_MEMUP |
EDP_PSR_DEBUG_MASK_HPD |
2018-04-25 14:23:31 -07:00
EDP_PSR_DEBUG_MASK_LPSP |
EDP_PSR_DEBUG_MASK_DISP_REG_WRITE ) ;
2017-09-07 16:00:36 -07:00
}
}
2014-11-14 08:52:29 -08:00
/**
* intel_psr_enable - Enable PSR
* @ intel_dp : Intel DP
2017-08-18 16:49:56 +03:00
* @ crtc_state : new CRTC state
2014-11-14 08:52:29 -08:00
*
* This function can only be called after the pipe is fully trained and enabled .
*/
2017-08-18 16:49:56 +03:00
void intel_psr_enable ( struct intel_dp * intel_dp ,
const struct intel_crtc_state * crtc_state )
2014-11-14 08:52:28 -08:00
{
struct intel_digital_port * intel_dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = intel_dig_port - > base . base . dev ;
2016-07-04 11:34:36 +01:00
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
2014-11-14 08:52:28 -08:00
2017-10-12 16:02:01 +03:00
if ( ! crtc_state - > has_psr )
2014-11-14 08:52:28 -08:00
return ;
2018-01-03 13:38:24 -08:00
if ( WARN_ON ( ! CAN_PSR ( dev_priv ) ) )
return ;
2017-09-14 11:16:41 -07:00
WARN_ON ( dev_priv - > drrs . dp ) ;
2014-11-14 08:52:28 -08:00
mutex_lock ( & dev_priv - > psr . lock ) ;
if ( dev_priv - > psr . enabled ) {
DRM_DEBUG_KMS ( " PSR already in use \n " ) ;
goto unlock ;
}
2018-03-28 15:30:42 -07:00
dev_priv - > psr . psr2_enabled = crtc_state - > has_psr2 ;
2014-11-14 08:52:28 -08:00
dev_priv - > psr . busy_frontbuffer_bits = 0 ;
2017-09-07 16:00:39 -07:00
dev_priv - > psr . setup_vsc ( intel_dp , crtc_state ) ;
2017-09-07 16:00:40 -07:00
dev_priv - > psr . enable_sink ( intel_dp ) ;
2017-09-07 16:00:41 -07:00
dev_priv - > psr . enable_source ( intel_dp , crtc_state ) ;
2017-09-07 16:00:38 -07:00
dev_priv - > psr . enabled = intel_dp ;
if ( INTEL_GEN ( dev_priv ) > = 9 ) {
intel_psr_activate ( intel_dp ) ;
} else {
/*
* FIXME : Activation should happen immediately since this
* function is just called after pipe is fully trained and
* enabled .
* However on some platforms we face issues when first
* activation follows a modeset so quickly .
* - On VLV / CHV we get bank screen on first activation
* - On HSW / BDW we get a recoverable frozen screen until
* next exit - activate sequence .
*/
2015-11-11 11:37:07 -08:00
schedule_delayed_work ( & dev_priv - > psr . work ,
msecs_to_jiffies ( intel_dp - > panel_power_cycle_delay * 5 ) ) ;
2017-09-07 16:00:38 -07:00
}
2015-11-11 11:37:07 -08:00
2014-11-14 08:52:28 -08:00
unlock :
mutex_unlock ( & dev_priv - > psr . lock ) ;
}
2017-08-18 16:49:56 +03:00
static void vlv_psr_disable ( struct intel_dp * intel_dp ,
const struct intel_crtc_state * old_crtc_state )
2014-11-14 08:52:28 -08:00
{
struct intel_digital_port * intel_dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = intel_dig_port - > base . base . dev ;
2016-07-04 11:34:36 +01:00
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
2017-08-18 16:49:56 +03:00
struct intel_crtc * crtc = to_intel_crtc ( old_crtc_state - > base . crtc ) ;
2014-11-19 07:37:00 -08:00
uint32_t val ;
2014-11-14 08:52:28 -08:00
2014-11-19 07:37:00 -08:00
if ( dev_priv - > psr . active ) {
2017-09-12 11:30:59 -07:00
/* Put VLV PSR back to PSR_state 0 (disabled). */
2016-06-30 15:33:26 +01:00
if ( intel_wait_for_register ( dev_priv ,
2017-08-18 16:49:56 +03:00
VLV_PSRSTAT ( crtc - > pipe ) ,
2016-06-30 15:33:26 +01:00
VLV_EDP_PSR_IN_TRANS ,
0 ,
1 ) )
2014-11-19 07:37:00 -08:00
WARN ( 1 , " PSR transition took longer than expected \n " ) ;
2017-08-18 16:49:56 +03:00
val = I915_READ ( VLV_PSRCTL ( crtc - > pipe ) ) ;
2014-11-19 07:37:00 -08:00
val & = ~ VLV_EDP_PSR_ACTIVE_ENTRY ;
val & = ~ VLV_EDP_PSR_ENABLE ;
val & = ~ VLV_EDP_PSR_MODE_MASK ;
2017-08-18 16:49:56 +03:00
I915_WRITE ( VLV_PSRCTL ( crtc - > pipe ) , val ) ;
2014-11-19 07:37:00 -08:00
dev_priv - > psr . active = false ;
} else {
2017-08-18 16:49:56 +03:00
WARN_ON ( vlv_is_psr_active_on_pipe ( dev , crtc - > pipe ) ) ;
2014-11-14 08:52:28 -08:00
}
2014-11-19 07:37:00 -08:00
}
2017-08-18 16:49:56 +03:00
static void hsw_psr_disable ( struct intel_dp * intel_dp ,
const struct intel_crtc_state * old_crtc_state )
2014-11-19 07:37:00 -08:00
{
struct intel_digital_port * intel_dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = intel_dig_port - > base . base . dev ;
2016-07-04 11:34:36 +01:00
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
2014-11-14 08:52:28 -08:00
if ( dev_priv - > psr . active ) {
2017-12-19 20:35:20 -08:00
i915_reg_t psr_status ;
2017-01-16 13:06:22 +00:00
u32 psr_status_mask ;
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . psr2_enabled ) {
2017-12-20 12:10:21 -08:00
psr_status = EDP_PSR2_STATUS ;
2017-01-16 13:06:22 +00:00
psr_status_mask = EDP_PSR2_STATUS_STATE_MASK ;
2017-12-19 20:35:20 -08:00
I915_WRITE ( EDP_PSR2_CTL ,
I915_READ ( EDP_PSR2_CTL ) &
2017-01-16 13:06:22 +00:00
~ ( EDP_PSR2_ENABLE | EDP_SU_TRACK_ENABLE ) ) ;
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
} else {
2017-12-20 12:10:21 -08:00
psr_status = EDP_PSR_STATUS ;
2017-01-16 13:06:22 +00:00
psr_status_mask = EDP_PSR_STATUS_STATE_MASK ;
2017-12-19 20:35:20 -08:00
I915_WRITE ( EDP_PSR_CTL ,
I915_READ ( EDP_PSR_CTL ) & ~ EDP_PSR_ENABLE ) ;
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
}
2017-01-16 13:06:22 +00:00
/* Wait till PSR is idle */
if ( intel_wait_for_register ( dev_priv ,
2017-12-19 20:35:20 -08:00
psr_status , psr_status_mask , 0 ,
2017-01-16 13:06:22 +00:00
2000 ) )
DRM_ERROR ( " Timed out waiting for PSR Idle State \n " ) ;
2014-11-14 08:52:28 -08:00
dev_priv - > psr . active = false ;
} else {
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . psr2_enabled )
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
WARN_ON ( I915_READ ( EDP_PSR2_CTL ) & EDP_PSR2_ENABLE ) ;
else
WARN_ON ( I915_READ ( EDP_PSR_CTL ) & EDP_PSR_ENABLE ) ;
2014-11-14 08:52:28 -08:00
}
2018-02-23 14:15:15 -08:00
psr_aux_io_power_put ( intel_dp ) ;
2014-11-19 07:37:00 -08:00
}
/**
* intel_psr_disable - Disable PSR
* @ intel_dp : Intel DP
2017-08-18 16:49:56 +03:00
* @ old_crtc_state : old CRTC state
2014-11-19 07:37:00 -08:00
*
* This function needs to be called before disabling pipe .
*/
2017-08-18 16:49:56 +03:00
void intel_psr_disable ( struct intel_dp * intel_dp ,
const struct intel_crtc_state * old_crtc_state )
2014-11-19 07:37:00 -08:00
{
struct intel_digital_port * intel_dig_port = dp_to_dig_port ( intel_dp ) ;
struct drm_device * dev = intel_dig_port - > base . base . dev ;
2016-07-04 11:34:36 +01:00
struct drm_i915_private * dev_priv = to_i915 ( dev ) ;
2014-11-19 07:37:00 -08:00
2017-10-12 16:02:01 +03:00
if ( ! old_crtc_state - > has_psr )
2017-09-07 16:00:31 -07:00
return ;
2018-01-03 13:38:24 -08:00
if ( WARN_ON ( ! CAN_PSR ( dev_priv ) ) )
return ;
2014-11-19 07:37:00 -08:00
mutex_lock ( & dev_priv - > psr . lock ) ;
if ( ! dev_priv - > psr . enabled ) {
mutex_unlock ( & dev_priv - > psr . lock ) ;
return ;
}
2017-09-07 16:00:32 -07:00
dev_priv - > psr . disable_source ( intel_dp , old_crtc_state ) ;
2014-11-14 08:52:28 -08:00
2015-11-23 14:19:32 -08:00
/* Disable PSR on Sink */
drm_dp_dpcd_writeb ( & intel_dp - > aux , DP_PSR_EN_CFG , 0 ) ;
2014-11-14 08:52:28 -08:00
dev_priv - > psr . enabled = NULL ;
mutex_unlock ( & dev_priv - > psr . lock ) ;
cancel_delayed_work_sync ( & dev_priv - > psr . work ) ;
}
2018-04-05 12:49:15 +01:00
static bool psr_wait_for_idle ( struct drm_i915_private * dev_priv )
2014-11-14 08:52:28 -08:00
{
2018-04-05 12:49:15 +01:00
struct intel_dp * intel_dp ;
i915_reg_t reg ;
u32 mask ;
int err ;
intel_dp = dev_priv - > psr . enabled ;
if ( ! intel_dp )
return false ;
2014-11-14 08:52:28 -08:00
2016-04-07 11:08:05 +03:00
if ( HAS_DDI ( dev_priv ) ) {
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . psr2_enabled ) {
2018-04-05 12:49:15 +01:00
reg = EDP_PSR2_STATUS ;
mask = EDP_PSR2_STATUS_STATE_MASK ;
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
} else {
2018-04-05 12:49:15 +01:00
reg = EDP_PSR_STATUS ;
mask = EDP_PSR_STATUS_STATE_MASK ;
2014-11-19 07:37:47 -08:00
}
} else {
2018-04-05 12:49:15 +01:00
struct drm_crtc * crtc =
dp_to_dig_port ( intel_dp ) - > base . base . crtc ;
enum pipe pipe = to_intel_crtc ( crtc ) - > pipe ;
reg = VLV_PSRSTAT ( pipe ) ;
mask = VLV_EDP_PSR_IN_TRANS ;
2014-11-14 08:52:28 -08:00
}
2018-04-05 12:49:15 +01:00
mutex_unlock ( & dev_priv - > psr . lock ) ;
err = intel_wait_for_register ( dev_priv , reg , mask , 0 , 50 ) ;
if ( err )
DRM_ERROR ( " Timed out waiting for PSR Idle for re-enable \n " ) ;
/* After the unlocked wait, verify that PSR is still wanted! */
2014-11-14 08:52:28 -08:00
mutex_lock ( & dev_priv - > psr . lock ) ;
2018-04-05 12:49:15 +01:00
return err = = 0 & & dev_priv - > psr . enabled ;
}
2014-11-14 08:52:28 -08:00
2018-04-05 12:49:15 +01:00
static void intel_psr_work ( struct work_struct * work )
{
struct drm_i915_private * dev_priv =
container_of ( work , typeof ( * dev_priv ) , psr . work . work ) ;
mutex_lock ( & dev_priv - > psr . lock ) ;
/*
* We have to make sure PSR is ready for re - enable
* otherwise it keeps disabled until next full enable / disable cycle .
* PSR might take some time to get fully disabled
* and be ready for re - enable .
*/
if ( ! psr_wait_for_idle ( dev_priv ) )
2014-11-14 08:52:28 -08:00
goto unlock ;
/*
* The delayed work can race with an invalidate hence we need to
* recheck . Since psr_flush first clears this and then reschedules we
* won ' t ever miss a flush when bailing out here .
*/
if ( dev_priv - > psr . busy_frontbuffer_bits )
goto unlock ;
2018-04-05 12:49:15 +01:00
intel_psr_activate ( dev_priv - > psr . enabled ) ;
2014-11-14 08:52:28 -08:00
unlock :
mutex_unlock ( & dev_priv - > psr . lock ) ;
}
2016-08-04 16:32:38 +01:00
static void intel_psr_exit ( struct drm_i915_private * dev_priv )
2014-11-14 08:52:28 -08:00
{
2014-11-19 07:37:47 -08:00
struct intel_dp * intel_dp = dev_priv - > psr . enabled ;
struct drm_crtc * crtc = dp_to_dig_port ( intel_dp ) - > base . base . crtc ;
enum pipe pipe = to_intel_crtc ( crtc ) - > pipe ;
u32 val ;
2014-11-14 08:52:28 -08:00
2014-11-19 07:37:47 -08:00
if ( ! dev_priv - > psr . active )
return ;
2016-08-04 16:32:38 +01:00
if ( HAS_DDI ( dev_priv ) ) {
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . psr2_enabled ) {
drm/i915/psr: fix blank screen issue for psr2
Psr1 and psr2 are mutually exclusive,ie when psr2 is enabled,
psr1 should be disabled.When psr2 is exited , bit 31 of reg
PSR2_CTL must be set to 0 but currently bit 31 of SRD_CTL
(psr1 control register)is set to 0.
Also ,PSR2_IDLE state is looked up from SRD_STATUS(psr1 register)
instead of PSR2_STATUS register, which has wrong data, resulting
in blankscreen.
hsw_enable_source is split into hsw_enable_source_psr1 and
hsw_enable_source_psr2 for easier code review and maintenance,
as suggested by rodrigo and jim.
v2: (Rodrigo)
- Rename hsw_enable_source_psr* to intel_enable_source_psr*
v3: (Rodrigo)
- In hsw_psr_disable ,
1) for psr active case, handle psr2 followed by psr1.
2) psr inactive case, handle psr2 followed by psr1
v4:(Rodrigo)
- move psr2 restriction(32X20) to match_conditions function
returning false and fully blocking PSR to a new patch before
this one.
v5: in source_psr2, removed val = EDP_PSR_ENABLE
Cc: Rodrigo Vivi <rodrigo.vivi@intel.com>
Cc: Jim Bride <jim.bride@linux.intel.com>
Signed-off-by: Vathsala Nagaraju <vathsala.nagaraju@intel.com>
Signed-off-by: Patil Deepti <deepti.patil@intel.com>
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Signed-off-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
Link: http://patchwork.freedesktop.org/patch/msgid/1484244059-9201-1-git-send-email-vathsala.nagaraju@intel.com
2017-01-12 23:30:59 +05:30
val = I915_READ ( EDP_PSR2_CTL ) ;
WARN_ON ( ! ( val & EDP_PSR2_ENABLE ) ) ;
I915_WRITE ( EDP_PSR2_CTL , val & ~ EDP_PSR2_ENABLE ) ;
} else {
val = I915_READ ( EDP_PSR_CTL ) ;
WARN_ON ( ! ( val & EDP_PSR_ENABLE ) ) ;
I915_WRITE ( EDP_PSR_CTL , val & ~ EDP_PSR_ENABLE ) ;
}
2014-11-19 07:37:47 -08:00
} else {
val = I915_READ ( VLV_PSRCTL ( pipe ) ) ;
2017-09-12 11:30:59 -07:00
/*
* Here we do the transition drirectly from
* PSR_state 3 ( active - no Remote Frame Buffer ( RFB ) update ) to
* PSR_state 5 ( exit ) .
* PSR State 4 ( active with single frame update ) can be skipped .
* On PSR_state 5 ( exit ) Hardware is responsible to transition
* back to PSR_state 1 ( inactive ) .
* Now we are at Same state after vlv_psr_enable_source .
2014-11-19 07:37:47 -08:00
*/
val & = ~ VLV_EDP_PSR_ACTIVE_ENTRY ;
I915_WRITE ( VLV_PSRCTL ( pipe ) , val ) ;
2017-09-12 11:30:59 -07:00
/*
* Send AUX wake up - Spec says after transitioning to PSR
2014-11-19 07:37:47 -08:00
* active we have to send AUX wake up by writing 01 h in DPCD
* 600 h of sink device .
* XXX : This might slow down the transition , but without this
* HW doesn ' t complete the transition to PSR_state 1 and we
* never get the screen updated .
*/
drm_dp_dpcd_writeb ( & intel_dp - > aux , DP_SET_POWER ,
DP_SET_POWER_D0 ) ;
2014-11-14 08:52:28 -08:00
}
2014-11-19 07:37:47 -08:00
dev_priv - > psr . active = false ;
2014-11-14 08:52:28 -08:00
}
2015-04-10 11:15:10 -07:00
/**
* intel_psr_single_frame_update - Single Frame Update
2016-08-04 16:32:38 +01:00
* @ dev_priv : i915 device
2015-06-18 10:30:27 +02:00
* @ frontbuffer_bits : frontbuffer plane tracking bits
2015-04-10 11:15:10 -07:00
*
* Some platforms support a single frame update feature that is used to
* send and update only one frame on Remote Frame Buffer .
* So far it is only implemented for Valleyview and Cherryview because
* hardware requires this to be done before a page flip .
*/
2016-08-04 16:32:38 +01:00
void intel_psr_single_frame_update ( struct drm_i915_private * dev_priv ,
2015-06-18 10:30:27 +02:00
unsigned frontbuffer_bits )
2015-04-10 11:15:10 -07:00
{
struct drm_crtc * crtc ;
enum pipe pipe ;
u32 val ;
2018-01-03 13:38:23 -08:00
if ( ! CAN_PSR ( dev_priv ) )
2017-09-07 16:00:31 -07:00
return ;
2015-04-10 11:15:10 -07:00
/*
* Single frame update is already supported on BDW + but it requires
* many W / A and it isn ' t really needed .
*/
2016-08-04 16:32:38 +01:00
if ( ! IS_VALLEYVIEW ( dev_priv ) & & ! IS_CHERRYVIEW ( dev_priv ) )
2015-04-10 11:15:10 -07:00
return ;
mutex_lock ( & dev_priv - > psr . lock ) ;
if ( ! dev_priv - > psr . enabled ) {
mutex_unlock ( & dev_priv - > psr . lock ) ;
return ;
}
crtc = dp_to_dig_port ( dev_priv - > psr . enabled ) - > base . base . crtc ;
pipe = to_intel_crtc ( crtc ) - > pipe ;
2015-06-18 10:30:27 +02:00
if ( frontbuffer_bits & INTEL_FRONTBUFFER_ALL_MASK ( pipe ) ) {
val = I915_READ ( VLV_PSRCTL ( pipe ) ) ;
2015-04-10 11:15:10 -07:00
2015-06-18 10:30:27 +02:00
/*
* We need to set this bit before writing registers for a flip .
* This bit will be self - clear when it gets to the PSR active state .
*/
I915_WRITE ( VLV_PSRCTL ( pipe ) , val | VLV_EDP_PSR_SINGLE_FRAME_UPDATE ) ;
}
2015-04-10 11:15:10 -07:00
mutex_unlock ( & dev_priv - > psr . lock ) ;
}
2014-11-14 08:52:29 -08:00
/**
* intel_psr_invalidate - Invalidade PSR
2016-08-04 16:32:38 +01:00
* @ dev_priv : i915 device
2014-11-14 08:52:29 -08:00
* @ frontbuffer_bits : frontbuffer plane tracking bits
2018-03-06 19:34:20 -08:00
* @ origin : which operation caused the invalidate
2014-11-14 08:52:29 -08:00
*
* Since the hardware frontbuffer tracking has gaps we need to integrate
* with the software frontbuffer tracking . This function gets called every
* time frontbuffer rendering starts and a buffer gets dirtied . PSR must be
* disabled if the frontbuffer mask contains a buffer relevant to PSR .
*
* Dirty frontbuffers relevant to PSR are tracked in busy_frontbuffer_bits . "
*/
2016-08-04 16:32:38 +01:00
void intel_psr_invalidate ( struct drm_i915_private * dev_priv ,
2018-03-06 19:34:20 -08:00
unsigned frontbuffer_bits , enum fb_op_origin origin )
2014-11-14 08:52:28 -08:00
{
struct drm_crtc * crtc ;
enum pipe pipe ;
2018-01-03 13:38:23 -08:00
if ( ! CAN_PSR ( dev_priv ) )
2017-09-07 16:00:31 -07:00
return ;
2018-03-06 19:34:20 -08:00
if ( dev_priv - > psr . has_hw_tracking & & origin = = ORIGIN_FLIP )
return ;
2014-11-14 08:52:28 -08:00
mutex_lock ( & dev_priv - > psr . lock ) ;
if ( ! dev_priv - > psr . enabled ) {
mutex_unlock ( & dev_priv - > psr . lock ) ;
return ;
}
crtc = dp_to_dig_port ( dev_priv - > psr . enabled ) - > base . base . crtc ;
pipe = to_intel_crtc ( crtc ) - > pipe ;
frontbuffer_bits & = INTEL_FRONTBUFFER_ALL_MASK ( pipe ) ;
dev_priv - > psr . busy_frontbuffer_bits | = frontbuffer_bits ;
2015-06-18 10:30:26 +02:00
if ( frontbuffer_bits )
2016-08-04 16:32:38 +01:00
intel_psr_exit ( dev_priv ) ;
2015-06-18 10:30:26 +02:00
2014-11-14 08:52:28 -08:00
mutex_unlock ( & dev_priv - > psr . lock ) ;
}
2014-11-14 08:52:29 -08:00
/**
* intel_psr_flush - Flush PSR
2016-08-04 16:32:38 +01:00
* @ dev_priv : i915 device
2014-11-14 08:52:29 -08:00
* @ frontbuffer_bits : frontbuffer plane tracking bits
2015-07-08 16:21:31 -07:00
* @ origin : which operation caused the flush
2014-11-14 08:52:29 -08:00
*
* Since the hardware frontbuffer tracking has gaps we need to integrate
* with the software frontbuffer tracking . This function gets called every
* time frontbuffer rendering has completed and flushed out to memory . PSR
* can be enabled again if no other frontbuffer relevant to PSR is dirty .
*
* Dirty frontbuffers relevant to PSR are tracked in busy_frontbuffer_bits .
*/
2016-08-04 16:32:38 +01:00
void intel_psr_flush ( struct drm_i915_private * dev_priv ,
2015-07-08 16:21:31 -07:00
unsigned frontbuffer_bits , enum fb_op_origin origin )
2014-11-14 08:52:28 -08:00
{
struct drm_crtc * crtc ;
enum pipe pipe ;
2018-01-03 13:38:23 -08:00
if ( ! CAN_PSR ( dev_priv ) )
2017-09-07 16:00:31 -07:00
return ;
2018-03-06 19:34:20 -08:00
if ( dev_priv - > psr . has_hw_tracking & & origin = = ORIGIN_FLIP )
return ;
2014-11-14 08:52:28 -08:00
mutex_lock ( & dev_priv - > psr . lock ) ;
if ( ! dev_priv - > psr . enabled ) {
mutex_unlock ( & dev_priv - > psr . lock ) ;
return ;
}
crtc = dp_to_dig_port ( dev_priv - > psr . enabled ) - > base . base . crtc ;
pipe = to_intel_crtc ( crtc ) - > pipe ;
2015-06-18 10:30:26 +02:00
frontbuffer_bits & = INTEL_FRONTBUFFER_ALL_MASK ( pipe ) ;
2014-11-14 08:52:28 -08:00
dev_priv - > psr . busy_frontbuffer_bits & = ~ frontbuffer_bits ;
2015-11-18 11:21:12 -08:00
/* By definition flush = invalidate + flush */
2018-03-08 16:52:18 -08:00
if ( frontbuffer_bits ) {
2018-03-28 15:30:42 -07:00
if ( dev_priv - > psr . psr2_enabled | |
2018-03-08 16:52:18 -08:00
IS_VALLEYVIEW ( dev_priv ) | | IS_CHERRYVIEW ( dev_priv ) ) {
intel_psr_exit ( dev_priv ) ;
} else {
/*
* Display WA # 0884 : all
* This documented WA for bxt can be safely applied
* broadly so we can force HW tracking to exit PSR
* instead of disabling and re - enabling .
2018-03-12 14:05:28 -07:00
* Workaround tells us to write 0 to CUR_SURFLIVE_A ,
2018-03-08 16:52:18 -08:00
* but it makes more sense write to the current active
* pipe .
*/
2018-03-12 14:05:28 -07:00
I915_WRITE ( CURSURFLIVE ( pipe ) , 0 ) ;
2018-03-08 16:52:18 -08:00
}
}
2014-11-19 07:37:47 -08:00
2014-11-14 08:52:28 -08:00
if ( ! dev_priv - > psr . active & & ! dev_priv - > psr . busy_frontbuffer_bits )
2015-11-11 11:37:07 -08:00
if ( ! work_busy ( & dev_priv - > psr . work . work ) )
schedule_delayed_work ( & dev_priv - > psr . work ,
2015-11-11 11:37:08 -08:00
msecs_to_jiffies ( 100 ) ) ;
2014-11-14 08:52:28 -08:00
mutex_unlock ( & dev_priv - > psr . lock ) ;
}
2014-11-14 08:52:29 -08:00
/**
* intel_psr_init - Init basic PSR work and mutex .
2016-11-29 13:48:47 +02:00
* @ dev_priv : i915 device private
2014-11-14 08:52:29 -08:00
*
* This function is called only once at driver load to initialize basic
* PSR stuff .
*/
2016-11-23 16:21:44 +02:00
void intel_psr_init ( struct drm_i915_private * dev_priv )
2014-11-14 08:52:28 -08:00
{
2017-09-07 16:00:31 -07:00
if ( ! HAS_PSR ( dev_priv ) )
return ;
2015-11-11 20:34:15 +02:00
dev_priv - > psr_mmio_base = IS_HASWELL ( dev_priv ) ?
HSW_EDP_PSR_BASE : BDW_EDP_PSR_BASE ;
2018-01-03 13:38:24 -08:00
if ( ! dev_priv - > psr . sink_support )
return ;
2016-12-13 18:57:44 -02:00
/* Per platform default: all disabled. */
2017-09-19 19:38:44 +00:00
if ( i915_modparams . enable_psr = = - 1 )
i915_modparams . enable_psr = 0 ;
2016-02-12 04:08:11 -08:00
2016-02-01 12:02:08 -08:00
/* Set link_standby x link_off defaults */
2016-10-13 11:03:00 +01:00
if ( IS_HASWELL ( dev_priv ) | | IS_BROADWELL ( dev_priv ) )
2016-02-01 12:02:07 -08:00
/* HSW and BDW require workarounds that we don't implement. */
dev_priv - > psr . link_standby = false ;
2016-10-14 10:13:44 +01:00
else if ( IS_VALLEYVIEW ( dev_priv ) | | IS_CHERRYVIEW ( dev_priv ) )
2016-02-01 12:02:07 -08:00
/* On VLV and CHV only standby mode is supported. */
dev_priv - > psr . link_standby = true ;
else
/* For new platforms let's respect VBT back again */
dev_priv - > psr . link_standby = dev_priv - > vbt . psr . full_link ;
2016-02-01 12:02:08 -08:00
/* Override link_standby x link_off defaults */
2017-09-19 19:38:44 +00:00
if ( i915_modparams . enable_psr = = 2 & & ! dev_priv - > psr . link_standby ) {
2016-02-01 12:02:08 -08:00
DRM_DEBUG_KMS ( " PSR: Forcing link standby \n " ) ;
dev_priv - > psr . link_standby = true ;
}
2017-09-19 19:38:44 +00:00
if ( i915_modparams . enable_psr = = 3 & & dev_priv - > psr . link_standby ) {
2016-02-01 12:02:08 -08:00
DRM_DEBUG_KMS ( " PSR: Forcing main link off \n " ) ;
dev_priv - > psr . link_standby = false ;
}
2014-11-14 08:52:28 -08:00
INIT_DELAYED_WORK ( & dev_priv - > psr . work , intel_psr_work ) ;
mutex_init ( & dev_priv - > psr . lock ) ;
2017-09-07 16:00:32 -07:00
if ( IS_VALLEYVIEW ( dev_priv ) | | IS_CHERRYVIEW ( dev_priv ) ) {
2017-09-07 16:00:41 -07:00
dev_priv - > psr . enable_source = vlv_psr_enable_source ;
2017-09-07 16:00:32 -07:00
dev_priv - > psr . disable_source = vlv_psr_disable ;
2017-09-07 16:00:40 -07:00
dev_priv - > psr . enable_sink = vlv_psr_enable_sink ;
2017-09-07 16:00:34 -07:00
dev_priv - > psr . activate = vlv_psr_activate ;
2017-09-07 16:00:39 -07:00
dev_priv - > psr . setup_vsc = vlv_psr_setup_vsc ;
2017-09-07 16:00:32 -07:00
} else {
2018-03-06 19:34:20 -08:00
dev_priv - > psr . has_hw_tracking = true ;
2017-09-07 16:00:41 -07:00
dev_priv - > psr . enable_source = hsw_psr_enable_source ;
2017-09-07 16:00:32 -07:00
dev_priv - > psr . disable_source = hsw_psr_disable ;
2017-09-07 16:00:40 -07:00
dev_priv - > psr . enable_sink = hsw_psr_enable_sink ;
2017-09-07 16:00:34 -07:00
dev_priv - > psr . activate = hsw_psr_activate ;
2017-09-07 16:00:39 -07:00
dev_priv - > psr . setup_vsc = hsw_psr_setup_vsc ;
2017-09-07 16:00:32 -07:00
}
2014-11-14 08:52:28 -08:00
}