Home | History | Annotate | Line # | Download | only in core
      1 /*	$NetBSD: amdgpu_dc_link_dp.c,v 1.5 2021/12/19 11:22:40 riastradh Exp $	*/
      2 
      3 /* Copyright 2015 Advanced Micro Devices, Inc. */
      4 #include <sys/cdefs.h>
      5 __KERNEL_RCSID(0, "$NetBSD: amdgpu_dc_link_dp.c,v 1.5 2021/12/19 11:22:40 riastradh Exp $");
      6 
      7 #include "dm_services.h"
      8 #include "dc.h"
      9 #include "dc_link_dp.h"
     10 #include "dm_helpers.h"
     11 #include "opp.h"
     12 #include "dsc.h"
     13 #include "resource.h"
     14 
     15 #include "inc/core_types.h"
     16 #include "link_hwss.h"
     17 #include "dc_link_ddc.h"
     18 #include "core_status.h"
     19 #include "dpcd_defs.h"
     20 
     21 #include "resource.h"
     22 #define DC_LOGGER \
     23 	link->ctx->logger
     24 
     25 
     26 #define DP_REPEATER_CONFIGURATION_AND_STATUS_SIZE   0x50
     27 
     28 /* maximum pre emphasis level allowed for each voltage swing level*/
     29 static const enum dc_pre_emphasis voltage_swing_to_pre_emphasis[] = {
     30 		PRE_EMPHASIS_LEVEL3,
     31 		PRE_EMPHASIS_LEVEL2,
     32 		PRE_EMPHASIS_LEVEL1,
     33 		PRE_EMPHASIS_DISABLED };
     34 
     35 enum {
     36 	POST_LT_ADJ_REQ_LIMIT = 6,
     37 	POST_LT_ADJ_REQ_TIMEOUT = 200
     38 };
     39 
     40 enum {
     41 	LINK_TRAINING_MAX_RETRY_COUNT = 5,
     42 	/* to avoid infinite loop where-in the receiver
     43 	 * switches between different VS
     44 	 */
     45 	LINK_TRAINING_MAX_CR_RETRY = 100
     46 };
     47 
     48 static bool decide_fallback_link_setting(
     49 		struct dc_link_settings initial_link_settings,
     50 		struct dc_link_settings *current_link_setting,
     51 		enum link_training_result training_result);
     52 static struct dc_link_settings get_common_supported_link_settings(
     53 		struct dc_link_settings link_setting_a,
     54 		struct dc_link_settings link_setting_b);
     55 
     56 static uint32_t get_training_aux_rd_interval(
     57 	struct dc_link *link,
     58 	uint32_t default_wait_in_micro_secs)
     59 {
     60 	union training_aux_rd_interval training_rd_interval;
     61 
     62 	memset(&training_rd_interval, 0, sizeof(training_rd_interval));
     63 
     64 	/* overwrite the delay if rev > 1.1*/
     65 	if (link->dpcd_caps.dpcd_rev.raw >= DPCD_REV_12) {
     66 		/* DP 1.2 or later - retrieve delay through
     67 		 * "DPCD_ADDR_TRAINING_AUX_RD_INTERVAL" register */
     68 		core_link_read_dpcd(
     69 			link,
     70 			DP_TRAINING_AUX_RD_INTERVAL,
     71 			(uint8_t *)&training_rd_interval,
     72 			sizeof(training_rd_interval));
     73 
     74 		if (training_rd_interval.bits.TRAINIG_AUX_RD_INTERVAL)
     75 			default_wait_in_micro_secs = training_rd_interval.bits.TRAINIG_AUX_RD_INTERVAL * 4000;
     76 	}
     77 
     78 	return default_wait_in_micro_secs;
     79 }
     80 
     81 static void wait_for_training_aux_rd_interval(
     82 	struct dc_link *link,
     83 	uint32_t wait_in_micro_secs)
     84 {
     85 	udelay(wait_in_micro_secs);
     86 
     87 	DC_LOG_HW_LINK_TRAINING("%s:\n wait = %d\n",
     88 		__func__,
     89 		wait_in_micro_secs);
     90 }
     91 
     92 static void dpcd_set_training_pattern(
     93 	struct dc_link *link,
     94 	union dpcd_training_pattern dpcd_pattern)
     95 {
     96 	core_link_write_dpcd(
     97 		link,
     98 		DP_TRAINING_PATTERN_SET,
     99 		&dpcd_pattern.raw,
    100 		1);
    101 
    102 	DC_LOG_HW_LINK_TRAINING("%s\n %x pattern = %x\n",
    103 		__func__,
    104 		DP_TRAINING_PATTERN_SET,
    105 		dpcd_pattern.v1_4.TRAINING_PATTERN_SET);
    106 }
    107 
    108 static enum dc_dp_training_pattern get_supported_tp(struct dc_link *link)
    109 {
    110 	enum dc_dp_training_pattern highest_tp = DP_TRAINING_PATTERN_SEQUENCE_2;
    111 	struct encoder_feature_support *features = &link->link_enc->features;
    112 	struct dpcd_caps *dpcd_caps = &link->dpcd_caps;
    113 
    114 	if (features->flags.bits.IS_TPS3_CAPABLE)
    115 		highest_tp = DP_TRAINING_PATTERN_SEQUENCE_3;
    116 
    117 	if (features->flags.bits.IS_TPS4_CAPABLE)
    118 		highest_tp = DP_TRAINING_PATTERN_SEQUENCE_4;
    119 
    120 	if (dpcd_caps->max_down_spread.bits.TPS4_SUPPORTED &&
    121 		highest_tp >= DP_TRAINING_PATTERN_SEQUENCE_4)
    122 		return DP_TRAINING_PATTERN_SEQUENCE_4;
    123 
    124 	if (dpcd_caps->max_ln_count.bits.TPS3_SUPPORTED &&
    125 		highest_tp >= DP_TRAINING_PATTERN_SEQUENCE_3)
    126 		return DP_TRAINING_PATTERN_SEQUENCE_3;
    127 
    128 	return DP_TRAINING_PATTERN_SEQUENCE_2;
    129 }
    130 
    131 static void dpcd_set_link_settings(
    132 	struct dc_link *link,
    133 	const struct link_training_settings *lt_settings)
    134 {
    135 	uint8_t rate;
    136 
    137 	union down_spread_ctrl downspread = { {0} };
    138 	union lane_count_set lane_count_set = { {0} };
    139 	enum dc_dp_training_pattern dp_tr_pattern;
    140 
    141 	downspread.raw = (uint8_t)
    142 	(lt_settings->link_settings.link_spread);
    143 
    144 	lane_count_set.bits.LANE_COUNT_SET =
    145 	lt_settings->link_settings.lane_count;
    146 
    147 	lane_count_set.bits.ENHANCED_FRAMING = lt_settings->enhanced_framing;
    148 	lane_count_set.bits.POST_LT_ADJ_REQ_GRANTED = 0;
    149 
    150 	dp_tr_pattern = get_supported_tp(link);
    151 
    152 	if (dp_tr_pattern != DP_TRAINING_PATTERN_SEQUENCE_4) {
    153 		lane_count_set.bits.POST_LT_ADJ_REQ_GRANTED =
    154 				link->dpcd_caps.max_ln_count.bits.POST_LT_ADJ_REQ_SUPPORTED;
    155 	}
    156 
    157 	core_link_write_dpcd(link, DP_DOWNSPREAD_CTRL,
    158 		&downspread.raw, sizeof(downspread));
    159 
    160 	core_link_write_dpcd(link, DP_LANE_COUNT_SET,
    161 		&lane_count_set.raw, 1);
    162 
    163 	if (link->dpcd_caps.dpcd_rev.raw >= DPCD_REV_14 &&
    164 			lt_settings->link_settings.use_link_rate_set == true) {
    165 		rate = 0;
    166 		core_link_write_dpcd(link, DP_LINK_BW_SET, &rate, 1);
    167 		core_link_write_dpcd(link, DP_LINK_RATE_SET,
    168 				&lt_settings->link_settings.link_rate_set, 1);
    169 	} else {
    170 		rate = (uint8_t) (lt_settings->link_settings.link_rate);
    171 		core_link_write_dpcd(link, DP_LINK_BW_SET, &rate, 1);
    172 	}
    173 
    174 	if (rate) {
    175 		DC_LOG_HW_LINK_TRAINING("%s\n %x rate = %x\n %x lane = %x framing = %x\n %x spread = %x\n",
    176 			__func__,
    177 			DP_LINK_BW_SET,
    178 			lt_settings->link_settings.link_rate,
    179 			DP_LANE_COUNT_SET,
    180 			lt_settings->link_settings.lane_count,
    181 			lt_settings->enhanced_framing,
    182 			DP_DOWNSPREAD_CTRL,
    183 			lt_settings->link_settings.link_spread);
    184 	} else {
    185 		DC_LOG_HW_LINK_TRAINING("%s\n %x rate set = %x\n %x lane = %x framing = %x\n %x spread = %x\n",
    186 			__func__,
    187 			DP_LINK_RATE_SET,
    188 			lt_settings->link_settings.link_rate_set,
    189 			DP_LANE_COUNT_SET,
    190 			lt_settings->link_settings.lane_count,
    191 			lt_settings->enhanced_framing,
    192 			DP_DOWNSPREAD_CTRL,
    193 			lt_settings->link_settings.link_spread);
    194 	}
    195 }
    196 
    197 static enum dpcd_training_patterns
    198 	dc_dp_training_pattern_to_dpcd_training_pattern(
    199 	struct dc_link *link,
    200 	enum dc_dp_training_pattern pattern)
    201 {
    202 	enum dpcd_training_patterns dpcd_tr_pattern =
    203 	DPCD_TRAINING_PATTERN_VIDEOIDLE;
    204 
    205 	switch (pattern) {
    206 	case DP_TRAINING_PATTERN_SEQUENCE_1:
    207 		dpcd_tr_pattern = DPCD_TRAINING_PATTERN_1;
    208 		break;
    209 	case DP_TRAINING_PATTERN_SEQUENCE_2:
    210 		dpcd_tr_pattern = DPCD_TRAINING_PATTERN_2;
    211 		break;
    212 	case DP_TRAINING_PATTERN_SEQUENCE_3:
    213 		dpcd_tr_pattern = DPCD_TRAINING_PATTERN_3;
    214 		break;
    215 	case DP_TRAINING_PATTERN_SEQUENCE_4:
    216 		dpcd_tr_pattern = DPCD_TRAINING_PATTERN_4;
    217 		break;
    218 	default:
    219 		ASSERT(0);
    220 		DC_LOG_HW_LINK_TRAINING("%s: Invalid HW Training pattern: %d\n",
    221 			__func__, pattern);
    222 		break;
    223 	}
    224 
    225 	return dpcd_tr_pattern;
    226 }
    227 
    228 static inline bool is_repeater(struct dc_link *link, uint32_t offset)
    229 {
    230 	return (!link->is_lttpr_mode_transparent && offset != 0);
    231 }
    232 
    233 static void dpcd_set_lt_pattern_and_lane_settings(
    234 	struct dc_link *link,
    235 	const struct link_training_settings *lt_settings,
    236 	enum dc_dp_training_pattern pattern,
    237 	uint32_t offset)
    238 {
    239 	union dpcd_training_lane dpcd_lane[LANE_COUNT_DP_MAX] = { { {0} } };
    240 
    241 	uint32_t dpcd_base_lt_offset;
    242 
    243 	uint8_t dpcd_lt_buffer[5] = {0};
    244 	union dpcd_training_pattern dpcd_pattern = { {0} };
    245 	uint32_t lane;
    246 	uint32_t size_in_bytes;
    247 	bool edp_workaround = false; /* TODO link_prop.INTERNAL */
    248 	dpcd_base_lt_offset = DP_TRAINING_PATTERN_SET;
    249 
    250 	if (is_repeater(link, offset))
    251 		dpcd_base_lt_offset = DP_TRAINING_PATTERN_SET_PHY_REPEATER1 +
    252 			((DP_REPEATER_CONFIGURATION_AND_STATUS_SIZE) * (offset - 1));
    253 
    254 	/*****************************************************************
    255 	* DpcdAddress_TrainingPatternSet
    256 	*****************************************************************/
    257 	dpcd_pattern.v1_4.TRAINING_PATTERN_SET =
    258 		dc_dp_training_pattern_to_dpcd_training_pattern(link, pattern);
    259 
    260 	dpcd_lt_buffer[DP_TRAINING_PATTERN_SET - DP_TRAINING_PATTERN_SET]
    261 		= dpcd_pattern.raw;
    262 
    263 	if (is_repeater(link, offset)) {
    264 		DC_LOG_HW_LINK_TRAINING("%s\n LTTPR Repeater ID: %d\n 0x%X pattern = %x\n",
    265 			__func__,
    266 			offset,
    267 			dpcd_base_lt_offset,
    268 			dpcd_pattern.v1_4.TRAINING_PATTERN_SET);
    269 	} else {
    270 		DC_LOG_HW_LINK_TRAINING("%s\n 0x%X pattern = %x\n",
    271 			__func__,
    272 			dpcd_base_lt_offset,
    273 			dpcd_pattern.v1_4.TRAINING_PATTERN_SET);
    274 	}
    275 	/*****************************************************************
    276 	* DpcdAddress_Lane0Set -> DpcdAddress_Lane3Set
    277 	*****************************************************************/
    278 	for (lane = 0; lane <
    279 		(uint32_t)(lt_settings->link_settings.lane_count); lane++) {
    280 
    281 		dpcd_lane[lane].bits.VOLTAGE_SWING_SET =
    282 		(uint8_t)(lt_settings->lane_settings[lane].VOLTAGE_SWING);
    283 		dpcd_lane[lane].bits.PRE_EMPHASIS_SET =
    284 		(uint8_t)(lt_settings->lane_settings[lane].PRE_EMPHASIS);
    285 
    286 		dpcd_lane[lane].bits.MAX_SWING_REACHED =
    287 		(lt_settings->lane_settings[lane].VOLTAGE_SWING ==
    288 		VOLTAGE_SWING_MAX_LEVEL ? 1 : 0);
    289 		dpcd_lane[lane].bits.MAX_PRE_EMPHASIS_REACHED =
    290 		(lt_settings->lane_settings[lane].PRE_EMPHASIS ==
    291 		PRE_EMPHASIS_MAX_LEVEL ? 1 : 0);
    292 	}
    293 
    294 	/* concatenate everything into one buffer*/
    295 
    296 	size_in_bytes = lt_settings->link_settings.lane_count * sizeof(dpcd_lane[0]);
    297 
    298 	 // 0x00103 - 0x00102
    299 	memmove(
    300 		&dpcd_lt_buffer[DP_TRAINING_LANE0_SET - DP_TRAINING_PATTERN_SET],
    301 		dpcd_lane,
    302 		size_in_bytes);
    303 
    304 	if (is_repeater(link, offset)) {
    305 		DC_LOG_HW_LINK_TRAINING("%s:\n LTTPR Repeater ID: %d\n"
    306 				" 0x%X VS set = %x PE set = %x max VS Reached = %x  max PE Reached = %x\n",
    307 			__func__,
    308 			offset,
    309 			dpcd_base_lt_offset,
    310 			dpcd_lane[0].bits.VOLTAGE_SWING_SET,
    311 			dpcd_lane[0].bits.PRE_EMPHASIS_SET,
    312 			dpcd_lane[0].bits.MAX_SWING_REACHED,
    313 			dpcd_lane[0].bits.MAX_PRE_EMPHASIS_REACHED);
    314 	} else {
    315 		DC_LOG_HW_LINK_TRAINING("%s:\n 0x%X VS set = %x  PE set = %x max VS Reached = %x  max PE Reached = %x\n",
    316 			__func__,
    317 			dpcd_base_lt_offset,
    318 			dpcd_lane[0].bits.VOLTAGE_SWING_SET,
    319 			dpcd_lane[0].bits.PRE_EMPHASIS_SET,
    320 			dpcd_lane[0].bits.MAX_SWING_REACHED,
    321 			dpcd_lane[0].bits.MAX_PRE_EMPHASIS_REACHED);
    322 	}
    323 	if (edp_workaround) {
    324 		/* for eDP write in 2 parts because the 5-byte burst is
    325 		* causing issues on some eDP panels (EPR#366724)
    326 		*/
    327 		core_link_write_dpcd(
    328 			link,
    329 			DP_TRAINING_PATTERN_SET,
    330 			&dpcd_pattern.raw,
    331 			sizeof(dpcd_pattern.raw));
    332 
    333 		core_link_write_dpcd(
    334 			link,
    335 			DP_TRAINING_LANE0_SET,
    336 			(uint8_t *)(dpcd_lane),
    337 			size_in_bytes);
    338 
    339 		} else
    340 		/* write it all in (1 + number-of-lanes)-byte burst*/
    341 			core_link_write_dpcd(
    342 				link,
    343 				dpcd_base_lt_offset,
    344 				dpcd_lt_buffer,
    345 				size_in_bytes + sizeof(dpcd_pattern.raw));
    346 
    347 	link->cur_lane_setting = lt_settings->lane_settings[0];
    348 }
    349 
    350 static bool is_cr_done(enum dc_lane_count ln_count,
    351 	union lane_status *dpcd_lane_status)
    352 {
    353 	bool done = true;
    354 	uint32_t lane;
    355 	/*LANEx_CR_DONE bits All 1's?*/
    356 	for (lane = 0; lane < (uint32_t)(ln_count); lane++) {
    357 		if (!dpcd_lane_status[lane].bits.CR_DONE_0)
    358 			done = false;
    359 	}
    360 	return done;
    361 
    362 }
    363 
    364 static bool is_ch_eq_done(enum dc_lane_count ln_count,
    365 	union lane_status *dpcd_lane_status,
    366 	union lane_align_status_updated *lane_status_updated)
    367 {
    368 	bool done = true;
    369 	uint32_t lane;
    370 	if (!lane_status_updated->bits.INTERLANE_ALIGN_DONE)
    371 		done = false;
    372 	else {
    373 		for (lane = 0; lane < (uint32_t)(ln_count); lane++) {
    374 			if (!dpcd_lane_status[lane].bits.SYMBOL_LOCKED_0 ||
    375 				!dpcd_lane_status[lane].bits.CHANNEL_EQ_DONE_0)
    376 				done = false;
    377 		}
    378 	}
    379 	return done;
    380 
    381 }
    382 
    383 static void update_drive_settings(
    384 		struct link_training_settings *dest,
    385 		struct link_training_settings src)
    386 {
    387 	uint32_t lane;
    388 	for (lane = 0; lane < src.link_settings.lane_count; lane++) {
    389 		if (dest->voltage_swing == NULL)
    390 			dest->lane_settings[lane].VOLTAGE_SWING = src.lane_settings[lane].VOLTAGE_SWING;
    391 		else
    392 			dest->lane_settings[lane].VOLTAGE_SWING = *dest->voltage_swing;
    393 
    394 		if (dest->pre_emphasis == NULL)
    395 			dest->lane_settings[lane].PRE_EMPHASIS = src.lane_settings[lane].PRE_EMPHASIS;
    396 		else
    397 			dest->lane_settings[lane].PRE_EMPHASIS = *dest->pre_emphasis;
    398 
    399 		if (dest->post_cursor2 == NULL)
    400 			dest->lane_settings[lane].POST_CURSOR2 = src.lane_settings[lane].POST_CURSOR2;
    401 		else
    402 			dest->lane_settings[lane].POST_CURSOR2 = *dest->post_cursor2;
    403 	}
    404 }
    405 
    406 static uint8_t get_nibble_at_index(const uint8_t *buf,
    407 	uint32_t index)
    408 {
    409 	uint8_t nibble;
    410 	nibble = buf[index / 2];
    411 
    412 	if (index % 2)
    413 		nibble >>= 4;
    414 	else
    415 		nibble &= 0x0F;
    416 
    417 	return nibble;
    418 }
    419 
    420 static enum dc_pre_emphasis get_max_pre_emphasis_for_voltage_swing(
    421 	enum dc_voltage_swing voltage)
    422 {
    423 	enum dc_pre_emphasis pre_emphasis;
    424 	pre_emphasis = PRE_EMPHASIS_MAX_LEVEL;
    425 
    426 	if (voltage <= VOLTAGE_SWING_MAX_LEVEL)
    427 		pre_emphasis = voltage_swing_to_pre_emphasis[voltage];
    428 
    429 	return pre_emphasis;
    430 
    431 }
    432 
    433 static void find_max_drive_settings(
    434 	const struct link_training_settings *link_training_setting,
    435 	struct link_training_settings *max_lt_setting)
    436 {
    437 	uint32_t lane;
    438 	struct dc_lane_settings max_requested;
    439 
    440 	max_requested.VOLTAGE_SWING =
    441 		link_training_setting->
    442 		lane_settings[0].VOLTAGE_SWING;
    443 	max_requested.PRE_EMPHASIS =
    444 		link_training_setting->
    445 		lane_settings[0].PRE_EMPHASIS;
    446 	/*max_requested.postCursor2 =
    447 	 * link_training_setting->laneSettings[0].postCursor2;*/
    448 
    449 	/* Determine what the maximum of the requested settings are*/
    450 	for (lane = 1; lane < link_training_setting->link_settings.lane_count;
    451 			lane++) {
    452 		if (link_training_setting->lane_settings[lane].VOLTAGE_SWING >
    453 			max_requested.VOLTAGE_SWING)
    454 
    455 			max_requested.VOLTAGE_SWING =
    456 			link_training_setting->
    457 			lane_settings[lane].VOLTAGE_SWING;
    458 
    459 		if (link_training_setting->lane_settings[lane].PRE_EMPHASIS >
    460 				max_requested.PRE_EMPHASIS)
    461 			max_requested.PRE_EMPHASIS =
    462 			link_training_setting->
    463 			lane_settings[lane].PRE_EMPHASIS;
    464 
    465 		/*
    466 		if (link_training_setting->laneSettings[lane].postCursor2 >
    467 		 max_requested.postCursor2)
    468 		{
    469 		max_requested.postCursor2 =
    470 		link_training_setting->laneSettings[lane].postCursor2;
    471 		}
    472 		*/
    473 	}
    474 
    475 	/* make sure the requested settings are
    476 	 * not higher than maximum settings*/
    477 	if (max_requested.VOLTAGE_SWING > VOLTAGE_SWING_MAX_LEVEL)
    478 		max_requested.VOLTAGE_SWING = VOLTAGE_SWING_MAX_LEVEL;
    479 
    480 	if (max_requested.PRE_EMPHASIS > PRE_EMPHASIS_MAX_LEVEL)
    481 		max_requested.PRE_EMPHASIS = PRE_EMPHASIS_MAX_LEVEL;
    482 	/*
    483 	if (max_requested.postCursor2 > PostCursor2_MaxLevel)
    484 	max_requested.postCursor2 = PostCursor2_MaxLevel;
    485 	*/
    486 
    487 	/* make sure the pre-emphasis matches the voltage swing*/
    488 	if (max_requested.PRE_EMPHASIS >
    489 		get_max_pre_emphasis_for_voltage_swing(
    490 			max_requested.VOLTAGE_SWING))
    491 		max_requested.PRE_EMPHASIS =
    492 		get_max_pre_emphasis_for_voltage_swing(
    493 			max_requested.VOLTAGE_SWING);
    494 
    495 	/*
    496 	 * Post Cursor2 levels are completely independent from
    497 	 * pre-emphasis (Post Cursor1) levels. But Post Cursor2 levels
    498 	 * can only be applied to each allowable combination of voltage
    499 	 * swing and pre-emphasis levels */
    500 	 /* if ( max_requested.postCursor2 >
    501 	  *  getMaxPostCursor2ForVoltageSwing(max_requested.voltageSwing))
    502 	  *  max_requested.postCursor2 =
    503 	  *  getMaxPostCursor2ForVoltageSwing(max_requested.voltageSwing);
    504 	  */
    505 
    506 	max_lt_setting->link_settings.link_rate =
    507 		link_training_setting->link_settings.link_rate;
    508 	max_lt_setting->link_settings.lane_count =
    509 	link_training_setting->link_settings.lane_count;
    510 	max_lt_setting->link_settings.link_spread =
    511 		link_training_setting->link_settings.link_spread;
    512 
    513 	for (lane = 0; lane <
    514 		link_training_setting->link_settings.lane_count;
    515 		lane++) {
    516 		max_lt_setting->lane_settings[lane].VOLTAGE_SWING =
    517 			max_requested.VOLTAGE_SWING;
    518 		max_lt_setting->lane_settings[lane].PRE_EMPHASIS =
    519 			max_requested.PRE_EMPHASIS;
    520 		/*max_lt_setting->laneSettings[lane].postCursor2 =
    521 		 * max_requested.postCursor2;
    522 		 */
    523 	}
    524 
    525 }
    526 
    527 static void get_lane_status_and_drive_settings(
    528 	struct dc_link *link,
    529 	const struct link_training_settings *link_training_setting,
    530 	union lane_status *ln_status,
    531 	union lane_align_status_updated *ln_status_updated,
    532 	struct link_training_settings *req_settings,
    533 	uint32_t offset)
    534 {
    535 	unsigned int lane01_status_address = DP_LANE0_1_STATUS;
    536 	uint8_t lane_adjust_offset = 4;
    537 	unsigned int lane01_adjust_address;
    538 	uint8_t dpcd_buf[6] = {0};
    539 	union lane_adjust dpcd_lane_adjust[LANE_COUNT_DP_MAX] = { { {0} } };
    540 	struct link_training_settings request_settings = { {0} };
    541 	uint32_t lane;
    542 
    543 	memset(req_settings, '\0', sizeof(struct link_training_settings));
    544 
    545 	if (is_repeater(link, offset)) {
    546 		lane01_status_address =
    547 				DP_LANE0_1_STATUS_PHY_REPEATER1 +
    548 				((DP_REPEATER_CONFIGURATION_AND_STATUS_SIZE) * (offset - 1));
    549 		lane_adjust_offset = 3;
    550 	}
    551 
    552 	core_link_read_dpcd(
    553 		link,
    554 		lane01_status_address,
    555 		(uint8_t *)(dpcd_buf),
    556 		sizeof(dpcd_buf));
    557 
    558 	for (lane = 0; lane <
    559 		(uint32_t)(link_training_setting->link_settings.lane_count);
    560 		lane++) {
    561 
    562 		ln_status[lane].raw =
    563 			get_nibble_at_index(&dpcd_buf[0], lane);
    564 		dpcd_lane_adjust[lane].raw =
    565 			get_nibble_at_index(&dpcd_buf[lane_adjust_offset], lane);
    566 	}
    567 
    568 	ln_status_updated->raw = dpcd_buf[2];
    569 
    570 	if (is_repeater(link, offset)) {
    571 		DC_LOG_HW_LINK_TRAINING("%s:\n LTTPR Repeater ID: %d\n"
    572 				" 0x%X Lane01Status = %x\n 0x%X Lane23Status = %x\n ",
    573 			__func__,
    574 			offset,
    575 			lane01_status_address, dpcd_buf[0],
    576 			lane01_status_address + 1, dpcd_buf[1]);
    577 	} else {
    578 		DC_LOG_HW_LINK_TRAINING("%s:\n 0x%X Lane01Status = %x\n 0x%X Lane23Status = %x\n ",
    579 			__func__,
    580 			lane01_status_address, dpcd_buf[0],
    581 			lane01_status_address + 1, dpcd_buf[1]);
    582 	}
    583 	lane01_adjust_address = DP_ADJUST_REQUEST_LANE0_1;
    584 
    585 	if (is_repeater(link, offset))
    586 		lane01_adjust_address = DP_ADJUST_REQUEST_LANE0_1_PHY_REPEATER1 +
    587 				((DP_REPEATER_CONFIGURATION_AND_STATUS_SIZE) * (offset - 1));
    588 
    589 	if (is_repeater(link, offset)) {
    590 		DC_LOG_HW_LINK_TRAINING("%s:\n LTTPR Repeater ID: %d\n"
    591 				" 0x%X Lane01AdjustRequest = %x\n 0x%X Lane23AdjustRequest = %x\n",
    592 					__func__,
    593 					offset,
    594 					lane01_adjust_address,
    595 					dpcd_buf[lane_adjust_offset],
    596 					lane01_adjust_address + 1,
    597 					dpcd_buf[lane_adjust_offset + 1]);
    598 	} else {
    599 		DC_LOG_HW_LINK_TRAINING("%s:\n 0x%X Lane01AdjustRequest = %x\n 0x%X Lane23AdjustRequest = %x\n",
    600 			__func__,
    601 			lane01_adjust_address,
    602 			dpcd_buf[lane_adjust_offset],
    603 			lane01_adjust_address + 1,
    604 			dpcd_buf[lane_adjust_offset + 1]);
    605 	}
    606 
    607 	/*copy to req_settings*/
    608 	request_settings.link_settings.lane_count =
    609 		link_training_setting->link_settings.lane_count;
    610 	request_settings.link_settings.link_rate =
    611 		link_training_setting->link_settings.link_rate;
    612 	request_settings.link_settings.link_spread =
    613 		link_training_setting->link_settings.link_spread;
    614 
    615 	for (lane = 0; lane <
    616 		(uint32_t)(link_training_setting->link_settings.lane_count);
    617 		lane++) {
    618 
    619 		request_settings.lane_settings[lane].VOLTAGE_SWING =
    620 			(enum dc_voltage_swing)(dpcd_lane_adjust[lane].bits.
    621 				VOLTAGE_SWING_LANE);
    622 		request_settings.lane_settings[lane].PRE_EMPHASIS =
    623 			(enum dc_pre_emphasis)(dpcd_lane_adjust[lane].bits.
    624 				PRE_EMPHASIS_LANE);
    625 	}
    626 
    627 	/*Note: for postcursor2, read adjusted
    628 	 * postcursor2 settings from*/
    629 	/*DpcdAddress_AdjustRequestPostCursor2 =
    630 	 *0x020C (not implemented yet)*/
    631 
    632 	/* we find the maximum of the requested settings across all lanes*/
    633 	/* and set this maximum for all lanes*/
    634 	find_max_drive_settings(&request_settings, req_settings);
    635 
    636 	/* if post cursor 2 is needed in the future,
    637 	 * read DpcdAddress_AdjustRequestPostCursor2 = 0x020C
    638 	 */
    639 
    640 }
    641 
    642 static void dpcd_set_lane_settings(
    643 	struct dc_link *link,
    644 	const struct link_training_settings *link_training_setting,
    645 	uint32_t offset)
    646 {
    647 	union dpcd_training_lane dpcd_lane[LANE_COUNT_DP_MAX] = {{{0}}};
    648 	uint32_t lane;
    649 	unsigned int lane0_set_address;
    650 
    651 	lane0_set_address = DP_TRAINING_LANE0_SET;
    652 
    653 	if (is_repeater(link, offset))
    654 		lane0_set_address = DP_TRAINING_LANE0_SET_PHY_REPEATER1 +
    655 		((DP_REPEATER_CONFIGURATION_AND_STATUS_SIZE) * (offset - 1));
    656 
    657 	for (lane = 0; lane <
    658 		(uint32_t)(link_training_setting->
    659 		link_settings.lane_count);
    660 		lane++) {
    661 		dpcd_lane[lane].bits.VOLTAGE_SWING_SET =
    662 			(uint8_t)(link_training_setting->
    663 			lane_settings[lane].VOLTAGE_SWING);
    664 		dpcd_lane[lane].bits.PRE_EMPHASIS_SET =
    665 			(uint8_t)(link_training_setting->
    666 			lane_settings[lane].PRE_EMPHASIS);
    667 		dpcd_lane[lane].bits.MAX_SWING_REACHED =
    668 			(link_training_setting->
    669 			lane_settings[lane].VOLTAGE_SWING ==
    670 			VOLTAGE_SWING_MAX_LEVEL ? 1 : 0);
    671 		dpcd_lane[lane].bits.MAX_PRE_EMPHASIS_REACHED =
    672 			(link_training_setting->
    673 			lane_settings[lane].PRE_EMPHASIS ==
    674 			PRE_EMPHASIS_MAX_LEVEL ? 1 : 0);
    675 	}
    676 
    677 	core_link_write_dpcd(link,
    678 		lane0_set_address,
    679 		(uint8_t *)(dpcd_lane),
    680 		link_training_setting->link_settings.lane_count);
    681 
    682 	/*
    683 	if (LTSettings.link.rate == LinkRate_High2)
    684 	{
    685 		DpcdTrainingLaneSet2 dpcd_lane2[lane_count_DPMax] = {0};
    686 		for ( uint32_t lane = 0;
    687 		lane < lane_count_DPMax; lane++)
    688 		{
    689 			dpcd_lane2[lane].bits.post_cursor2_set =
    690 			static_cast<unsigned char>(
    691 			LTSettings.laneSettings[lane].postCursor2);
    692 			dpcd_lane2[lane].bits.max_post_cursor2_reached = 0;
    693 		}
    694 		m_pDpcdAccessSrv->WriteDpcdData(
    695 		DpcdAddress_Lane0Set2,
    696 		reinterpret_cast<unsigned char*>(dpcd_lane2),
    697 		LTSettings.link.lanes);
    698 	}
    699 	*/
    700 
    701 	if (is_repeater(link, offset)) {
    702 		DC_LOG_HW_LINK_TRAINING("%s\n LTTPR Repeater ID: %d\n"
    703 				" 0x%X VS set = %x  PE set = %x max VS Reached = %x  max PE Reached = %x\n",
    704 			__func__,
    705 			offset,
    706 			lane0_set_address,
    707 			dpcd_lane[0].bits.VOLTAGE_SWING_SET,
    708 			dpcd_lane[0].bits.PRE_EMPHASIS_SET,
    709 			dpcd_lane[0].bits.MAX_SWING_REACHED,
    710 			dpcd_lane[0].bits.MAX_PRE_EMPHASIS_REACHED);
    711 
    712 	} else {
    713 		DC_LOG_HW_LINK_TRAINING("%s\n 0x%X VS set = %x  PE set = %x max VS Reached = %x  max PE Reached = %x\n",
    714 			__func__,
    715 			lane0_set_address,
    716 			dpcd_lane[0].bits.VOLTAGE_SWING_SET,
    717 			dpcd_lane[0].bits.PRE_EMPHASIS_SET,
    718 			dpcd_lane[0].bits.MAX_SWING_REACHED,
    719 			dpcd_lane[0].bits.MAX_PRE_EMPHASIS_REACHED);
    720 	}
    721 	link->cur_lane_setting = link_training_setting->lane_settings[0];
    722 
    723 }
    724 
    725 static bool is_max_vs_reached(
    726 	const struct link_training_settings *lt_settings)
    727 {
    728 	uint32_t lane;
    729 	for (lane = 0; lane <
    730 		(uint32_t)(lt_settings->link_settings.lane_count);
    731 		lane++) {
    732 		if (lt_settings->lane_settings[lane].VOLTAGE_SWING
    733 			== VOLTAGE_SWING_MAX_LEVEL)
    734 			return true;
    735 	}
    736 	return false;
    737 
    738 }
    739 
    740 static bool perform_post_lt_adj_req_sequence(
    741 	struct dc_link *link,
    742 	struct link_training_settings *lt_settings)
    743 {
    744 	enum dc_lane_count lane_count =
    745 	lt_settings->link_settings.lane_count;
    746 
    747 	uint32_t adj_req_count;
    748 	uint32_t adj_req_timer;
    749 	bool req_drv_setting_changed;
    750 	uint32_t lane;
    751 
    752 	req_drv_setting_changed = false;
    753 	for (adj_req_count = 0; adj_req_count < POST_LT_ADJ_REQ_LIMIT;
    754 	adj_req_count++) {
    755 
    756 		req_drv_setting_changed = false;
    757 
    758 		for (adj_req_timer = 0;
    759 			adj_req_timer < POST_LT_ADJ_REQ_TIMEOUT;
    760 			adj_req_timer++) {
    761 
    762 			struct link_training_settings req_settings;
    763 			union lane_status dpcd_lane_status[LANE_COUNT_DP_MAX];
    764 			union lane_align_status_updated
    765 				dpcd_lane_status_updated;
    766 
    767 			get_lane_status_and_drive_settings(
    768 			link,
    769 			lt_settings,
    770 			dpcd_lane_status,
    771 			&dpcd_lane_status_updated,
    772 			&req_settings,
    773 			DPRX);
    774 
    775 			if (dpcd_lane_status_updated.bits.
    776 					POST_LT_ADJ_REQ_IN_PROGRESS == 0)
    777 				return true;
    778 
    779 			if (!is_cr_done(lane_count, dpcd_lane_status))
    780 				return false;
    781 
    782 			if (!is_ch_eq_done(
    783 				lane_count,
    784 				dpcd_lane_status,
    785 				&dpcd_lane_status_updated))
    786 				return false;
    787 
    788 			for (lane = 0; lane < (uint32_t)(lane_count); lane++) {
    789 
    790 				if (lt_settings->
    791 				lane_settings[lane].VOLTAGE_SWING !=
    792 				req_settings.lane_settings[lane].
    793 				VOLTAGE_SWING ||
    794 				lt_settings->lane_settings[lane].PRE_EMPHASIS !=
    795 				req_settings.lane_settings[lane].PRE_EMPHASIS) {
    796 
    797 					req_drv_setting_changed = true;
    798 					break;
    799 				}
    800 			}
    801 
    802 			if (req_drv_setting_changed) {
    803 				update_drive_settings(
    804 					lt_settings, req_settings);
    805 
    806 				dc_link_dp_set_drive_settings(link,
    807 						lt_settings);
    808 				break;
    809 			}
    810 
    811 			msleep(1);
    812 		}
    813 
    814 		if (!req_drv_setting_changed) {
    815 			DC_LOG_WARNING("%s: Post Link Training Adjust Request Timed out\n",
    816 				__func__);
    817 
    818 			ASSERT(0);
    819 			return true;
    820 		}
    821 	}
    822 	DC_LOG_WARNING("%s: Post Link Training Adjust Request limit reached\n",
    823 		__func__);
    824 
    825 	ASSERT(0);
    826 	return true;
    827 
    828 }
    829 
    830 /* Only used for channel equalization */
    831 static uint32_t translate_training_aux_read_interval(uint32_t dpcd_aux_read_interval)
    832 {
    833 	unsigned int aux_rd_interval_us = 400;
    834 
    835 	switch (dpcd_aux_read_interval) {
    836 	case 0x01:
    837 		aux_rd_interval_us = 400;
    838 		break;
    839 	case 0x02:
    840 		aux_rd_interval_us = 4000;
    841 		break;
    842 	case 0x03:
    843 		aux_rd_interval_us = 8000;
    844 		break;
    845 	case 0x04:
    846 		aux_rd_interval_us = 16000;
    847 		break;
    848 	default:
    849 		break;
    850 	}
    851 
    852 	return aux_rd_interval_us;
    853 }
    854 
    855 static enum link_training_result get_cr_failure(enum dc_lane_count ln_count,
    856 					union lane_status *dpcd_lane_status)
    857 {
    858 	enum link_training_result result = LINK_TRAINING_SUCCESS;
    859 
    860 	if (ln_count >= LANE_COUNT_ONE && !dpcd_lane_status[0].bits.CR_DONE_0)
    861 		result = LINK_TRAINING_CR_FAIL_LANE0;
    862 	else if (ln_count >= LANE_COUNT_TWO && !dpcd_lane_status[1].bits.CR_DONE_0)
    863 		result = LINK_TRAINING_CR_FAIL_LANE1;
    864 	else if (ln_count >= LANE_COUNT_FOUR && !dpcd_lane_status[2].bits.CR_DONE_0)
    865 		result = LINK_TRAINING_CR_FAIL_LANE23;
    866 	else if (ln_count >= LANE_COUNT_FOUR && !dpcd_lane_status[3].bits.CR_DONE_0)
    867 		result = LINK_TRAINING_CR_FAIL_LANE23;
    868 	return result;
    869 }
    870 
    871 static enum link_training_result perform_channel_equalization_sequence(
    872 	struct dc_link *link,
    873 	struct link_training_settings *lt_settings,
    874 	uint32_t offset)
    875 {
    876 	struct link_training_settings req_settings;
    877 	enum dc_dp_training_pattern tr_pattern;
    878 	uint32_t retries_ch_eq;
    879 	uint32_t wait_time_microsec;
    880 	enum dc_lane_count lane_count = lt_settings->link_settings.lane_count;
    881 	union lane_align_status_updated dpcd_lane_status_updated = { {0} };
    882 	union lane_status dpcd_lane_status[LANE_COUNT_DP_MAX] = { { {0} } };
    883 
    884 	/* Note: also check that TPS4 is a supported feature*/
    885 
    886 	tr_pattern = lt_settings->pattern_for_eq;
    887 
    888 	if (is_repeater(link, offset))
    889 		tr_pattern = DP_TRAINING_PATTERN_SEQUENCE_4;
    890 
    891 	dp_set_hw_training_pattern(link, tr_pattern, offset);
    892 
    893 	for (retries_ch_eq = 0; retries_ch_eq <= LINK_TRAINING_MAX_RETRY_COUNT;
    894 		retries_ch_eq++) {
    895 
    896 		dp_set_hw_lane_settings(link, lt_settings, offset);
    897 
    898 		/* 2. update DPCD*/
    899 		if (!retries_ch_eq)
    900 			/* EPR #361076 - write as a 5-byte burst,
    901 			 * but only for the 1-st iteration
    902 			 */
    903 
    904 			dpcd_set_lt_pattern_and_lane_settings(
    905 				link,
    906 				lt_settings,
    907 				tr_pattern, offset);
    908 		else
    909 			dpcd_set_lane_settings(link, lt_settings, offset);
    910 
    911 		/* 3. wait for receiver to lock-on*/
    912 		wait_time_microsec = lt_settings->eq_pattern_time;
    913 
    914 		if (is_repeater(link, offset))
    915 			wait_time_microsec =
    916 					translate_training_aux_read_interval(
    917 						link->dpcd_caps.lttpr_caps.aux_rd_interval[offset - 1]);
    918 
    919 		wait_for_training_aux_rd_interval(
    920 				link,
    921 				wait_time_microsec);
    922 
    923 		/* 4. Read lane status and requested
    924 		 * drive settings as set by the sink*/
    925 
    926 		get_lane_status_and_drive_settings(
    927 			link,
    928 			lt_settings,
    929 			dpcd_lane_status,
    930 			&dpcd_lane_status_updated,
    931 			&req_settings,
    932 			offset);
    933 
    934 		/* 5. check CR done*/
    935 		if (!is_cr_done(lane_count, dpcd_lane_status))
    936 			return LINK_TRAINING_EQ_FAIL_CR;
    937 
    938 		/* 6. check CHEQ done*/
    939 		if (is_ch_eq_done(lane_count,
    940 			dpcd_lane_status,
    941 			&dpcd_lane_status_updated))
    942 			return LINK_TRAINING_SUCCESS;
    943 
    944 		/* 7. update VS/PE/PC2 in lt_settings*/
    945 		update_drive_settings(lt_settings, req_settings);
    946 	}
    947 
    948 	return LINK_TRAINING_EQ_FAIL_EQ;
    949 
    950 }
    951 #define TRAINING_AUX_RD_INTERVAL 100 //us
    952 
    953 static enum link_training_result perform_clock_recovery_sequence(
    954 	struct dc_link *link,
    955 	struct link_training_settings *lt_settings,
    956 	uint32_t offset)
    957 {
    958 	uint32_t retries_cr;
    959 	uint32_t retry_count;
    960 	uint32_t wait_time_microsec;
    961 	struct link_training_settings req_settings;
    962 	enum dc_lane_count lane_count = lt_settings->link_settings.lane_count;
    963 	enum dc_dp_training_pattern tr_pattern = DP_TRAINING_PATTERN_SEQUENCE_1;
    964 	union lane_status dpcd_lane_status[LANE_COUNT_DP_MAX];
    965 	union lane_align_status_updated dpcd_lane_status_updated;
    966 
    967 	retries_cr = 0;
    968 	retry_count = 0;
    969 
    970 	dp_set_hw_training_pattern(link, tr_pattern, offset);
    971 
    972 	/* najeeb - The synaptics MST hub can put the LT in
    973 	* infinite loop by switching the VS
    974 	*/
    975 	/* between level 0 and level 1 continuously, here
    976 	* we try for CR lock for LinkTrainingMaxCRRetry count*/
    977 	while ((retries_cr < LINK_TRAINING_MAX_RETRY_COUNT) &&
    978 		(retry_count < LINK_TRAINING_MAX_CR_RETRY)) {
    979 
    980 		memset(&dpcd_lane_status, '\0', sizeof(dpcd_lane_status));
    981 		memset(&dpcd_lane_status_updated, '\0',
    982 		sizeof(dpcd_lane_status_updated));
    983 
    984 		/* 1. call HWSS to set lane settings*/
    985 		dp_set_hw_lane_settings(
    986 				link,
    987 				lt_settings,
    988 				offset);
    989 
    990 		/* 2. update DPCD of the receiver*/
    991 		if (!retry_count)
    992 			/* EPR #361076 - write as a 5-byte burst,
    993 			 * but only for the 1-st iteration.*/
    994 			dpcd_set_lt_pattern_and_lane_settings(
    995 					link,
    996 					lt_settings,
    997 					tr_pattern,
    998 					offset);
    999 		else
   1000 			dpcd_set_lane_settings(
   1001 					link,
   1002 					lt_settings,
   1003 					offset);
   1004 
   1005 		/* 3. wait receiver to lock-on*/
   1006 		wait_time_microsec = lt_settings->cr_pattern_time;
   1007 
   1008 		if (!link->is_lttpr_mode_transparent)
   1009 			wait_time_microsec = TRAINING_AUX_RD_INTERVAL;
   1010 
   1011 		wait_for_training_aux_rd_interval(
   1012 				link,
   1013 				wait_time_microsec);
   1014 
   1015 		/* 4. Read lane status and requested drive
   1016 		* settings as set by the sink
   1017 		*/
   1018 		get_lane_status_and_drive_settings(
   1019 				link,
   1020 				lt_settings,
   1021 				dpcd_lane_status,
   1022 				&dpcd_lane_status_updated,
   1023 				&req_settings,
   1024 				offset);
   1025 
   1026 		/* 5. check CR done*/
   1027 		if (is_cr_done(lane_count, dpcd_lane_status))
   1028 			return LINK_TRAINING_SUCCESS;
   1029 
   1030 		/* 6. max VS reached*/
   1031 		if (is_max_vs_reached(lt_settings))
   1032 			break;
   1033 
   1034 		/* 7. same voltage*/
   1035 		/* Note: VS same for all lanes,
   1036 		* so comparing first lane is sufficient*/
   1037 		if (lt_settings->lane_settings[0].VOLTAGE_SWING ==
   1038 			req_settings.lane_settings[0].VOLTAGE_SWING)
   1039 			retries_cr++;
   1040 		else
   1041 			retries_cr = 0;
   1042 
   1043 		/* 8. update VS/PE/PC2 in lt_settings*/
   1044 		update_drive_settings(lt_settings, req_settings);
   1045 
   1046 		retry_count++;
   1047 	}
   1048 
   1049 	if (retry_count >= LINK_TRAINING_MAX_CR_RETRY) {
   1050 		ASSERT(0);
   1051 		DC_LOG_ERROR("%s: Link Training Error, could not get CR after %d tries. Possibly voltage swing issue",
   1052 			__func__,
   1053 			LINK_TRAINING_MAX_CR_RETRY);
   1054 
   1055 	}
   1056 
   1057 	return get_cr_failure(lane_count, dpcd_lane_status);
   1058 }
   1059 
   1060 static inline enum link_training_result perform_link_training_int(
   1061 	struct dc_link *link,
   1062 	struct link_training_settings *lt_settings,
   1063 	enum link_training_result status)
   1064 {
   1065 	union lane_count_set lane_count_set = { {0} };
   1066 	union dpcd_training_pattern dpcd_pattern = { {0} };
   1067 
   1068 	/* 3. set training not in progress*/
   1069 	dpcd_pattern.v1_4.TRAINING_PATTERN_SET = DPCD_TRAINING_PATTERN_VIDEOIDLE;
   1070 	dpcd_set_training_pattern(link, dpcd_pattern);
   1071 
   1072 	/* 4. mainlink output idle pattern*/
   1073 	dp_set_hw_test_pattern(link, DP_TEST_PATTERN_VIDEO_MODE, NULL, 0);
   1074 
   1075 	/*
   1076 	 * 5. post training adjust if required
   1077 	 * If the upstream DPTX and downstream DPRX both support TPS4,
   1078 	 * TPS4 must be used instead of POST_LT_ADJ_REQ.
   1079 	 */
   1080 	if (link->dpcd_caps.max_ln_count.bits.POST_LT_ADJ_REQ_SUPPORTED != 1 ||
   1081 			get_supported_tp(link) == DP_TRAINING_PATTERN_SEQUENCE_4)
   1082 		return status;
   1083 
   1084 	if (status == LINK_TRAINING_SUCCESS &&
   1085 		perform_post_lt_adj_req_sequence(link, lt_settings) == false)
   1086 		status = LINK_TRAINING_LQA_FAIL;
   1087 
   1088 	lane_count_set.bits.LANE_COUNT_SET = lt_settings->link_settings.lane_count;
   1089 	lane_count_set.bits.ENHANCED_FRAMING = lt_settings->enhanced_framing;
   1090 	lane_count_set.bits.POST_LT_ADJ_REQ_GRANTED = 0;
   1091 
   1092 	core_link_write_dpcd(
   1093 		link,
   1094 		DP_LANE_COUNT_SET,
   1095 		&lane_count_set.raw,
   1096 		sizeof(lane_count_set));
   1097 
   1098 	return status;
   1099 }
   1100 
   1101 static void initialize_training_settings(
   1102 	 struct dc_link *link,
   1103 	const struct dc_link_settings *link_setting,
   1104 	const struct dc_link_training_overrides *overrides,
   1105 	struct link_training_settings *lt_settings)
   1106 {
   1107 	uint32_t lane;
   1108 
   1109 	memset(lt_settings, '\0', sizeof(struct link_training_settings));
   1110 
   1111 	/* Initialize link settings */
   1112 	lt_settings->link_settings.use_link_rate_set = link_setting->use_link_rate_set;
   1113 	lt_settings->link_settings.link_rate_set = link_setting->link_rate_set;
   1114 
   1115 	if (link->preferred_link_setting.link_rate != LINK_RATE_UNKNOWN)
   1116 		lt_settings->link_settings.link_rate = link->preferred_link_setting.link_rate;
   1117 	else
   1118 		lt_settings->link_settings.link_rate = link_setting->link_rate;
   1119 
   1120 	if (link->preferred_link_setting.lane_count != LANE_COUNT_UNKNOWN)
   1121 		lt_settings->link_settings.lane_count = link->preferred_link_setting.lane_count;
   1122 	else
   1123 		lt_settings->link_settings.lane_count = link_setting->lane_count;
   1124 
   1125 	/*@todo[vdevulap] move SS to LS, should not be handled by displaypath*/
   1126 
   1127 	/* TODO hard coded to SS for now
   1128 	 * lt_settings.link_settings.link_spread =
   1129 	 * dal_display_path_is_ss_supported(
   1130 	 * path_mode->display_path) ?
   1131 	 * LINK_SPREAD_05_DOWNSPREAD_30KHZ :
   1132 	 * LINK_SPREAD_DISABLED;
   1133 	 */
   1134 	/* Initialize link spread */
   1135 	if (link->dp_ss_off)
   1136 		lt_settings->link_settings.link_spread = LINK_SPREAD_DISABLED;
   1137 	else if (overrides->downspread != NULL)
   1138 		lt_settings->link_settings.link_spread
   1139 			= *overrides->downspread
   1140 			? LINK_SPREAD_05_DOWNSPREAD_30KHZ
   1141 			: LINK_SPREAD_DISABLED;
   1142 	else
   1143 		lt_settings->link_settings.link_spread = LINK_SPREAD_05_DOWNSPREAD_30KHZ;
   1144 
   1145 	/* Initialize lane settings overrides */
   1146 	if (overrides->voltage_swing != NULL)
   1147 		lt_settings->voltage_swing = overrides->voltage_swing;
   1148 
   1149 	if (overrides->pre_emphasis != NULL)
   1150 		lt_settings->pre_emphasis = overrides->pre_emphasis;
   1151 
   1152 	if (overrides->post_cursor2 != NULL)
   1153 		lt_settings->post_cursor2 = overrides->post_cursor2;
   1154 
   1155 	/* Initialize lane settings (VS/PE/PC2) */
   1156 	for (lane = 0; lane < LANE_COUNT_DP_MAX; lane++) {
   1157 		lt_settings->lane_settings[lane].VOLTAGE_SWING =
   1158 			lt_settings->voltage_swing != NULL ?
   1159 			*lt_settings->voltage_swing :
   1160 			VOLTAGE_SWING_LEVEL0;
   1161 		lt_settings->lane_settings[lane].PRE_EMPHASIS =
   1162 			lt_settings->pre_emphasis != NULL ?
   1163 			*lt_settings->pre_emphasis
   1164 			: PRE_EMPHASIS_DISABLED;
   1165 		lt_settings->lane_settings[lane].POST_CURSOR2 =
   1166 			lt_settings->post_cursor2 != NULL ?
   1167 			*lt_settings->post_cursor2
   1168 			: POST_CURSOR2_DISABLED;
   1169 	}
   1170 
   1171 	/* Initialize training timings */
   1172 	if (overrides->cr_pattern_time != NULL)
   1173 		lt_settings->cr_pattern_time = *overrides->cr_pattern_time;
   1174 	else
   1175 		lt_settings->cr_pattern_time = get_training_aux_rd_interval(link, 100);
   1176 
   1177 	if (overrides->eq_pattern_time != NULL)
   1178 		lt_settings->eq_pattern_time = *overrides->eq_pattern_time;
   1179 	else
   1180 		lt_settings->eq_pattern_time = get_training_aux_rd_interval(link, 400);
   1181 
   1182 	if (overrides->pattern_for_eq != NULL)
   1183 		lt_settings->pattern_for_eq = *overrides->pattern_for_eq;
   1184 	else
   1185 		lt_settings->pattern_for_eq = get_supported_tp(link);
   1186 
   1187 	if (overrides->enhanced_framing != NULL)
   1188 		lt_settings->enhanced_framing = *overrides->enhanced_framing;
   1189 	else
   1190 		lt_settings->enhanced_framing = 1;
   1191 }
   1192 
   1193 static uint8_t convert_to_count(uint8_t lttpr_repeater_count)
   1194 {
   1195 	switch (lttpr_repeater_count) {
   1196 	case 0x80: // 1 lttpr repeater
   1197 		return 1;
   1198 	case 0x40: // 2 lttpr repeaters
   1199 		return 2;
   1200 	case 0x20: // 3 lttpr repeaters
   1201 		return 3;
   1202 	case 0x10: // 4 lttpr repeaters
   1203 		return 4;
   1204 	case 0x08: // 5 lttpr repeaters
   1205 		return 5;
   1206 	case 0x04: // 6 lttpr repeaters
   1207 		return 6;
   1208 	case 0x02: // 7 lttpr repeaters
   1209 		return 7;
   1210 	case 0x01: // 8 lttpr repeaters
   1211 		return 8;
   1212 	default:
   1213 		break;
   1214 	}
   1215 	return 0; // invalid value
   1216 }
   1217 
   1218 static void configure_lttpr_mode(struct dc_link *link)
   1219 {
   1220 	/* aux timeout is already set to extended */
   1221 	/* RESET/SET lttpr mode to enable non transparent mode */
   1222 	uint8_t repeater_cnt;
   1223 	uint32_t aux_interval_address;
   1224 	uint8_t repeater_id;
   1225 	enum dc_status result = DC_ERROR_UNEXPECTED;
   1226 	uint8_t repeater_mode = DP_PHY_REPEATER_MODE_TRANSPARENT;
   1227 
   1228 	DC_LOG_HW_LINK_TRAINING("%s\n Set LTTPR to Transparent Mode\n", __func__);
   1229 	result = core_link_write_dpcd(link,
   1230 			DP_PHY_REPEATER_MODE,
   1231 			(uint8_t *)&repeater_mode,
   1232 			sizeof(repeater_mode));
   1233 
   1234 	if (result == DC_OK) {
   1235 		link->dpcd_caps.lttpr_caps.mode = repeater_mode;
   1236 	}
   1237 
   1238 	if (!link->is_lttpr_mode_transparent) {
   1239 
   1240 		DC_LOG_HW_LINK_TRAINING("%s\n Set LTTPR to Non Transparent Mode\n", __func__);
   1241 
   1242 		repeater_mode = DP_PHY_REPEATER_MODE_NON_TRANSPARENT;
   1243 		result = core_link_write_dpcd(link,
   1244 				DP_PHY_REPEATER_MODE,
   1245 				(uint8_t *)&repeater_mode,
   1246 				sizeof(repeater_mode));
   1247 
   1248 		if (result == DC_OK) {
   1249 			link->dpcd_caps.lttpr_caps.mode = repeater_mode;
   1250 		}
   1251 
   1252 		repeater_cnt = convert_to_count(link->dpcd_caps.lttpr_caps.phy_repeater_cnt);
   1253 		for (repeater_id = repeater_cnt; repeater_id > 0; repeater_id--) {
   1254 			aux_interval_address = DP_TRAINING_AUX_RD_INTERVAL_PHY_REPEATER1 +
   1255 						((DP_REPEATER_CONFIGURATION_AND_STATUS_SIZE) * (repeater_id - 1));
   1256 			core_link_read_dpcd(
   1257 				link,
   1258 				aux_interval_address,
   1259 				(uint8_t *)&link->dpcd_caps.lttpr_caps.aux_rd_interval[repeater_id - 1],
   1260 				sizeof(link->dpcd_caps.lttpr_caps.aux_rd_interval[repeater_id - 1]));
   1261 			link->dpcd_caps.lttpr_caps.aux_rd_interval[repeater_id - 1] &= 0x7F;
   1262 		}
   1263 	}
   1264 }
   1265 
   1266 static void repeater_training_done(struct dc_link *link, uint32_t offset)
   1267 {
   1268 	union dpcd_training_pattern dpcd_pattern = { {0} };
   1269 
   1270 	const uint32_t dpcd_base_lt_offset =
   1271 			DP_TRAINING_PATTERN_SET_PHY_REPEATER1 +
   1272 				((DP_REPEATER_CONFIGURATION_AND_STATUS_SIZE) * (offset - 1));
   1273 	/* Set training not in progress*/
   1274 	dpcd_pattern.v1_4.TRAINING_PATTERN_SET = DPCD_TRAINING_PATTERN_VIDEOIDLE;
   1275 
   1276 	core_link_write_dpcd(
   1277 		link,
   1278 		dpcd_base_lt_offset,
   1279 		&dpcd_pattern.raw,
   1280 		1);
   1281 
   1282 	DC_LOG_HW_LINK_TRAINING("%s\n LTTPR Id: %d 0x%X pattern = %x\n",
   1283 		__func__,
   1284 		offset,
   1285 		dpcd_base_lt_offset,
   1286 		dpcd_pattern.v1_4.TRAINING_PATTERN_SET);
   1287 }
   1288 
   1289 static void print_status_message(
   1290 	struct dc_link *link,
   1291 	const struct link_training_settings *lt_settings,
   1292 	enum link_training_result status)
   1293 {
   1294 	const char *link_rate = "Unknown";
   1295 	const char *lt_result = "Unknown";
   1296 	const char *lt_spread = "Disabled";
   1297 
   1298 	switch (lt_settings->link_settings.link_rate) {
   1299 	case LINK_RATE_LOW:
   1300 		link_rate = "RBR";
   1301 		break;
   1302 	case LINK_RATE_HIGH:
   1303 		link_rate = "HBR";
   1304 		break;
   1305 	case LINK_RATE_HIGH2:
   1306 		link_rate = "HBR2";
   1307 		break;
   1308 	case LINK_RATE_RBR2:
   1309 		link_rate = "RBR2";
   1310 		break;
   1311 	case LINK_RATE_HIGH3:
   1312 		link_rate = "HBR3";
   1313 		break;
   1314 	default:
   1315 		break;
   1316 	}
   1317 
   1318 	switch (status) {
   1319 	case LINK_TRAINING_SUCCESS:
   1320 		lt_result = "pass";
   1321 		break;
   1322 	case LINK_TRAINING_CR_FAIL_LANE0:
   1323 		lt_result = "CR failed lane0";
   1324 		break;
   1325 	case LINK_TRAINING_CR_FAIL_LANE1:
   1326 		lt_result = "CR failed lane1";
   1327 		break;
   1328 	case LINK_TRAINING_CR_FAIL_LANE23:
   1329 		lt_result = "CR failed lane23";
   1330 		break;
   1331 	case LINK_TRAINING_EQ_FAIL_CR:
   1332 		lt_result = "CR failed in EQ";
   1333 		break;
   1334 	case LINK_TRAINING_EQ_FAIL_EQ:
   1335 		lt_result = "EQ failed";
   1336 		break;
   1337 	case LINK_TRAINING_LQA_FAIL:
   1338 		lt_result = "LQA failed";
   1339 		break;
   1340 	default:
   1341 		break;
   1342 	}
   1343 
   1344 	switch (lt_settings->link_settings.link_spread) {
   1345 	case LINK_SPREAD_DISABLED:
   1346 		lt_spread = "Disabled";
   1347 		break;
   1348 	case LINK_SPREAD_05_DOWNSPREAD_30KHZ:
   1349 		lt_spread = "0.5% 30KHz";
   1350 		break;
   1351 	case LINK_SPREAD_05_DOWNSPREAD_33KHZ:
   1352 		lt_spread = "0.5% 33KHz";
   1353 		break;
   1354 	default:
   1355 		break;
   1356 	}
   1357 
   1358 	/* Connectivity log: link training */
   1359 	CONN_MSG_LT(link, "%sx%d %s VS=%d, PE=%d, DS=%s",
   1360 				link_rate,
   1361 				lt_settings->link_settings.lane_count,
   1362 				lt_result,
   1363 				lt_settings->lane_settings[0].VOLTAGE_SWING,
   1364 				lt_settings->lane_settings[0].PRE_EMPHASIS,
   1365 				lt_spread);
   1366 }
   1367 
   1368 void dc_link_dp_set_drive_settings(
   1369 	struct dc_link *link,
   1370 	struct link_training_settings *lt_settings)
   1371 {
   1372 	/* program ASIC PHY settings*/
   1373 	dp_set_hw_lane_settings(link, lt_settings, DPRX);
   1374 
   1375 	/* Notify DP sink the PHY settings from source */
   1376 	dpcd_set_lane_settings(link, lt_settings, DPRX);
   1377 }
   1378 
   1379 bool dc_link_dp_perform_link_training_skip_aux(
   1380 	struct dc_link *link,
   1381 	const struct dc_link_settings *link_setting)
   1382 {
   1383 	struct link_training_settings lt_settings;
   1384 	enum dc_dp_training_pattern pattern_for_cr = DP_TRAINING_PATTERN_SEQUENCE_1;
   1385 
   1386 	initialize_training_settings(
   1387 			link,
   1388 			link_setting,
   1389 			&link->preferred_training_settings,
   1390 			&lt_settings);
   1391 
   1392 	/* 1. Perform_clock_recovery_sequence. */
   1393 
   1394 	/* transmit training pattern for clock recovery */
   1395 	dp_set_hw_training_pattern(link, pattern_for_cr, DPRX);
   1396 
   1397 	/* call HWSS to set lane settings*/
   1398 	dp_set_hw_lane_settings(link, &lt_settings, DPRX);
   1399 
   1400 	/* wait receiver to lock-on*/
   1401 	wait_for_training_aux_rd_interval(link, lt_settings.cr_pattern_time);
   1402 
   1403 	/* 2. Perform_channel_equalization_sequence. */
   1404 
   1405 	/* transmit training pattern for channel equalization. */
   1406 	dp_set_hw_training_pattern(link, lt_settings.pattern_for_eq, DPRX);
   1407 
   1408 	/* call HWSS to set lane settings*/
   1409 	dp_set_hw_lane_settings(link, &lt_settings, DPRX);
   1410 
   1411 	/* wait receiver to lock-on. */
   1412 	wait_for_training_aux_rd_interval(link, lt_settings.eq_pattern_time);
   1413 
   1414 	/* 3. Perform_link_training_int. */
   1415 
   1416 	/* Mainlink output idle pattern. */
   1417 	dp_set_hw_test_pattern(link, DP_TEST_PATTERN_VIDEO_MODE, NULL, 0);
   1418 
   1419 	print_status_message(link, &lt_settings, LINK_TRAINING_SUCCESS);
   1420 
   1421 	return true;
   1422 }
   1423 
   1424 enum link_training_result dc_link_dp_perform_link_training(
   1425 	struct dc_link *link,
   1426 	const struct dc_link_settings *link_setting,
   1427 	bool skip_video_pattern)
   1428 {
   1429 	enum link_training_result status = LINK_TRAINING_SUCCESS;
   1430 	struct link_training_settings lt_settings;
   1431 
   1432 	bool fec_enable;
   1433 	uint8_t repeater_cnt;
   1434 	uint8_t repeater_id;
   1435 
   1436 	initialize_training_settings(
   1437 			link,
   1438 			link_setting,
   1439 			&link->preferred_training_settings,
   1440 			&lt_settings);
   1441 
   1442 	/* 1. set link rate, lane count and spread. */
   1443 	dpcd_set_link_settings(link, &lt_settings);
   1444 
   1445 	if (link->preferred_training_settings.fec_enable != NULL)
   1446 		fec_enable = *link->preferred_training_settings.fec_enable;
   1447 	else
   1448 		fec_enable = true;
   1449 
   1450 	dp_set_fec_ready(link, fec_enable);
   1451 
   1452 	if (!link->is_lttpr_mode_transparent) {
   1453 		/* Configure lttpr mode */
   1454 		configure_lttpr_mode(link);
   1455 
   1456 		/* 2. perform link training (set link training done
   1457 		 *  to false is done as well)
   1458 		 */
   1459 		repeater_cnt = convert_to_count(link->dpcd_caps.lttpr_caps.phy_repeater_cnt);
   1460 
   1461 		for (repeater_id = repeater_cnt; (repeater_id > 0 && status == LINK_TRAINING_SUCCESS);
   1462 				repeater_id--) {
   1463 			status = perform_clock_recovery_sequence(link, &lt_settings, repeater_id);
   1464 
   1465 			if (status != LINK_TRAINING_SUCCESS)
   1466 				break;
   1467 
   1468 			status = perform_channel_equalization_sequence(link,
   1469 					&lt_settings,
   1470 					repeater_id);
   1471 
   1472 			if (status != LINK_TRAINING_SUCCESS)
   1473 				break;
   1474 
   1475 			repeater_training_done(link, repeater_id);
   1476 		}
   1477 	}
   1478 
   1479 	if (status == LINK_TRAINING_SUCCESS) {
   1480 		status = perform_clock_recovery_sequence(link, &lt_settings, DPRX);
   1481 	if (status == LINK_TRAINING_SUCCESS) {
   1482 		status = perform_channel_equalization_sequence(link,
   1483 					&lt_settings,
   1484 					DPRX);
   1485 		}
   1486 	}
   1487 
   1488 	if ((status == LINK_TRAINING_SUCCESS) || !skip_video_pattern) {
   1489 		status = perform_link_training_int(link,
   1490 				&lt_settings,
   1491 				status);
   1492 	}
   1493 
   1494 	/* 6. print status message*/
   1495 	print_status_message(link, &lt_settings, status);
   1496 
   1497 	if (status != LINK_TRAINING_SUCCESS)
   1498 		link->ctx->dc->debug_data.ltFailCount++;
   1499 
   1500 	return status;
   1501 }
   1502 
   1503 bool perform_link_training_with_retries(
   1504 	const struct dc_link_settings *link_setting,
   1505 	bool skip_video_pattern,
   1506 	int attempts,
   1507 	struct pipe_ctx *pipe_ctx,
   1508 	enum signal_type signal)
   1509 {
   1510 	uint8_t j;
   1511 	uint8_t delay_between_attempts = LINK_TRAINING_RETRY_DELAY;
   1512 	struct dc_stream_state *stream = pipe_ctx->stream;
   1513 	struct dc_link *link = stream->link;
   1514 	enum dp_panel_mode panel_mode = dp_get_panel_mode(link);
   1515 
   1516 	for (j = 0; j < attempts; ++j) {
   1517 
   1518 		dp_enable_link_phy(
   1519 			link,
   1520 			signal,
   1521 			pipe_ctx->clock_source->id,
   1522 			link_setting);
   1523 
   1524 		if (stream->sink_patches.dppowerup_delay > 0) {
   1525 			int delay_dp_power_up_in_ms = stream->sink_patches.dppowerup_delay;
   1526 
   1527 			msleep(delay_dp_power_up_in_ms);
   1528 		}
   1529 
   1530 		dp_set_panel_mode(link, panel_mode);
   1531 
   1532 		/* We need to do this before the link training to ensure the idle pattern in SST
   1533 		 * mode will be sent right after the link training
   1534 		 */
   1535 		link->link_enc->funcs->connect_dig_be_to_fe(link->link_enc,
   1536 								pipe_ctx->stream_res.stream_enc->id, true);
   1537 
   1538 		if (link->aux_access_disabled) {
   1539 			dc_link_dp_perform_link_training_skip_aux(link, link_setting);
   1540 			return true;
   1541 		} else if (dc_link_dp_perform_link_training(
   1542 				link,
   1543 				link_setting,
   1544 				skip_video_pattern) == LINK_TRAINING_SUCCESS)
   1545 			return true;
   1546 
   1547 		/* latest link training still fail, skip delay and keep PHY on
   1548 		 */
   1549 		if (j == (attempts - 1))
   1550 			break;
   1551 
   1552 		dp_disable_link_phy(link, signal);
   1553 
   1554 		msleep(delay_between_attempts);
   1555 
   1556 		delay_between_attempts += LINK_TRAINING_RETRY_DELAY;
   1557 	}
   1558 
   1559 	return false;
   1560 }
   1561 
   1562 static enum clock_source_id get_clock_source_id(struct dc_link *link)
   1563 {
   1564 	enum clock_source_id dp_cs_id = CLOCK_SOURCE_ID_UNDEFINED;
   1565 	struct clock_source *dp_cs = link->dc->res_pool->dp_clock_source;
   1566 
   1567 	if (dp_cs != NULL) {
   1568 		dp_cs_id = dp_cs->id;
   1569 	} else {
   1570 		/*
   1571 		 * dp clock source is not initialized for some reason.
   1572 		 * Should not happen, CLOCK_SOURCE_ID_EXTERNAL will be used
   1573 		 */
   1574 		ASSERT(dp_cs);
   1575 	}
   1576 
   1577 	return dp_cs_id;
   1578 }
   1579 
   1580 static void set_dp_mst_mode(struct dc_link *link, bool mst_enable)
   1581 {
   1582 	if (mst_enable == false &&
   1583 		link->type == dc_connection_mst_branch) {
   1584 		/* Disable MST on link. Use only local sink. */
   1585 		dp_disable_link_phy_mst(link, link->connector_signal);
   1586 
   1587 		link->type = dc_connection_single;
   1588 		link->local_sink = link->remote_sinks[0];
   1589 		link->local_sink->sink_signal = SIGNAL_TYPE_DISPLAY_PORT;
   1590 	} else if (mst_enable == true &&
   1591 			link->type == dc_connection_single &&
   1592 			link->remote_sinks[0] != NULL) {
   1593 		/* Re-enable MST on link. */
   1594 		dp_disable_link_phy(link, link->connector_signal);
   1595 		dp_enable_mst_on_sink(link, true);
   1596 
   1597 		link->type = dc_connection_mst_branch;
   1598 		link->local_sink->sink_signal = SIGNAL_TYPE_DISPLAY_PORT_MST;
   1599 	}
   1600 }
   1601 
   1602 bool dc_link_dp_sync_lt_begin(struct dc_link *link)
   1603 {
   1604 	/* Begin Sync LT. During this time,
   1605 	 * DPCD:600h must not be powered down.
   1606 	 */
   1607 	link->sync_lt_in_progress = true;
   1608 
   1609 	/*Clear any existing preferred settings.*/
   1610 	memset(&link->preferred_training_settings, 0,
   1611 		sizeof(struct dc_link_training_overrides));
   1612 	memset(&link->preferred_link_setting, 0,
   1613 		sizeof(struct dc_link_settings));
   1614 
   1615 	return true;
   1616 }
   1617 
   1618 enum link_training_result dc_link_dp_sync_lt_attempt(
   1619     struct dc_link *link,
   1620     struct dc_link_settings *link_settings,
   1621     struct dc_link_training_overrides *lt_overrides)
   1622 {
   1623 	struct link_training_settings lt_settings;
   1624 	enum link_training_result lt_status = LINK_TRAINING_SUCCESS;
   1625 	enum dp_panel_mode panel_mode = DP_PANEL_MODE_DEFAULT;
   1626 	enum clock_source_id dp_cs_id = CLOCK_SOURCE_ID_EXTERNAL;
   1627 	bool fec_enable = false;
   1628 
   1629 	initialize_training_settings(
   1630 		link,
   1631 		link_settings,
   1632 		lt_overrides,
   1633 		&lt_settings);
   1634 
   1635 	/* Setup MST Mode */
   1636 	if (lt_overrides->mst_enable)
   1637 		set_dp_mst_mode(link, *lt_overrides->mst_enable);
   1638 
   1639 	/* Disable link */
   1640 	dp_disable_link_phy(link, link->connector_signal);
   1641 
   1642 	/* Enable link */
   1643 	dp_cs_id = get_clock_source_id(link);
   1644 	dp_enable_link_phy(link, link->connector_signal,
   1645 		dp_cs_id, link_settings);
   1646 
   1647 	/* Set FEC enable */
   1648 	fec_enable = lt_overrides->fec_enable && *lt_overrides->fec_enable;
   1649 	dp_set_fec_ready(link, fec_enable);
   1650 
   1651 	if (lt_overrides->alternate_scrambler_reset) {
   1652 		if (*lt_overrides->alternate_scrambler_reset)
   1653 			panel_mode = DP_PANEL_MODE_EDP;
   1654 		else
   1655 			panel_mode = DP_PANEL_MODE_DEFAULT;
   1656 	} else
   1657 		panel_mode = dp_get_panel_mode(link);
   1658 
   1659 	dp_set_panel_mode(link, panel_mode);
   1660 
   1661 	/* Attempt to train with given link training settings */
   1662 
   1663 	/* Set link rate, lane count and spread. */
   1664 	dpcd_set_link_settings(link, &lt_settings);
   1665 
   1666 	/* 2. perform link training (set link training done
   1667 	 *  to false is done as well)
   1668 	 */
   1669 	lt_status = perform_clock_recovery_sequence(link, &lt_settings, DPRX);
   1670 	if (lt_status == LINK_TRAINING_SUCCESS) {
   1671 		lt_status = perform_channel_equalization_sequence(link,
   1672 						&lt_settings,
   1673 						DPRX);
   1674 	}
   1675 
   1676 	/* 3. Sync LT must skip TRAINING_PATTERN_SET:0 (video pattern)*/
   1677 	/* 4. print status message*/
   1678 	print_status_message(link, &lt_settings, lt_status);
   1679 
   1680 	return lt_status;
   1681 }
   1682 
   1683 bool dc_link_dp_sync_lt_end(struct dc_link *link, bool link_down)
   1684 {
   1685 	/* If input parameter is set, shut down phy.
   1686 	 * Still shouldn't turn off dp_receiver (DPCD:600h)
   1687 	 */
   1688 	if (link_down == true) {
   1689 		dp_disable_link_phy(link, link->connector_signal);
   1690 		dp_set_fec_ready(link, false);
   1691 	}
   1692 
   1693 	link->sync_lt_in_progress = false;
   1694 	return true;
   1695 }
   1696 
   1697 static struct dc_link_settings get_max_link_cap(struct dc_link *link)
   1698 {
   1699 	/* Set Default link settings */
   1700 	struct dc_link_settings max_link_cap = {LANE_COUNT_FOUR, LINK_RATE_HIGH,
   1701 			LINK_SPREAD_05_DOWNSPREAD_30KHZ, false, 0};
   1702 
   1703 	/* Higher link settings based on feature supported */
   1704 	if (link->link_enc->features.flags.bits.IS_HBR2_CAPABLE)
   1705 		max_link_cap.link_rate = LINK_RATE_HIGH2;
   1706 
   1707 	if (link->link_enc->features.flags.bits.IS_HBR3_CAPABLE)
   1708 		max_link_cap.link_rate = LINK_RATE_HIGH3;
   1709 
   1710 	if (link->link_enc->funcs->get_max_link_cap)
   1711 		link->link_enc->funcs->get_max_link_cap(link->link_enc, &max_link_cap);
   1712 
   1713 	/* Lower link settings based on sink's link cap */
   1714 	if (link->reported_link_cap.lane_count < max_link_cap.lane_count)
   1715 		max_link_cap.lane_count =
   1716 				link->reported_link_cap.lane_count;
   1717 	if (link->reported_link_cap.link_rate < max_link_cap.link_rate)
   1718 		max_link_cap.link_rate =
   1719 				link->reported_link_cap.link_rate;
   1720 	if (link->reported_link_cap.link_spread <
   1721 			max_link_cap.link_spread)
   1722 		max_link_cap.link_spread =
   1723 				link->reported_link_cap.link_spread;
   1724 	/*
   1725 	 * account for lttpr repeaters cap
   1726 	 * notes: repeaters do not snoop in the DPRX Capabilities addresses (3.6.3).
   1727 	 */
   1728 	if (!link->is_lttpr_mode_transparent) {
   1729 		if (link->dpcd_caps.lttpr_caps.max_lane_count < max_link_cap.lane_count)
   1730 			max_link_cap.lane_count = link->dpcd_caps.lttpr_caps.max_lane_count;
   1731 
   1732 		if (link->dpcd_caps.lttpr_caps.max_link_rate < max_link_cap.link_rate)
   1733 			max_link_cap.link_rate = link->dpcd_caps.lttpr_caps.max_link_rate;
   1734 
   1735 		DC_LOG_HW_LINK_TRAINING("%s\n Training with LTTPR,  max_lane count %d max_link rate %d \n",
   1736 						__func__,
   1737 						max_link_cap.lane_count,
   1738 						max_link_cap.link_rate);
   1739 	}
   1740 	return max_link_cap;
   1741 }
   1742 
   1743 static enum dc_status read_hpd_rx_irq_data(
   1744 	struct dc_link *link,
   1745 	union hpd_irq_data *irq_data)
   1746 {
   1747 	static enum dc_status retval;
   1748 
   1749 	/* The HW reads 16 bytes from 200h on HPD,
   1750 	 * but if we get an AUX_DEFER, the HW cannot retry
   1751 	 * and this causes the CTS tests 4.3.2.1 - 3.2.4 to
   1752 	 * fail, so we now explicitly read 6 bytes which is
   1753 	 * the req from the above mentioned test cases.
   1754 	 *
   1755 	 * For DP 1.4 we need to read those from 2002h range.
   1756 	 */
   1757 	if (link->dpcd_caps.dpcd_rev.raw < DPCD_REV_14)
   1758 		retval = core_link_read_dpcd(
   1759 			link,
   1760 			DP_SINK_COUNT,
   1761 			irq_data->raw,
   1762 			sizeof(union hpd_irq_data));
   1763 	else {
   1764 		/* Read 14 bytes in a single read and then copy only the required fields.
   1765 		 * This is more efficient than doing it in two separate AUX reads. */
   1766 
   1767 		uint8_t tmp[DP_SINK_STATUS_ESI - DP_SINK_COUNT_ESI + 1];
   1768 
   1769 		retval = core_link_read_dpcd(
   1770 			link,
   1771 			DP_SINK_COUNT_ESI,
   1772 			tmp,
   1773 			sizeof(tmp));
   1774 
   1775 		if (retval != DC_OK)
   1776 			return retval;
   1777 
   1778 		irq_data->bytes.sink_cnt.raw = tmp[DP_SINK_COUNT_ESI - DP_SINK_COUNT_ESI];
   1779 		irq_data->bytes.device_service_irq.raw = tmp[DP_DEVICE_SERVICE_IRQ_VECTOR_ESI0 - DP_SINK_COUNT_ESI];
   1780 		irq_data->bytes.lane01_status.raw = tmp[DP_LANE0_1_STATUS_ESI - DP_SINK_COUNT_ESI];
   1781 		irq_data->bytes.lane23_status.raw = tmp[DP_LANE2_3_STATUS_ESI - DP_SINK_COUNT_ESI];
   1782 		irq_data->bytes.lane_status_updated.raw = tmp[DP_LANE_ALIGN_STATUS_UPDATED_ESI - DP_SINK_COUNT_ESI];
   1783 		irq_data->bytes.sink_status.raw = tmp[DP_SINK_STATUS_ESI - DP_SINK_COUNT_ESI];
   1784 	}
   1785 
   1786 	return retval;
   1787 }
   1788 
   1789 static bool hpd_rx_irq_check_link_loss_status(
   1790 	struct dc_link *link,
   1791 	union hpd_irq_data *hpd_irq_dpcd_data)
   1792 {
   1793 	uint8_t irq_reg_rx_power_state = 0;
   1794 	enum dc_status dpcd_result = DC_ERROR_UNEXPECTED;
   1795 	union lane_status lane_status;
   1796 	uint32_t lane;
   1797 	bool sink_status_changed;
   1798 	bool return_code;
   1799 
   1800 	sink_status_changed = false;
   1801 	return_code = false;
   1802 
   1803 	if (link->cur_link_settings.lane_count == 0)
   1804 		return return_code;
   1805 
   1806 	/*1. Check that Link Status changed, before re-training.*/
   1807 
   1808 	/*parse lane status*/
   1809 	for (lane = 0; lane < link->cur_link_settings.lane_count; lane++) {
   1810 		/* check status of lanes 0,1
   1811 		 * changed DpcdAddress_Lane01Status (0x202)
   1812 		 */
   1813 		lane_status.raw = get_nibble_at_index(
   1814 			&hpd_irq_dpcd_data->bytes.lane01_status.raw,
   1815 			lane);
   1816 
   1817 		if (!lane_status.bits.CHANNEL_EQ_DONE_0 ||
   1818 			!lane_status.bits.CR_DONE_0 ||
   1819 			!lane_status.bits.SYMBOL_LOCKED_0) {
   1820 			/* if one of the channel equalization, clock
   1821 			 * recovery or symbol lock is dropped
   1822 			 * consider it as (link has been
   1823 			 * dropped) dp sink status has changed
   1824 			 */
   1825 			sink_status_changed = true;
   1826 			break;
   1827 		}
   1828 	}
   1829 
   1830 	/* Check interlane align.*/
   1831 	if (sink_status_changed ||
   1832 		!hpd_irq_dpcd_data->bytes.lane_status_updated.bits.INTERLANE_ALIGN_DONE) {
   1833 
   1834 		DC_LOG_HW_HPD_IRQ("%s: Link Status changed.\n", __func__);
   1835 
   1836 		return_code = true;
   1837 
   1838 		/*2. Check that we can handle interrupt: Not in FS DOS,
   1839 		 *  Not in "Display Timeout" state, Link is trained.
   1840 		 */
   1841 		dpcd_result = core_link_read_dpcd(link,
   1842 			DP_SET_POWER,
   1843 			&irq_reg_rx_power_state,
   1844 			sizeof(irq_reg_rx_power_state));
   1845 
   1846 		if (dpcd_result != DC_OK) {
   1847 			DC_LOG_HW_HPD_IRQ("%s: DPCD read failed to obtain power state.\n",
   1848 				__func__);
   1849 		} else {
   1850 			if (irq_reg_rx_power_state != DP_SET_POWER_D0)
   1851 				return_code = false;
   1852 		}
   1853 	}
   1854 
   1855 	return return_code;
   1856 }
   1857 
   1858 bool dp_verify_link_cap(
   1859 	struct dc_link *link,
   1860 	struct dc_link_settings *known_limit_link_setting,
   1861 	int *fail_count)
   1862 {
   1863 	struct dc_link_settings max_link_cap = {0};
   1864 	struct dc_link_settings cur_link_setting = {0};
   1865 	struct dc_link_settings *cur = &cur_link_setting;
   1866 	struct dc_link_settings initial_link_settings = {0};
   1867 	bool success;
   1868 	bool skip_link_training;
   1869 	bool skip_video_pattern;
   1870 	enum clock_source_id dp_cs_id = CLOCK_SOURCE_ID_EXTERNAL;
   1871 	enum link_training_result status;
   1872 	union hpd_irq_data irq_data;
   1873 
   1874 	if (link->dc->debug.skip_detection_link_training) {
   1875 		link->verified_link_cap = *known_limit_link_setting;
   1876 		return true;
   1877 	}
   1878 
   1879 	memset(&irq_data, 0, sizeof(irq_data));
   1880 	success = false;
   1881 	skip_link_training = false;
   1882 
   1883 	max_link_cap = get_max_link_cap(link);
   1884 
   1885 	/* Grant extended timeout request */
   1886 	if (!link->is_lttpr_mode_transparent && link->dpcd_caps.lttpr_caps.max_ext_timeout > 0) {
   1887 		uint8_t grant = link->dpcd_caps.lttpr_caps.max_ext_timeout & 0x80;
   1888 
   1889 		core_link_write_dpcd(link, DP_PHY_REPEATER_EXTENDED_WAIT_TIMEOUT, &grant, sizeof(grant));
   1890 	}
   1891 
   1892 	/* TODO implement override and monitor patch later */
   1893 
   1894 	/* try to train the link from high to low to
   1895 	 * find the physical link capability
   1896 	 */
   1897 	/* disable PHY done possible by BIOS, will be done by driver itself */
   1898 	dp_disable_link_phy(link, link->connector_signal);
   1899 
   1900 	/* Temporary Renoir-specific workaround for SWDEV-215184;
   1901 	 * PHY will sometimes be in bad state on hotplugging display from certain USB-C dongle,
   1902 	 * so add extra cycle of enabling and disabling the PHY before first link training.
   1903 	 */
   1904 	if (link->link_enc->features.flags.bits.DP_IS_USB_C &&
   1905 			link->dc->debug.usbc_combo_phy_reset_wa) {
   1906 		dp_enable_link_phy(link, link->connector_signal, dp_cs_id, cur);
   1907 		dp_disable_link_phy(link, link->connector_signal);
   1908 	}
   1909 
   1910 	dp_cs_id = get_clock_source_id(link);
   1911 
   1912 	/* link training starts with the maximum common settings
   1913 	 * supported by both sink and ASIC.
   1914 	 */
   1915 	initial_link_settings = get_common_supported_link_settings(
   1916 			*known_limit_link_setting,
   1917 			max_link_cap);
   1918 	cur_link_setting = initial_link_settings;
   1919 	do {
   1920 		skip_video_pattern = true;
   1921 
   1922 		if (cur->link_rate == LINK_RATE_LOW)
   1923 			skip_video_pattern = false;
   1924 
   1925 		dp_enable_link_phy(
   1926 				link,
   1927 				link->connector_signal,
   1928 				dp_cs_id,
   1929 				cur);
   1930 
   1931 
   1932 		if (skip_link_training)
   1933 			success = true;
   1934 		else {
   1935 			status = dc_link_dp_perform_link_training(
   1936 							link,
   1937 							cur,
   1938 							skip_video_pattern);
   1939 			if (status == LINK_TRAINING_SUCCESS)
   1940 				success = true;
   1941 			else
   1942 				(*fail_count)++;
   1943 		}
   1944 
   1945 		if (success) {
   1946 			link->verified_link_cap = *cur;
   1947 			udelay(1000);
   1948 			if (read_hpd_rx_irq_data(link, &irq_data) == DC_OK)
   1949 				if (hpd_rx_irq_check_link_loss_status(
   1950 						link,
   1951 						&irq_data))
   1952 					(*fail_count)++;
   1953 		}
   1954 		/* always disable the link before trying another
   1955 		 * setting or before returning we'll enable it later
   1956 		 * based on the actual mode we're driving
   1957 		 */
   1958 		dp_disable_link_phy(link, link->connector_signal);
   1959 	} while (!success && decide_fallback_link_setting(
   1960 			initial_link_settings, cur, status));
   1961 
   1962 	/* Link Training failed for all Link Settings
   1963 	 *  (Lane Count is still unknown)
   1964 	 */
   1965 	if (!success) {
   1966 		/* If all LT fails for all settings,
   1967 		 * set verified = failed safe (1 lane low)
   1968 		 */
   1969 		link->verified_link_cap.lane_count = LANE_COUNT_ONE;
   1970 		link->verified_link_cap.link_rate = LINK_RATE_LOW;
   1971 
   1972 		link->verified_link_cap.link_spread =
   1973 		LINK_SPREAD_DISABLED;
   1974 	}
   1975 
   1976 
   1977 	return success;
   1978 }
   1979 
   1980 bool dp_verify_link_cap_with_retries(
   1981 	struct dc_link *link,
   1982 	struct dc_link_settings *known_limit_link_setting,
   1983 	int attempts)
   1984 {
   1985 	uint8_t i = 0;
   1986 	bool success = false;
   1987 
   1988 	for (i = 0; i < attempts; i++) {
   1989 		int fail_count = 0;
   1990 		enum dc_connection_type type = dc_connection_none;
   1991 
   1992 		memset(&link->verified_link_cap, 0,
   1993 				sizeof(struct dc_link_settings));
   1994 		if (!dc_link_detect_sink(link, &type) || type == dc_connection_none) {
   1995 			link->verified_link_cap.lane_count = LANE_COUNT_ONE;
   1996 			link->verified_link_cap.link_rate = LINK_RATE_LOW;
   1997 			link->verified_link_cap.link_spread = LINK_SPREAD_DISABLED;
   1998 			break;
   1999 		} else if (dp_verify_link_cap(link,
   2000 				&link->reported_link_cap,
   2001 				&fail_count) && fail_count == 0) {
   2002 			success = true;
   2003 			break;
   2004 		}
   2005 		msleep(10);
   2006 	}
   2007 	return success;
   2008 }
   2009 
   2010 bool dp_verify_mst_link_cap(
   2011 	struct dc_link *link)
   2012 {
   2013 	struct dc_link_settings max_link_cap = {0};
   2014 
   2015 	max_link_cap = get_max_link_cap(link);
   2016 	link->verified_link_cap = get_common_supported_link_settings(
   2017 		link->reported_link_cap,
   2018 		max_link_cap);
   2019 
   2020 	return true;
   2021 }
   2022 
   2023 static struct dc_link_settings get_common_supported_link_settings(
   2024 		struct dc_link_settings link_setting_a,
   2025 		struct dc_link_settings link_setting_b)
   2026 {
   2027 	struct dc_link_settings link_settings = {0};
   2028 
   2029 	link_settings.lane_count =
   2030 		(link_setting_a.lane_count <=
   2031 			link_setting_b.lane_count) ?
   2032 			link_setting_a.lane_count :
   2033 			link_setting_b.lane_count;
   2034 	link_settings.link_rate =
   2035 		(link_setting_a.link_rate <=
   2036 			link_setting_b.link_rate) ?
   2037 			link_setting_a.link_rate :
   2038 			link_setting_b.link_rate;
   2039 	link_settings.link_spread = LINK_SPREAD_DISABLED;
   2040 
   2041 	/* in DP compliance test, DPR-120 may have
   2042 	 * a random value in its MAX_LINK_BW dpcd field.
   2043 	 * We map it to the maximum supported link rate that
   2044 	 * is smaller than MAX_LINK_BW in this case.
   2045 	 */
   2046 	if (link_settings.link_rate > LINK_RATE_HIGH3) {
   2047 		link_settings.link_rate = LINK_RATE_HIGH3;
   2048 	} else if (link_settings.link_rate < LINK_RATE_HIGH3
   2049 			&& link_settings.link_rate > LINK_RATE_HIGH2) {
   2050 		link_settings.link_rate = LINK_RATE_HIGH2;
   2051 	} else if (link_settings.link_rate < LINK_RATE_HIGH2
   2052 			&& link_settings.link_rate > LINK_RATE_HIGH) {
   2053 		link_settings.link_rate = LINK_RATE_HIGH;
   2054 	} else if (link_settings.link_rate < LINK_RATE_HIGH
   2055 			&& link_settings.link_rate > LINK_RATE_LOW) {
   2056 		link_settings.link_rate = LINK_RATE_LOW;
   2057 	} else if (link_settings.link_rate < LINK_RATE_LOW) {
   2058 		link_settings.link_rate = LINK_RATE_UNKNOWN;
   2059 	}
   2060 
   2061 	return link_settings;
   2062 }
   2063 
   2064 static inline bool reached_minimum_lane_count(enum dc_lane_count lane_count)
   2065 {
   2066 	return lane_count <= LANE_COUNT_ONE;
   2067 }
   2068 
   2069 static inline bool reached_minimum_link_rate(enum dc_link_rate link_rate)
   2070 {
   2071 	return link_rate <= LINK_RATE_LOW;
   2072 }
   2073 
   2074 static enum dc_lane_count reduce_lane_count(enum dc_lane_count lane_count)
   2075 {
   2076 	switch (lane_count) {
   2077 	case LANE_COUNT_FOUR:
   2078 		return LANE_COUNT_TWO;
   2079 	case LANE_COUNT_TWO:
   2080 		return LANE_COUNT_ONE;
   2081 	case LANE_COUNT_ONE:
   2082 		return LANE_COUNT_UNKNOWN;
   2083 	default:
   2084 		return LANE_COUNT_UNKNOWN;
   2085 	}
   2086 }
   2087 
   2088 static enum dc_link_rate reduce_link_rate(enum dc_link_rate link_rate)
   2089 {
   2090 	switch (link_rate) {
   2091 	case LINK_RATE_HIGH3:
   2092 		return LINK_RATE_HIGH2;
   2093 	case LINK_RATE_HIGH2:
   2094 		return LINK_RATE_HIGH;
   2095 	case LINK_RATE_HIGH:
   2096 		return LINK_RATE_LOW;
   2097 	case LINK_RATE_LOW:
   2098 		return LINK_RATE_UNKNOWN;
   2099 	default:
   2100 		return LINK_RATE_UNKNOWN;
   2101 	}
   2102 }
   2103 
   2104 static enum dc_lane_count increase_lane_count(enum dc_lane_count lane_count)
   2105 {
   2106 	switch (lane_count) {
   2107 	case LANE_COUNT_ONE:
   2108 		return LANE_COUNT_TWO;
   2109 	case LANE_COUNT_TWO:
   2110 		return LANE_COUNT_FOUR;
   2111 	default:
   2112 		return LANE_COUNT_UNKNOWN;
   2113 	}
   2114 }
   2115 
   2116 static enum dc_link_rate increase_link_rate(enum dc_link_rate link_rate)
   2117 {
   2118 	switch (link_rate) {
   2119 	case LINK_RATE_LOW:
   2120 		return LINK_RATE_HIGH;
   2121 	case LINK_RATE_HIGH:
   2122 		return LINK_RATE_HIGH2;
   2123 	case LINK_RATE_HIGH2:
   2124 		return LINK_RATE_HIGH3;
   2125 	default:
   2126 		return LINK_RATE_UNKNOWN;
   2127 	}
   2128 }
   2129 
   2130 /*
   2131  * function: set link rate and lane count fallback based
   2132  * on current link setting and last link training result
   2133  * return value:
   2134  *			true - link setting could be set
   2135  *			false - has reached minimum setting
   2136  *					and no further fallback could be done
   2137  */
   2138 static bool decide_fallback_link_setting(
   2139 		struct dc_link_settings initial_link_settings,
   2140 		struct dc_link_settings *current_link_setting,
   2141 		enum link_training_result training_result)
   2142 {
   2143 	if (!current_link_setting)
   2144 		return false;
   2145 
   2146 	switch (training_result) {
   2147 	case LINK_TRAINING_CR_FAIL_LANE0:
   2148 	case LINK_TRAINING_CR_FAIL_LANE1:
   2149 	case LINK_TRAINING_CR_FAIL_LANE23:
   2150 	case LINK_TRAINING_LQA_FAIL:
   2151 	{
   2152 		if (!reached_minimum_link_rate
   2153 				(current_link_setting->link_rate)) {
   2154 			current_link_setting->link_rate =
   2155 				reduce_link_rate(
   2156 					current_link_setting->link_rate);
   2157 		} else if (!reached_minimum_lane_count
   2158 				(current_link_setting->lane_count)) {
   2159 			current_link_setting->link_rate =
   2160 				initial_link_settings.link_rate;
   2161 			if (training_result == LINK_TRAINING_CR_FAIL_LANE0)
   2162 				return false;
   2163 			else if (training_result == LINK_TRAINING_CR_FAIL_LANE1)
   2164 				current_link_setting->lane_count =
   2165 						LANE_COUNT_ONE;
   2166 			else if (training_result ==
   2167 					LINK_TRAINING_CR_FAIL_LANE23)
   2168 				current_link_setting->lane_count =
   2169 						LANE_COUNT_TWO;
   2170 			else
   2171 				current_link_setting->lane_count =
   2172 					reduce_lane_count(
   2173 					current_link_setting->lane_count);
   2174 		} else {
   2175 			return false;
   2176 		}
   2177 		break;
   2178 	}
   2179 	case LINK_TRAINING_EQ_FAIL_EQ:
   2180 	{
   2181 		if (!reached_minimum_lane_count
   2182 				(current_link_setting->lane_count)) {
   2183 			current_link_setting->lane_count =
   2184 				reduce_lane_count(
   2185 					current_link_setting->lane_count);
   2186 		} else if (!reached_minimum_link_rate
   2187 				(current_link_setting->link_rate)) {
   2188 			current_link_setting->link_rate =
   2189 				reduce_link_rate(
   2190 					current_link_setting->link_rate);
   2191 		} else {
   2192 			return false;
   2193 		}
   2194 		break;
   2195 	}
   2196 	case LINK_TRAINING_EQ_FAIL_CR:
   2197 	{
   2198 		if (!reached_minimum_link_rate
   2199 				(current_link_setting->link_rate)) {
   2200 			current_link_setting->link_rate =
   2201 				reduce_link_rate(
   2202 					current_link_setting->link_rate);
   2203 		} else {
   2204 			return false;
   2205 		}
   2206 		break;
   2207 	}
   2208 	default:
   2209 		return false;
   2210 	}
   2211 	return true;
   2212 }
   2213 
   2214 bool dp_validate_mode_timing(
   2215 	struct dc_link *link,
   2216 	const struct dc_crtc_timing *timing)
   2217 {
   2218 	uint32_t req_bw;
   2219 	uint32_t max_bw;
   2220 
   2221 	const struct dc_link_settings *link_setting;
   2222 
   2223 	/*always DP fail safe mode*/
   2224 	if ((timing->pix_clk_100hz / 10) == (uint32_t) 25175 &&
   2225 		timing->h_addressable == (uint32_t) 640 &&
   2226 		timing->v_addressable == (uint32_t) 480)
   2227 		return true;
   2228 
   2229 	link_setting = dc_link_get_link_cap(link);
   2230 
   2231 	/* TODO: DYNAMIC_VALIDATION needs to be implemented */
   2232 	/*if (flags.DYNAMIC_VALIDATION == 1 &&
   2233 		link->verified_link_cap.lane_count != LANE_COUNT_UNKNOWN)
   2234 		link_setting = &link->verified_link_cap;
   2235 	*/
   2236 
   2237 	req_bw = dc_bandwidth_in_kbps_from_timing(timing);
   2238 	max_bw = dc_link_bandwidth_kbps(link, link_setting);
   2239 
   2240 	if (req_bw <= max_bw) {
   2241 		/* remember the biggest mode here, during
   2242 		 * initial link training (to get
   2243 		 * verified_link_cap), LS sends event about
   2244 		 * cannot train at reported cap to upper
   2245 		 * layer and upper layer will re-enumerate modes.
   2246 		 * this is not necessary if the lower
   2247 		 * verified_link_cap is enough to drive
   2248 		 * all the modes */
   2249 
   2250 		/* TODO: DYNAMIC_VALIDATION needs to be implemented */
   2251 		/* if (flags.DYNAMIC_VALIDATION == 1)
   2252 			dpsst->max_req_bw_for_verified_linkcap = dal_max(
   2253 				dpsst->max_req_bw_for_verified_linkcap, req_bw); */
   2254 		return true;
   2255 	} else
   2256 		return false;
   2257 }
   2258 
   2259 static bool decide_dp_link_settings(struct dc_link *link, struct dc_link_settings *link_setting, uint32_t req_bw)
   2260 {
   2261 	struct dc_link_settings initial_link_setting = {
   2262 		LANE_COUNT_ONE, LINK_RATE_LOW, LINK_SPREAD_DISABLED, false, 0};
   2263 	struct dc_link_settings current_link_setting =
   2264 			initial_link_setting;
   2265 	uint32_t link_bw;
   2266 
   2267 	/* search for the minimum link setting that:
   2268 	 * 1. is supported according to the link training result
   2269 	 * 2. could support the b/w requested by the timing
   2270 	 */
   2271 	while (current_link_setting.link_rate <=
   2272 			link->verified_link_cap.link_rate) {
   2273 		link_bw = dc_link_bandwidth_kbps(
   2274 				link,
   2275 				&current_link_setting);
   2276 		if (req_bw <= link_bw) {
   2277 			*link_setting = current_link_setting;
   2278 			return true;
   2279 		}
   2280 
   2281 		if (current_link_setting.lane_count <
   2282 				link->verified_link_cap.lane_count) {
   2283 			current_link_setting.lane_count =
   2284 					increase_lane_count(
   2285 							current_link_setting.lane_count);
   2286 		} else {
   2287 			current_link_setting.link_rate =
   2288 					increase_link_rate(
   2289 							current_link_setting.link_rate);
   2290 			current_link_setting.lane_count =
   2291 					initial_link_setting.lane_count;
   2292 		}
   2293 	}
   2294 
   2295 	return false;
   2296 }
   2297 
   2298 static bool decide_edp_link_settings(struct dc_link *link, struct dc_link_settings *link_setting, uint32_t req_bw)
   2299 {
   2300 	struct dc_link_settings initial_link_setting;
   2301 	struct dc_link_settings current_link_setting;
   2302 	uint32_t link_bw;
   2303 
   2304 	if (link->dpcd_caps.dpcd_rev.raw < DPCD_REV_14 ||
   2305 			link->dpcd_caps.edp_supported_link_rates_count == 0) {
   2306 		*link_setting = link->verified_link_cap;
   2307 		return true;
   2308 	}
   2309 
   2310 	memset(&initial_link_setting, 0, sizeof(initial_link_setting));
   2311 	initial_link_setting.lane_count = LANE_COUNT_ONE;
   2312 	initial_link_setting.link_rate = link->dpcd_caps.edp_supported_link_rates[0];
   2313 	initial_link_setting.link_spread = LINK_SPREAD_DISABLED;
   2314 	initial_link_setting.use_link_rate_set = true;
   2315 	initial_link_setting.link_rate_set = 0;
   2316 	current_link_setting = initial_link_setting;
   2317 
   2318 	/* search for the minimum link setting that:
   2319 	 * 1. is supported according to the link training result
   2320 	 * 2. could support the b/w requested by the timing
   2321 	 */
   2322 	while (current_link_setting.link_rate <=
   2323 			link->verified_link_cap.link_rate) {
   2324 		link_bw = dc_link_bandwidth_kbps(
   2325 				link,
   2326 				&current_link_setting);
   2327 		if (req_bw <= link_bw) {
   2328 			*link_setting = current_link_setting;
   2329 			return true;
   2330 		}
   2331 
   2332 		if (current_link_setting.lane_count <
   2333 				link->verified_link_cap.lane_count) {
   2334 			current_link_setting.lane_count =
   2335 					increase_lane_count(
   2336 							current_link_setting.lane_count);
   2337 		} else {
   2338 			if (current_link_setting.link_rate_set < link->dpcd_caps.edp_supported_link_rates_count) {
   2339 				current_link_setting.link_rate_set++;
   2340 				current_link_setting.link_rate =
   2341 					link->dpcd_caps.edp_supported_link_rates[current_link_setting.link_rate_set];
   2342 				current_link_setting.lane_count =
   2343 									initial_link_setting.lane_count;
   2344 			} else
   2345 				break;
   2346 		}
   2347 	}
   2348 	return false;
   2349 }
   2350 
   2351 void decide_link_settings(struct dc_stream_state *stream,
   2352 	struct dc_link_settings *link_setting)
   2353 {
   2354 	struct dc_link *link;
   2355 	uint32_t req_bw;
   2356 
   2357 	req_bw = dc_bandwidth_in_kbps_from_timing(&stream->timing);
   2358 
   2359 	link = stream->link;
   2360 
   2361 	/* if preferred is specified through AMDDP, use it, if it's enough
   2362 	 * to drive the mode
   2363 	 */
   2364 	if (link->preferred_link_setting.lane_count !=
   2365 			LANE_COUNT_UNKNOWN &&
   2366 			link->preferred_link_setting.link_rate !=
   2367 					LINK_RATE_UNKNOWN) {
   2368 		*link_setting =  link->preferred_link_setting;
   2369 		return;
   2370 	}
   2371 
   2372 	/* MST doesn't perform link training for now
   2373 	 * TODO: add MST specific link training routine
   2374 	 */
   2375 	if (stream->signal == SIGNAL_TYPE_DISPLAY_PORT_MST) {
   2376 		*link_setting = link->verified_link_cap;
   2377 		return;
   2378 	}
   2379 
   2380 	if (link->connector_signal == SIGNAL_TYPE_EDP) {
   2381 		if (decide_edp_link_settings(link, link_setting, req_bw))
   2382 			return;
   2383 	} else if (decide_dp_link_settings(link, link_setting, req_bw))
   2384 		return;
   2385 
   2386 	BREAK_TO_DEBUGGER();
   2387 	ASSERT(link->verified_link_cap.lane_count != LANE_COUNT_UNKNOWN);
   2388 
   2389 	*link_setting = link->verified_link_cap;
   2390 }
   2391 
   2392 /*************************Short Pulse IRQ***************************/
   2393 static bool allow_hpd_rx_irq(const struct dc_link *link)
   2394 {
   2395 	/*
   2396 	 * Don't handle RX IRQ unless one of following is met:
   2397 	 * 1) The link is established (cur_link_settings != unknown)
   2398 	 * 2) We kicked off MST detection
   2399 	 * 3) We know we're dealing with an active dongle
   2400 	 */
   2401 
   2402 	if ((link->cur_link_settings.lane_count != LANE_COUNT_UNKNOWN) ||
   2403 		(link->type == dc_connection_mst_branch) ||
   2404 		is_dp_active_dongle(link))
   2405 		return true;
   2406 
   2407 	return false;
   2408 }
   2409 
   2410 static bool handle_hpd_irq_psr_sink(struct dc_link *link)
   2411 {
   2412 	union dpcd_psr_configuration psr_configuration;
   2413 
   2414 	if (!link->psr_feature_enabled)
   2415 		return false;
   2416 
   2417 	dm_helpers_dp_read_dpcd(
   2418 		link->ctx,
   2419 		link,
   2420 		368,/*DpcdAddress_PSR_Enable_Cfg*/
   2421 		&psr_configuration.raw,
   2422 		sizeof(psr_configuration.raw));
   2423 
   2424 
   2425 	if (psr_configuration.bits.ENABLE) {
   2426 		unsigned char dpcdbuf[3] = {0};
   2427 		union psr_error_status psr_error_status;
   2428 		union psr_sink_psr_status psr_sink_psr_status;
   2429 
   2430 		dm_helpers_dp_read_dpcd(
   2431 			link->ctx,
   2432 			link,
   2433 			0x2006, /*DpcdAddress_PSR_Error_Status*/
   2434 			(unsigned char *) dpcdbuf,
   2435 			sizeof(dpcdbuf));
   2436 
   2437 		/*DPCD 2006h   ERROR STATUS*/
   2438 		psr_error_status.raw = dpcdbuf[0];
   2439 		/*DPCD 2008h   SINK PANEL SELF REFRESH STATUS*/
   2440 		psr_sink_psr_status.raw = dpcdbuf[2];
   2441 
   2442 		if (psr_error_status.bits.LINK_CRC_ERROR ||
   2443 				psr_error_status.bits.RFB_STORAGE_ERROR) {
   2444 			/* Acknowledge and clear error bits */
   2445 			dm_helpers_dp_write_dpcd(
   2446 				link->ctx,
   2447 				link,
   2448 				8198,/*DpcdAddress_PSR_Error_Status*/
   2449 				&psr_error_status.raw,
   2450 				sizeof(psr_error_status.raw));
   2451 
   2452 			/* PSR error, disable and re-enable PSR */
   2453 			dc_link_set_psr_allow_active(link, false, true);
   2454 			dc_link_set_psr_allow_active(link, true, true);
   2455 
   2456 			return true;
   2457 		} else if (psr_sink_psr_status.bits.SINK_SELF_REFRESH_STATUS ==
   2458 				PSR_SINK_STATE_ACTIVE_DISPLAY_FROM_SINK_RFB){
   2459 			/* No error is detect, PSR is active.
   2460 			 * We should return with IRQ_HPD handled without
   2461 			 * checking for loss of sync since PSR would have
   2462 			 * powered down main link.
   2463 			 */
   2464 			return true;
   2465 		}
   2466 	}
   2467 	return false;
   2468 }
   2469 
   2470 static void dp_test_send_link_training(struct dc_link *link)
   2471 {
   2472 	struct dc_link_settings link_settings = {0};
   2473 
   2474 	core_link_read_dpcd(
   2475 			link,
   2476 			DP_TEST_LANE_COUNT,
   2477 			(unsigned char *)(&link_settings.lane_count),
   2478 			1);
   2479 	core_link_read_dpcd(
   2480 			link,
   2481 			DP_TEST_LINK_RATE,
   2482 			(unsigned char *)(&link_settings.link_rate),
   2483 			1);
   2484 
   2485 	/* Set preferred link settings */
   2486 	link->verified_link_cap.lane_count = link_settings.lane_count;
   2487 	link->verified_link_cap.link_rate = link_settings.link_rate;
   2488 
   2489 	dp_retrain_link_dp_test(link, &link_settings, false);
   2490 }
   2491 
   2492 /* TODO Raven hbr2 compliance eye output is unstable
   2493  * (toggling on and off) with debugger break
   2494  * This caueses intermittent PHY automation failure
   2495  * Need to look into the root cause */
   2496 static void dp_test_send_phy_test_pattern(struct dc_link *link)
   2497 {
   2498 	union phy_test_pattern dpcd_test_pattern;
   2499 	union lane_adjust dpcd_lane_adjustment[2];
   2500 	unsigned char dpcd_post_cursor_2_adjustment = 0;
   2501 	unsigned char test_80_bit_pattern[
   2502 			(DP_TEST_80BIT_CUSTOM_PATTERN_79_72 -
   2503 			DP_TEST_80BIT_CUSTOM_PATTERN_7_0)+1] = {0};
   2504 	enum dp_test_pattern test_pattern;
   2505 	struct dc_link_training_settings link_settings;
   2506 	union lane_adjust dpcd_lane_adjust;
   2507 	unsigned int lane;
   2508 	struct link_training_settings link_training_settings;
   2509 	int i = 0;
   2510 
   2511 	dpcd_test_pattern.raw = 0;
   2512 	memset(dpcd_lane_adjustment, 0, sizeof(dpcd_lane_adjustment));
   2513 	memset(&link_settings, 0, sizeof(link_settings));
   2514 
   2515 	/* get phy test pattern and pattern parameters from DP receiver */
   2516 	core_link_read_dpcd(
   2517 			link,
   2518 			DP_TEST_PHY_PATTERN,
   2519 			&dpcd_test_pattern.raw,
   2520 			sizeof(dpcd_test_pattern));
   2521 	core_link_read_dpcd(
   2522 			link,
   2523 			DP_ADJUST_REQUEST_LANE0_1,
   2524 			&dpcd_lane_adjustment[0].raw,
   2525 			sizeof(dpcd_lane_adjustment));
   2526 
   2527 	/*get post cursor 2 parameters
   2528 	 * For DP 1.1a or eariler, this DPCD register's value is 0
   2529 	 * For DP 1.2 or later:
   2530 	 * Bits 1:0 = POST_CURSOR2_LANE0; Bits 3:2 = POST_CURSOR2_LANE1
   2531 	 * Bits 5:4 = POST_CURSOR2_LANE2; Bits 7:6 = POST_CURSOR2_LANE3
   2532 	 */
   2533 	core_link_read_dpcd(
   2534 			link,
   2535 			DP_ADJUST_REQUEST_POST_CURSOR2,
   2536 			&dpcd_post_cursor_2_adjustment,
   2537 			sizeof(dpcd_post_cursor_2_adjustment));
   2538 
   2539 	/* translate request */
   2540 	switch (dpcd_test_pattern.bits.PATTERN) {
   2541 	case PHY_TEST_PATTERN_D10_2:
   2542 		test_pattern = DP_TEST_PATTERN_D102;
   2543 		break;
   2544 	case PHY_TEST_PATTERN_SYMBOL_ERROR:
   2545 		test_pattern = DP_TEST_PATTERN_SYMBOL_ERROR;
   2546 		break;
   2547 	case PHY_TEST_PATTERN_PRBS7:
   2548 		test_pattern = DP_TEST_PATTERN_PRBS7;
   2549 		break;
   2550 	case PHY_TEST_PATTERN_80BIT_CUSTOM:
   2551 		test_pattern = DP_TEST_PATTERN_80BIT_CUSTOM;
   2552 		break;
   2553 	case PHY_TEST_PATTERN_CP2520_1:
   2554 		/* CP2520 pattern is unstable, temporarily use TPS4 instead */
   2555 		test_pattern = (link->dc->caps.force_dp_tps4_for_cp2520 == 1) ?
   2556 				DP_TEST_PATTERN_TRAINING_PATTERN4 :
   2557 				DP_TEST_PATTERN_HBR2_COMPLIANCE_EYE;
   2558 		break;
   2559 	case PHY_TEST_PATTERN_CP2520_2:
   2560 		/* CP2520 pattern is unstable, temporarily use TPS4 instead */
   2561 		test_pattern = (link->dc->caps.force_dp_tps4_for_cp2520 == 1) ?
   2562 				DP_TEST_PATTERN_TRAINING_PATTERN4 :
   2563 				DP_TEST_PATTERN_HBR2_COMPLIANCE_EYE;
   2564 		break;
   2565 	case PHY_TEST_PATTERN_CP2520_3:
   2566 		test_pattern = DP_TEST_PATTERN_TRAINING_PATTERN4;
   2567 		break;
   2568 	default:
   2569 		test_pattern = DP_TEST_PATTERN_VIDEO_MODE;
   2570 	break;
   2571 	}
   2572 
   2573 	if (test_pattern == DP_TEST_PATTERN_80BIT_CUSTOM)
   2574 		core_link_read_dpcd(
   2575 				link,
   2576 				DP_TEST_80BIT_CUSTOM_PATTERN_7_0,
   2577 				test_80_bit_pattern,
   2578 				sizeof(test_80_bit_pattern));
   2579 
   2580 	/* prepare link training settings */
   2581 	link_settings.link = link->cur_link_settings;
   2582 
   2583 	for (lane = 0; lane <
   2584 		(unsigned int)(link->cur_link_settings.lane_count);
   2585 		lane++) {
   2586 		dpcd_lane_adjust.raw =
   2587 			get_nibble_at_index(&dpcd_lane_adjustment[0].raw, lane);
   2588 		link_settings.lane_settings[lane].VOLTAGE_SWING =
   2589 			(enum dc_voltage_swing)
   2590 			(dpcd_lane_adjust.bits.VOLTAGE_SWING_LANE);
   2591 		link_settings.lane_settings[lane].PRE_EMPHASIS =
   2592 			(enum dc_pre_emphasis)
   2593 			(dpcd_lane_adjust.bits.PRE_EMPHASIS_LANE);
   2594 		link_settings.lane_settings[lane].POST_CURSOR2 =
   2595 			(enum dc_post_cursor2)
   2596 			((dpcd_post_cursor_2_adjustment >> (lane * 2)) & 0x03);
   2597 	}
   2598 
   2599 	for (i = 0; i < 4; i++)
   2600 		link_training_settings.lane_settings[i] =
   2601 				link_settings.lane_settings[i];
   2602 	link_training_settings.link_settings = link_settings.link;
   2603 	link_training_settings.allow_invalid_msa_timing_param = false;
   2604 	/*Usage: Measure DP physical lane signal
   2605 	 * by DP SI test equipment automatically.
   2606 	 * PHY test pattern request is generated by equipment via HPD interrupt.
   2607 	 * HPD needs to be active all the time. HPD should be active
   2608 	 * all the time. Do not touch it.
   2609 	 * forward request to DS
   2610 	 */
   2611 	dc_link_dp_set_test_pattern(
   2612 		link,
   2613 		test_pattern,
   2614 		DP_TEST_PATTERN_COLOR_SPACE_UNDEFINED,
   2615 		&link_training_settings,
   2616 		test_80_bit_pattern,
   2617 		(DP_TEST_80BIT_CUSTOM_PATTERN_79_72 -
   2618 		DP_TEST_80BIT_CUSTOM_PATTERN_7_0)+1);
   2619 }
   2620 
   2621 static void dp_test_send_link_test_pattern(struct dc_link *link)
   2622 {
   2623 	union link_test_pattern dpcd_test_pattern;
   2624 	union test_misc dpcd_test_params;
   2625 	enum dp_test_pattern test_pattern;
   2626 	enum dp_test_pattern_color_space test_pattern_color_space =
   2627 			DP_TEST_PATTERN_COLOR_SPACE_UNDEFINED;
   2628 
   2629 	memset(&dpcd_test_pattern, 0, sizeof(dpcd_test_pattern));
   2630 	memset(&dpcd_test_params, 0, sizeof(dpcd_test_params));
   2631 
   2632 	/* get link test pattern and pattern parameters */
   2633 	core_link_read_dpcd(
   2634 			link,
   2635 			DP_TEST_PATTERN,
   2636 			&dpcd_test_pattern.raw,
   2637 			sizeof(dpcd_test_pattern));
   2638 	core_link_read_dpcd(
   2639 			link,
   2640 			DP_TEST_MISC0,
   2641 			&dpcd_test_params.raw,
   2642 			sizeof(dpcd_test_params));
   2643 
   2644 	switch (dpcd_test_pattern.bits.PATTERN) {
   2645 	case LINK_TEST_PATTERN_COLOR_RAMP:
   2646 		test_pattern = DP_TEST_PATTERN_COLOR_RAMP;
   2647 	break;
   2648 	case LINK_TEST_PATTERN_VERTICAL_BARS:
   2649 		test_pattern = DP_TEST_PATTERN_VERTICAL_BARS;
   2650 	break; /* black and white */
   2651 	case LINK_TEST_PATTERN_COLOR_SQUARES:
   2652 		test_pattern = (dpcd_test_params.bits.DYN_RANGE ==
   2653 				TEST_DYN_RANGE_VESA ?
   2654 				DP_TEST_PATTERN_COLOR_SQUARES :
   2655 				DP_TEST_PATTERN_COLOR_SQUARES_CEA);
   2656 	break;
   2657 	default:
   2658 		test_pattern = DP_TEST_PATTERN_VIDEO_MODE;
   2659 	break;
   2660 	}
   2661 
   2662 	test_pattern_color_space = dpcd_test_params.bits.YCBCR_COEFS ?
   2663 			DP_TEST_PATTERN_COLOR_SPACE_YCBCR709 :
   2664 			DP_TEST_PATTERN_COLOR_SPACE_YCBCR601;
   2665 
   2666 	dc_link_dp_set_test_pattern(
   2667 			link,
   2668 			test_pattern,
   2669 			test_pattern_color_space,
   2670 			NULL,
   2671 			NULL,
   2672 			0);
   2673 }
   2674 
   2675 static void dp_test_get_audio_test_data(struct dc_link *link, bool disable_video)
   2676 {
   2677 	union audio_test_mode            dpcd_test_mode = {0};
   2678 	struct audio_test_pattern_type   dpcd_pattern_type = {0};
   2679 	union audio_test_pattern_period  dpcd_pattern_period[AUDIO_CHANNELS_COUNT] = {0};
   2680 	enum dp_test_pattern test_pattern = DP_TEST_PATTERN_AUDIO_OPERATOR_DEFINED;
   2681 
   2682 	struct pipe_ctx *pipes = link->dc->current_state->res_ctx.pipe_ctx;
   2683 	struct pipe_ctx *pipe_ctx = &pipes[0];
   2684 	unsigned int channel_count;
   2685 	unsigned int channel = 0;
   2686 	unsigned int modes = 0;
   2687 	unsigned int sampling_rate_in_hz = 0;
   2688 
   2689 	// get audio test mode and test pattern parameters
   2690 	core_link_read_dpcd(
   2691 		link,
   2692 		DP_TEST_AUDIO_MODE,
   2693 		&dpcd_test_mode.raw,
   2694 		sizeof(dpcd_test_mode));
   2695 
   2696 	core_link_read_dpcd(
   2697 		link,
   2698 		DP_TEST_AUDIO_PATTERN_TYPE,
   2699 		&dpcd_pattern_type.value,
   2700 		sizeof(dpcd_pattern_type));
   2701 
   2702 	channel_count = dpcd_test_mode.bits.channel_count + 1;
   2703 
   2704 	// read pattern periods for requested channels when sawTooth pattern is requested
   2705 	if (dpcd_pattern_type.value == AUDIO_TEST_PATTERN_SAWTOOTH ||
   2706 			dpcd_pattern_type.value == AUDIO_TEST_PATTERN_OPERATOR_DEFINED) {
   2707 
   2708 		test_pattern = (dpcd_pattern_type.value == AUDIO_TEST_PATTERN_SAWTOOTH) ?
   2709 				DP_TEST_PATTERN_AUDIO_SAWTOOTH : DP_TEST_PATTERN_AUDIO_OPERATOR_DEFINED;
   2710 		// read period for each channel
   2711 		for (channel = 0; channel < channel_count; channel++) {
   2712 			core_link_read_dpcd(
   2713 							link,
   2714 							DP_TEST_AUDIO_PERIOD_CH1 + channel,
   2715 							&dpcd_pattern_period[channel].raw,
   2716 							sizeof(dpcd_pattern_period[channel]));
   2717 		}
   2718 	}
   2719 
   2720 	// translate sampling rate
   2721 	switch (dpcd_test_mode.bits.sampling_rate) {
   2722 	case AUDIO_SAMPLING_RATE_32KHZ:
   2723 		sampling_rate_in_hz = 32000;
   2724 		break;
   2725 	case AUDIO_SAMPLING_RATE_44_1KHZ:
   2726 		sampling_rate_in_hz = 44100;
   2727 		break;
   2728 	case AUDIO_SAMPLING_RATE_48KHZ:
   2729 		sampling_rate_in_hz = 48000;
   2730 		break;
   2731 	case AUDIO_SAMPLING_RATE_88_2KHZ:
   2732 		sampling_rate_in_hz = 88200;
   2733 		break;
   2734 	case AUDIO_SAMPLING_RATE_96KHZ:
   2735 		sampling_rate_in_hz = 96000;
   2736 		break;
   2737 	case AUDIO_SAMPLING_RATE_176_4KHZ:
   2738 		sampling_rate_in_hz = 176400;
   2739 		break;
   2740 	case AUDIO_SAMPLING_RATE_192KHZ:
   2741 		sampling_rate_in_hz = 192000;
   2742 		break;
   2743 	default:
   2744 		sampling_rate_in_hz = 0;
   2745 		break;
   2746 	}
   2747 
   2748 	link->audio_test_data.flags.test_requested = 1;
   2749 	link->audio_test_data.flags.disable_video = disable_video;
   2750 	link->audio_test_data.sampling_rate = sampling_rate_in_hz;
   2751 	link->audio_test_data.channel_count = channel_count;
   2752 	link->audio_test_data.pattern_type = test_pattern;
   2753 
   2754 	if (test_pattern == DP_TEST_PATTERN_AUDIO_SAWTOOTH) {
   2755 		for (modes = 0; modes < pipe_ctx->stream->audio_info.mode_count; modes++) {
   2756 			link->audio_test_data.pattern_period[modes] = dpcd_pattern_period[modes].bits.pattern_period;
   2757 		}
   2758 	}
   2759 }
   2760 
   2761 static void handle_automated_test(struct dc_link *link)
   2762 {
   2763 	union test_request test_request;
   2764 	union test_response test_response;
   2765 
   2766 	memset(&test_request, 0, sizeof(test_request));
   2767 	memset(&test_response, 0, sizeof(test_response));
   2768 
   2769 	core_link_read_dpcd(
   2770 		link,
   2771 		DP_TEST_REQUEST,
   2772 		&test_request.raw,
   2773 		sizeof(union test_request));
   2774 	if (test_request.bits.LINK_TRAINING) {
   2775 		/* ACK first to let DP RX test box monitor LT sequence */
   2776 		test_response.bits.ACK = 1;
   2777 		core_link_write_dpcd(
   2778 			link,
   2779 			DP_TEST_RESPONSE,
   2780 			&test_response.raw,
   2781 			sizeof(test_response));
   2782 		dp_test_send_link_training(link);
   2783 		/* no acknowledge request is needed again */
   2784 		test_response.bits.ACK = 0;
   2785 	}
   2786 	if (test_request.bits.LINK_TEST_PATTRN) {
   2787 		dp_test_send_link_test_pattern(link);
   2788 		test_response.bits.ACK = 1;
   2789 	}
   2790 
   2791 	if (test_request.bits.AUDIO_TEST_PATTERN) {
   2792 		dp_test_get_audio_test_data(link, test_request.bits.TEST_AUDIO_DISABLED_VIDEO);
   2793 		test_response.bits.ACK = 1;
   2794 	}
   2795 
   2796 	if (test_request.bits.PHY_TEST_PATTERN) {
   2797 		dp_test_send_phy_test_pattern(link);
   2798 		test_response.bits.ACK = 1;
   2799 	}
   2800 
   2801 	/* send request acknowledgment */
   2802 	if (test_response.bits.ACK)
   2803 		core_link_write_dpcd(
   2804 			link,
   2805 			DP_TEST_RESPONSE,
   2806 			&test_response.raw,
   2807 			sizeof(test_response));
   2808 }
   2809 
   2810 bool dc_link_handle_hpd_rx_irq(struct dc_link *link, union hpd_irq_data *out_hpd_irq_dpcd_data, bool *out_link_loss)
   2811 {
   2812 	union hpd_irq_data hpd_irq_dpcd_data = { { { {0} } } };
   2813 	union device_service_irq device_service_clear = { { 0 } };
   2814 	enum dc_status result;
   2815 	bool status = false;
   2816 	struct pipe_ctx *pipe_ctx;
   2817 	struct dc_link_settings previous_link_settings;
   2818 	int i;
   2819 
   2820 	if (out_link_loss)
   2821 		*out_link_loss = false;
   2822 	/* For use cases related to down stream connection status change,
   2823 	 * PSR and device auto test, refer to function handle_sst_hpd_irq
   2824 	 * in DAL2.1*/
   2825 
   2826 	DC_LOG_HW_HPD_IRQ("%s: Got short pulse HPD on link %d\n",
   2827 		__func__, link->link_index);
   2828 
   2829 
   2830 	 /* All the "handle_hpd_irq_xxx()" methods
   2831 		 * should be called only after
   2832 		 * dal_dpsst_ls_read_hpd_irq_data
   2833 		 * Order of calls is important too
   2834 		 */
   2835 	result = read_hpd_rx_irq_data(link, &hpd_irq_dpcd_data);
   2836 	if (out_hpd_irq_dpcd_data)
   2837 		*out_hpd_irq_dpcd_data = hpd_irq_dpcd_data;
   2838 
   2839 	if (result != DC_OK) {
   2840 		DC_LOG_HW_HPD_IRQ("%s: DPCD read failed to obtain irq data\n",
   2841 			__func__);
   2842 		return false;
   2843 	}
   2844 
   2845 	if (hpd_irq_dpcd_data.bytes.device_service_irq.bits.AUTOMATED_TEST) {
   2846 		device_service_clear.bits.AUTOMATED_TEST = 1;
   2847 		core_link_write_dpcd(
   2848 			link,
   2849 			DP_DEVICE_SERVICE_IRQ_VECTOR,
   2850 			&device_service_clear.raw,
   2851 			sizeof(device_service_clear.raw));
   2852 		device_service_clear.raw = 0;
   2853 		handle_automated_test(link);
   2854 		return false;
   2855 	}
   2856 
   2857 	if (!allow_hpd_rx_irq(link)) {
   2858 		DC_LOG_HW_HPD_IRQ("%s: skipping HPD handling on %d\n",
   2859 			__func__, link->link_index);
   2860 		return false;
   2861 	}
   2862 
   2863 	if (handle_hpd_irq_psr_sink(link))
   2864 		/* PSR-related error was detected and handled */
   2865 		return true;
   2866 
   2867 	/* If PSR-related error handled, Main link may be off,
   2868 	 * so do not handle as a normal sink status change interrupt.
   2869 	 */
   2870 
   2871 	if (hpd_irq_dpcd_data.bytes.device_service_irq.bits.UP_REQ_MSG_RDY)
   2872 		return true;
   2873 
   2874 	/* check if we have MST msg and return since we poll for it */
   2875 	if (hpd_irq_dpcd_data.bytes.device_service_irq.bits.DOWN_REP_MSG_RDY)
   2876 		return false;
   2877 
   2878 	/* For now we only handle 'Downstream port status' case.
   2879 	 * If we got sink count changed it means
   2880 	 * Downstream port status changed,
   2881 	 * then DM should call DC to do the detection.
   2882 	 * NOTE: Do not handle link loss on eDP since it is internal link*/
   2883 	if ((link->connector_signal != SIGNAL_TYPE_EDP) &&
   2884 		hpd_rx_irq_check_link_loss_status(
   2885 			link,
   2886 			&hpd_irq_dpcd_data)) {
   2887 		/* Connectivity log: link loss */
   2888 		CONN_DATA_LINK_LOSS(link,
   2889 					hpd_irq_dpcd_data.raw,
   2890 					sizeof(hpd_irq_dpcd_data),
   2891 					"Status: ");
   2892 
   2893 		for (i = 0; i < MAX_PIPES; i++) {
   2894 			pipe_ctx = &link->dc->current_state->res_ctx.pipe_ctx[i];
   2895 			if (pipe_ctx && pipe_ctx->stream && pipe_ctx->stream->link == link)
   2896 				break;
   2897 		}
   2898 
   2899 		if (pipe_ctx == NULL || pipe_ctx->stream == NULL)
   2900 			return false;
   2901 
   2902 		previous_link_settings = link->cur_link_settings;
   2903 
   2904 		perform_link_training_with_retries(&previous_link_settings,
   2905 			true, LINK_TRAINING_ATTEMPTS,
   2906 			pipe_ctx,
   2907 			pipe_ctx->stream->signal);
   2908 
   2909 		if (pipe_ctx->stream->signal == SIGNAL_TYPE_DISPLAY_PORT_MST)
   2910 			dc_link_reallocate_mst_payload(link);
   2911 
   2912 		status = false;
   2913 		if (out_link_loss)
   2914 			*out_link_loss = true;
   2915 	}
   2916 
   2917 	if (link->type == dc_connection_active_dongle &&
   2918 		hpd_irq_dpcd_data.bytes.sink_cnt.bits.SINK_COUNT
   2919 			!= link->dpcd_sink_count)
   2920 		status = true;
   2921 
   2922 	/* reasons for HPD RX:
   2923 	 * 1. Link Loss - ie Re-train the Link
   2924 	 * 2. MST sideband message
   2925 	 * 3. Automated Test - ie. Internal Commit
   2926 	 * 4. CP (copy protection) - (not interesting for DM???)
   2927 	 * 5. DRR
   2928 	 * 6. Downstream Port status changed
   2929 	 * -ie. Detect - this the only one
   2930 	 * which is interesting for DM because
   2931 	 * it must call dc_link_detect.
   2932 	 */
   2933 	return status;
   2934 }
   2935 
   2936 /*query dpcd for version and mst cap addresses*/
   2937 bool is_mst_supported(struct dc_link *link)
   2938 {
   2939 	bool mst          = false;
   2940 	enum dc_status st = DC_OK;
   2941 	union dpcd_rev rev;
   2942 	union mstm_cap cap;
   2943 
   2944 	if (link->preferred_training_settings.mst_enable &&
   2945 		*link->preferred_training_settings.mst_enable == false) {
   2946 		return false;
   2947 	}
   2948 
   2949 	rev.raw  = 0;
   2950 	cap.raw  = 0;
   2951 
   2952 	st = core_link_read_dpcd(link, DP_DPCD_REV, &rev.raw,
   2953 			sizeof(rev));
   2954 
   2955 	if (st == DC_OK && rev.raw >= DPCD_REV_12) {
   2956 
   2957 		st = core_link_read_dpcd(link, DP_MSTM_CAP,
   2958 				&cap.raw, sizeof(cap));
   2959 		if (st == DC_OK && cap.bits.MST_CAP == 1)
   2960 			mst = true;
   2961 	}
   2962 	return mst;
   2963 
   2964 }
   2965 
   2966 bool is_dp_active_dongle(const struct dc_link *link)
   2967 {
   2968 	return link->dpcd_caps.is_branch_dev;
   2969 }
   2970 
   2971 static int translate_dpcd_max_bpc(enum dpcd_downstream_port_max_bpc bpc)
   2972 {
   2973 	switch (bpc) {
   2974 	case DOWN_STREAM_MAX_8BPC:
   2975 		return 8;
   2976 	case DOWN_STREAM_MAX_10BPC:
   2977 		return 10;
   2978 	case DOWN_STREAM_MAX_12BPC:
   2979 		return 12;
   2980 	case DOWN_STREAM_MAX_16BPC:
   2981 		return 16;
   2982 	default:
   2983 		break;
   2984 	}
   2985 
   2986 	return -1;
   2987 }
   2988 
   2989 static void read_dp_device_vendor_id(struct dc_link *link)
   2990 {
   2991 	struct dp_device_vendor_id dp_id;
   2992 
   2993 	/* read IEEE branch device id */
   2994 	core_link_read_dpcd(
   2995 		link,
   2996 		DP_BRANCH_OUI,
   2997 		(uint8_t *)&dp_id,
   2998 		sizeof(dp_id));
   2999 
   3000 	link->dpcd_caps.branch_dev_id =
   3001 		(dp_id.ieee_oui[0] << 16) +
   3002 		(dp_id.ieee_oui[1] << 8) +
   3003 		dp_id.ieee_oui[2];
   3004 
   3005 	memmove(
   3006 		link->dpcd_caps.branch_dev_name,
   3007 		dp_id.ieee_device_id,
   3008 		sizeof(dp_id.ieee_device_id));
   3009 }
   3010 
   3011 
   3012 
   3013 static void get_active_converter_info(
   3014 	uint8_t data, struct dc_link *link)
   3015 {
   3016 	union dp_downstream_port_present ds_port = { .byte = data };
   3017 	memset(&link->dpcd_caps.dongle_caps, 0, sizeof(link->dpcd_caps.dongle_caps));
   3018 
   3019 	/* decode converter info*/
   3020 	if (!ds_port.fields.PORT_PRESENT) {
   3021 		link->dpcd_caps.dongle_type = DISPLAY_DONGLE_NONE;
   3022 		ddc_service_set_dongle_type(link->ddc,
   3023 				link->dpcd_caps.dongle_type);
   3024 		link->dpcd_caps.is_branch_dev = false;
   3025 		return;
   3026 	}
   3027 
   3028 	/* DPCD 0x5 bit 0 = 1, it indicate it's branch device */
   3029 	if (ds_port.fields.PORT_TYPE == DOWNSTREAM_DP) {
   3030 		link->dpcd_caps.is_branch_dev = false;
   3031 	}
   3032 
   3033 	else {
   3034 		link->dpcd_caps.is_branch_dev = ds_port.fields.PORT_PRESENT;
   3035 	}
   3036 
   3037 	switch (ds_port.fields.PORT_TYPE) {
   3038 	case DOWNSTREAM_VGA:
   3039 		link->dpcd_caps.dongle_type = DISPLAY_DONGLE_DP_VGA_CONVERTER;
   3040 		break;
   3041 	case DOWNSTREAM_DVI_HDMI_DP_PLUS_PLUS:
   3042 		/* At this point we don't know is it DVI or HDMI or DP++,
   3043 		 * assume DVI.*/
   3044 		link->dpcd_caps.dongle_type = DISPLAY_DONGLE_DP_DVI_CONVERTER;
   3045 		break;
   3046 	default:
   3047 		link->dpcd_caps.dongle_type = DISPLAY_DONGLE_NONE;
   3048 		break;
   3049 	}
   3050 
   3051 	if (link->dpcd_caps.dpcd_rev.raw >= DPCD_REV_11) {
   3052 		uint8_t det_caps[16]; /* CTS 4.2.2.7 expects source to read Detailed Capabilities Info : 00080h-0008F.*/
   3053 		union dwnstream_port_caps_byte0 *port_caps =
   3054 			(union dwnstream_port_caps_byte0 *)det_caps;
   3055 		core_link_read_dpcd(link, DP_DOWNSTREAM_PORT_0,
   3056 				det_caps, sizeof(det_caps));
   3057 
   3058 		switch (port_caps->bits.DWN_STRM_PORTX_TYPE) {
   3059 		/*Handle DP case as DONGLE_NONE*/
   3060 		case DOWN_STREAM_DETAILED_DP:
   3061 			link->dpcd_caps.dongle_type = DISPLAY_DONGLE_NONE;
   3062 			break;
   3063 		case DOWN_STREAM_DETAILED_VGA:
   3064 			link->dpcd_caps.dongle_type =
   3065 				DISPLAY_DONGLE_DP_VGA_CONVERTER;
   3066 			break;
   3067 		case DOWN_STREAM_DETAILED_DVI:
   3068 			link->dpcd_caps.dongle_type =
   3069 				DISPLAY_DONGLE_DP_DVI_CONVERTER;
   3070 			break;
   3071 		case DOWN_STREAM_DETAILED_HDMI:
   3072 		case DOWN_STREAM_DETAILED_DP_PLUS_PLUS:
   3073 			/*Handle DP++ active converter case, process DP++ case as HDMI case according DP1.4 spec*/
   3074 			link->dpcd_caps.dongle_type =
   3075 				DISPLAY_DONGLE_DP_HDMI_CONVERTER;
   3076 
   3077 			link->dpcd_caps.dongle_caps.dongle_type = link->dpcd_caps.dongle_type;
   3078 			if (ds_port.fields.DETAILED_CAPS) {
   3079 
   3080 				union dwnstream_port_caps_byte3_hdmi
   3081 					hdmi_caps = {.raw = det_caps[3] };
   3082 				union dwnstream_port_caps_byte2
   3083 					hdmi_color_caps = {.raw = det_caps[2] };
   3084 				link->dpcd_caps.dongle_caps.dp_hdmi_max_pixel_clk_in_khz =
   3085 					det_caps[1] * 2500;
   3086 
   3087 				link->dpcd_caps.dongle_caps.is_dp_hdmi_s3d_converter =
   3088 					hdmi_caps.bits.FRAME_SEQ_TO_FRAME_PACK;
   3089 				/*YCBCR capability only for HDMI case*/
   3090 				if (port_caps->bits.DWN_STRM_PORTX_TYPE
   3091 						== DOWN_STREAM_DETAILED_HDMI) {
   3092 					link->dpcd_caps.dongle_caps.is_dp_hdmi_ycbcr422_pass_through =
   3093 							hdmi_caps.bits.YCrCr422_PASS_THROUGH;
   3094 					link->dpcd_caps.dongle_caps.is_dp_hdmi_ycbcr420_pass_through =
   3095 							hdmi_caps.bits.YCrCr420_PASS_THROUGH;
   3096 					link->dpcd_caps.dongle_caps.is_dp_hdmi_ycbcr422_converter =
   3097 							hdmi_caps.bits.YCrCr422_CONVERSION;
   3098 					link->dpcd_caps.dongle_caps.is_dp_hdmi_ycbcr420_converter =
   3099 							hdmi_caps.bits.YCrCr420_CONVERSION;
   3100 				}
   3101 
   3102 				link->dpcd_caps.dongle_caps.dp_hdmi_max_bpc =
   3103 					translate_dpcd_max_bpc(
   3104 						hdmi_color_caps.bits.MAX_BITS_PER_COLOR_COMPONENT);
   3105 
   3106 				if (link->dpcd_caps.dongle_caps.dp_hdmi_max_pixel_clk_in_khz != 0)
   3107 					link->dpcd_caps.dongle_caps.extendedCapValid = true;
   3108 			}
   3109 
   3110 			break;
   3111 		}
   3112 	}
   3113 
   3114 	ddc_service_set_dongle_type(link->ddc, link->dpcd_caps.dongle_type);
   3115 
   3116 	{
   3117 		struct dp_sink_hw_fw_revision dp_hw_fw_revision;
   3118 
   3119 		core_link_read_dpcd(
   3120 			link,
   3121 			DP_BRANCH_REVISION_START,
   3122 			(uint8_t *)&dp_hw_fw_revision,
   3123 			sizeof(dp_hw_fw_revision));
   3124 
   3125 		link->dpcd_caps.branch_hw_revision =
   3126 			dp_hw_fw_revision.ieee_hw_rev;
   3127 
   3128 		memmove(
   3129 			link->dpcd_caps.branch_fw_revision,
   3130 			dp_hw_fw_revision.ieee_fw_rev,
   3131 			sizeof(dp_hw_fw_revision.ieee_fw_rev));
   3132 	}
   3133 }
   3134 
   3135 static void dp_wa_power_up_0010FA(struct dc_link *link, uint8_t *dpcd_data,
   3136 		int length)
   3137 {
   3138 	int retry = 0;
   3139 
   3140 	if (!link->dpcd_caps.dpcd_rev.raw) {
   3141 		do {
   3142 			dp_receiver_power_ctrl(link, true);
   3143 			core_link_read_dpcd(link, DP_DPCD_REV,
   3144 							dpcd_data, length);
   3145 			link->dpcd_caps.dpcd_rev.raw = dpcd_data[
   3146 				DP_DPCD_REV -
   3147 				DP_DPCD_REV];
   3148 		} while (retry++ < 4 && !link->dpcd_caps.dpcd_rev.raw);
   3149 	}
   3150 
   3151 	if (link->dpcd_caps.dongle_type == DISPLAY_DONGLE_DP_VGA_CONVERTER) {
   3152 		switch (link->dpcd_caps.branch_dev_id) {
   3153 		/* 0010FA active dongles (DP-VGA, DP-DLDVI converters) power down
   3154 		 * all internal circuits including AUX communication preventing
   3155 		 * reading DPCD table and EDID (spec violation).
   3156 		 * Encoder will skip DP RX power down on disable_output to
   3157 		 * keep receiver powered all the time.*/
   3158 		case DP_BRANCH_DEVICE_ID_0010FA:
   3159 		case DP_BRANCH_DEVICE_ID_0080E1:
   3160 		case DP_BRANCH_DEVICE_ID_00E04C:
   3161 			link->wa_flags.dp_keep_receiver_powered = true;
   3162 			break;
   3163 
   3164 		/* TODO: May need work around for other dongles. */
   3165 		default:
   3166 			link->wa_flags.dp_keep_receiver_powered = false;
   3167 			break;
   3168 		}
   3169 	} else
   3170 		link->wa_flags.dp_keep_receiver_powered = false;
   3171 }
   3172 
   3173 static bool retrieve_link_cap(struct dc_link *link)
   3174 {
   3175 	/* DP_ADAPTER_CAP - DP_DPCD_REV + 1 == 16 and also DP_DSC_BITS_PER_PIXEL_INC - DP_DSC_SUPPORT + 1 == 16,
   3176 	 * which means size 16 will be good for both of those DPCD register block reads
   3177 	 */
   3178 	uint8_t dpcd_data[16];
   3179 	uint8_t lttpr_dpcd_data[6];
   3180 
   3181 	/*Only need to read 1 byte starting from DP_DPRX_FEATURE_ENUMERATION_LIST.
   3182 	 */
   3183 	uint8_t dpcd_dprx_data = '\0';
   3184 	uint8_t dpcd_power_state = '\0';
   3185 
   3186 	struct dp_device_vendor_id sink_id;
   3187 	union down_stream_port_count down_strm_port_count;
   3188 	union edp_configuration_cap edp_config_cap;
   3189 	union dp_downstream_port_present ds_port = { 0 };
   3190 	enum dc_status status = DC_ERROR_UNEXPECTED;
   3191 	uint32_t read_dpcd_retry_cnt = 3;
   3192 	int i;
   3193 	struct dp_sink_hw_fw_revision dp_hw_fw_revision;
   3194 
   3195 	/* Set default timeout to 3.2ms and read LTTPR capabilities */
   3196 	bool ext_timeout_support = link->dc->caps.extended_aux_timeout_support &&
   3197 			!link->dc->config.disable_extended_timeout_support;
   3198 
   3199 	link->is_lttpr_mode_transparent = true;
   3200 
   3201 	if (ext_timeout_support) {
   3202 		dc_link_aux_configure_timeout(link->ddc,
   3203 					LINK_AUX_DEFAULT_EXTENDED_TIMEOUT_PERIOD);
   3204 	}
   3205 
   3206 	memset(dpcd_data, '\0', sizeof(dpcd_data));
   3207 	memset(lttpr_dpcd_data, '\0', sizeof(lttpr_dpcd_data));
   3208 	memset(&down_strm_port_count,
   3209 		'\0', sizeof(union down_stream_port_count));
   3210 	memset(&edp_config_cap, '\0',
   3211 		sizeof(union edp_configuration_cap));
   3212 
   3213 	status = core_link_read_dpcd(link, DP_SET_POWER,
   3214 				&dpcd_power_state, sizeof(dpcd_power_state));
   3215 
   3216 	/* Delay 1 ms if AUX CH is in power down state. Based on spec
   3217 	 * section 2.3.1.2, if AUX CH may be powered down due to
   3218 	 * write to DPCD 600h = 2. Sink AUX CH is monitoring differential
   3219 	 * signal and may need up to 1 ms before being able to reply.
   3220 	 */
   3221 	if (status != DC_OK || dpcd_power_state == DP_SET_POWER_D3)
   3222 		udelay(1000);
   3223 
   3224 	for (i = 0; i < read_dpcd_retry_cnt; i++) {
   3225 		status = core_link_read_dpcd(
   3226 				link,
   3227 				DP_DPCD_REV,
   3228 				dpcd_data,
   3229 				sizeof(dpcd_data));
   3230 		if (status == DC_OK)
   3231 			break;
   3232 	}
   3233 
   3234 	if (status != DC_OK) {
   3235 		dm_error("%s: Read dpcd data failed.\n", __func__);
   3236 		return false;
   3237 	}
   3238 
   3239 	if (ext_timeout_support) {
   3240 
   3241 		status = core_link_read_dpcd(
   3242 				link,
   3243 				DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV,
   3244 				lttpr_dpcd_data,
   3245 				sizeof(lttpr_dpcd_data));
   3246 
   3247 		link->dpcd_caps.lttpr_caps.revision.raw =
   3248 				lttpr_dpcd_data[DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV -
   3249 								DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV];
   3250 
   3251 		link->dpcd_caps.lttpr_caps.max_link_rate =
   3252 				lttpr_dpcd_data[DP_MAX_LINK_RATE_PHY_REPEATER -
   3253 								DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV];
   3254 
   3255 		link->dpcd_caps.lttpr_caps.phy_repeater_cnt =
   3256 				lttpr_dpcd_data[DP_PHY_REPEATER_CNT -
   3257 								DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV];
   3258 
   3259 		link->dpcd_caps.lttpr_caps.max_lane_count =
   3260 				lttpr_dpcd_data[DP_MAX_LANE_COUNT_PHY_REPEATER -
   3261 								DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV];
   3262 
   3263 		link->dpcd_caps.lttpr_caps.mode =
   3264 				lttpr_dpcd_data[DP_PHY_REPEATER_MODE -
   3265 								DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV];
   3266 
   3267 		link->dpcd_caps.lttpr_caps.max_ext_timeout =
   3268 				lttpr_dpcd_data[DP_PHY_REPEATER_EXTENDED_WAIT_TIMEOUT -
   3269 								DP_LT_TUNABLE_PHY_REPEATER_FIELD_DATA_STRUCTURE_REV];
   3270 
   3271 		if (link->dpcd_caps.lttpr_caps.phy_repeater_cnt > 0 &&
   3272 				link->dpcd_caps.lttpr_caps.max_lane_count > 0 &&
   3273 				link->dpcd_caps.lttpr_caps.max_lane_count <= 4 &&
   3274 				link->dpcd_caps.lttpr_caps.revision.raw >= 0x14) {
   3275 			link->is_lttpr_mode_transparent = false;
   3276 		} else {
   3277 			/*No lttpr reset timeout to its default value*/
   3278 			link->is_lttpr_mode_transparent = true;
   3279 			dc_link_aux_configure_timeout(link->ddc, LINK_AUX_DEFAULT_TIMEOUT_PERIOD);
   3280 		}
   3281 
   3282 		CONN_DATA_DETECT(link, lttpr_dpcd_data, sizeof(lttpr_dpcd_data), "LTTPR Caps: ");
   3283 	}
   3284 
   3285 	{
   3286 		union training_aux_rd_interval aux_rd_interval;
   3287 
   3288 		aux_rd_interval.raw =
   3289 			dpcd_data[DP_TRAINING_AUX_RD_INTERVAL];
   3290 
   3291 		link->dpcd_caps.ext_receiver_cap_field_present =
   3292 				aux_rd_interval.bits.EXT_RECEIVER_CAP_FIELD_PRESENT == 1;
   3293 
   3294 		if (aux_rd_interval.bits.EXT_RECEIVER_CAP_FIELD_PRESENT == 1) {
   3295 			uint8_t ext_cap_data[16];
   3296 
   3297 			memset(ext_cap_data, '\0', sizeof(ext_cap_data));
   3298 			for (i = 0; i < read_dpcd_retry_cnt; i++) {
   3299 				status = core_link_read_dpcd(
   3300 				link,
   3301 				DP_DP13_DPCD_REV,
   3302 				ext_cap_data,
   3303 				sizeof(ext_cap_data));
   3304 				if (status == DC_OK) {
   3305 					memcpy(dpcd_data, ext_cap_data, sizeof(dpcd_data));
   3306 					break;
   3307 				}
   3308 			}
   3309 			if (status != DC_OK)
   3310 				dm_error("%s: Read extend caps data failed, use cap from dpcd 0.\n", __func__);
   3311 		}
   3312 	}
   3313 
   3314 	link->dpcd_caps.dpcd_rev.raw =
   3315 			dpcd_data[DP_DPCD_REV - DP_DPCD_REV];
   3316 
   3317 	if (link->dpcd_caps.dpcd_rev.raw >= 0x14) {
   3318 		for (i = 0; i < read_dpcd_retry_cnt; i++) {
   3319 			status = core_link_read_dpcd(
   3320 					link,
   3321 					DP_DPRX_FEATURE_ENUMERATION_LIST,
   3322 					&dpcd_dprx_data,
   3323 					sizeof(dpcd_dprx_data));
   3324 			if (status == DC_OK)
   3325 				break;
   3326 		}
   3327 
   3328 		link->dpcd_caps.dprx_feature.raw = dpcd_dprx_data;
   3329 
   3330 		if (status != DC_OK)
   3331 			dm_error("%s: Read DPRX caps data failed.\n", __func__);
   3332 	}
   3333 
   3334 	else {
   3335 		link->dpcd_caps.dprx_feature.raw = 0;
   3336 	}
   3337 
   3338 
   3339 	/* Error condition checking...
   3340 	 * It is impossible for Sink to report Max Lane Count = 0.
   3341 	 * It is possible for Sink to report Max Link Rate = 0, if it is
   3342 	 * an eDP device that is reporting specialized link rates in the
   3343 	 * SUPPORTED_LINK_RATE table.
   3344 	 */
   3345 	if (dpcd_data[DP_MAX_LANE_COUNT - DP_DPCD_REV] == 0)
   3346 		return false;
   3347 
   3348 	ds_port.byte = dpcd_data[DP_DOWNSTREAMPORT_PRESENT -
   3349 				 DP_DPCD_REV];
   3350 
   3351 	read_dp_device_vendor_id(link);
   3352 
   3353 	get_active_converter_info(ds_port.byte, link);
   3354 
   3355 	dp_wa_power_up_0010FA(link, dpcd_data, sizeof(dpcd_data));
   3356 
   3357 	down_strm_port_count.raw = dpcd_data[DP_DOWN_STREAM_PORT_COUNT -
   3358 				 DP_DPCD_REV];
   3359 
   3360 	link->dpcd_caps.allow_invalid_MSA_timing_param =
   3361 		down_strm_port_count.bits.IGNORE_MSA_TIMING_PARAM;
   3362 
   3363 	link->dpcd_caps.max_ln_count.raw = dpcd_data[
   3364 		DP_MAX_LANE_COUNT - DP_DPCD_REV];
   3365 
   3366 	link->dpcd_caps.max_down_spread.raw = dpcd_data[
   3367 		DP_MAX_DOWNSPREAD - DP_DPCD_REV];
   3368 
   3369 	link->reported_link_cap.lane_count =
   3370 		link->dpcd_caps.max_ln_count.bits.MAX_LANE_COUNT;
   3371 	link->reported_link_cap.link_rate = dpcd_data[
   3372 		DP_MAX_LINK_RATE - DP_DPCD_REV];
   3373 	link->reported_link_cap.link_spread =
   3374 		link->dpcd_caps.max_down_spread.bits.MAX_DOWN_SPREAD ?
   3375 		LINK_SPREAD_05_DOWNSPREAD_30KHZ : LINK_SPREAD_DISABLED;
   3376 
   3377 	edp_config_cap.raw = dpcd_data[
   3378 		DP_EDP_CONFIGURATION_CAP - DP_DPCD_REV];
   3379 	link->dpcd_caps.panel_mode_edp =
   3380 		edp_config_cap.bits.ALT_SCRAMBLER_RESET;
   3381 	link->dpcd_caps.dpcd_display_control_capable =
   3382 		edp_config_cap.bits.DPCD_DISPLAY_CONTROL_CAPABLE;
   3383 
   3384 	link->test_pattern_enabled = false;
   3385 	link->compliance_test_state.raw = 0;
   3386 
   3387 	/* read sink count */
   3388 	core_link_read_dpcd(link,
   3389 			DP_SINK_COUNT,
   3390 			&link->dpcd_caps.sink_count.raw,
   3391 			sizeof(link->dpcd_caps.sink_count.raw));
   3392 
   3393 	/* read sink ieee oui */
   3394 	core_link_read_dpcd(link,
   3395 			DP_SINK_OUI,
   3396 			(uint8_t *)(&sink_id),
   3397 			sizeof(sink_id));
   3398 
   3399 	link->dpcd_caps.sink_dev_id =
   3400 			(sink_id.ieee_oui[0] << 16) +
   3401 			(sink_id.ieee_oui[1] << 8) +
   3402 			(sink_id.ieee_oui[2]);
   3403 
   3404 	memmove(
   3405 		link->dpcd_caps.sink_dev_id_str,
   3406 		sink_id.ieee_device_id,
   3407 		sizeof(sink_id.ieee_device_id));
   3408 
   3409 	core_link_read_dpcd(
   3410 		link,
   3411 		DP_SINK_HW_REVISION_START,
   3412 		(uint8_t *)&dp_hw_fw_revision,
   3413 		sizeof(dp_hw_fw_revision));
   3414 
   3415 	link->dpcd_caps.sink_hw_revision =
   3416 		dp_hw_fw_revision.ieee_hw_rev;
   3417 
   3418 	memmove(
   3419 		link->dpcd_caps.sink_fw_revision,
   3420 		dp_hw_fw_revision.ieee_fw_rev,
   3421 		sizeof(dp_hw_fw_revision.ieee_fw_rev));
   3422 
   3423 	memset(&link->dpcd_caps.dsc_caps, '\0',
   3424 			sizeof(link->dpcd_caps.dsc_caps));
   3425 	memset(&link->dpcd_caps.fec_cap, '\0', sizeof(link->dpcd_caps.fec_cap));
   3426 	/* Read DSC and FEC sink capabilities if DP revision is 1.4 and up */
   3427 	if (link->dpcd_caps.dpcd_rev.raw >= DPCD_REV_14) {
   3428 		status = core_link_read_dpcd(
   3429 				link,
   3430 				DP_FEC_CAPABILITY,
   3431 				&link->dpcd_caps.fec_cap.raw,
   3432 				sizeof(link->dpcd_caps.fec_cap.raw));
   3433 		status = core_link_read_dpcd(
   3434 				link,
   3435 				DP_DSC_SUPPORT,
   3436 				link->dpcd_caps.dsc_caps.dsc_basic_caps.raw,
   3437 				sizeof(link->dpcd_caps.dsc_caps.dsc_basic_caps.raw));
   3438 		status = core_link_read_dpcd(
   3439 				link,
   3440 				DP_DSC_BRANCH_OVERALL_THROUGHPUT_0,
   3441 				link->dpcd_caps.dsc_caps.dsc_ext_caps.raw,
   3442 				sizeof(link->dpcd_caps.dsc_caps.dsc_ext_caps.raw));
   3443 	}
   3444 
   3445 	/* Connectivity log: detection */
   3446 	CONN_DATA_DETECT(link, dpcd_data, sizeof(dpcd_data), "Rx Caps: ");
   3447 
   3448 	return true;
   3449 }
   3450 
   3451 bool dp_overwrite_extended_receiver_cap(struct dc_link *link)
   3452 {
   3453 	uint8_t dpcd_data[16];
   3454 	uint32_t read_dpcd_retry_cnt = 3;
   3455 	enum dc_status status = DC_ERROR_UNEXPECTED;
   3456 	union dp_downstream_port_present ds_port = { 0 };
   3457 	union down_stream_port_count down_strm_port_count;
   3458 	union edp_configuration_cap edp_config_cap;
   3459 
   3460 	int i;
   3461 
   3462 	for (i = 0; i < read_dpcd_retry_cnt; i++) {
   3463 		status = core_link_read_dpcd(
   3464 				link,
   3465 				DP_DPCD_REV,
   3466 				dpcd_data,
   3467 				sizeof(dpcd_data));
   3468 		if (status == DC_OK)
   3469 			break;
   3470 	}
   3471 
   3472 	link->dpcd_caps.dpcd_rev.raw =
   3473 		dpcd_data[DP_DPCD_REV - DP_DPCD_REV];
   3474 
   3475 	if (dpcd_data[DP_MAX_LANE_COUNT - DP_DPCD_REV] == 0)
   3476 		return false;
   3477 
   3478 	ds_port.byte = dpcd_data[DP_DOWNSTREAMPORT_PRESENT -
   3479 			DP_DPCD_REV];
   3480 
   3481 	get_active_converter_info(ds_port.byte, link);
   3482 
   3483 	down_strm_port_count.raw = dpcd_data[DP_DOWN_STREAM_PORT_COUNT -
   3484 			DP_DPCD_REV];
   3485 
   3486 	link->dpcd_caps.allow_invalid_MSA_timing_param =
   3487 		down_strm_port_count.bits.IGNORE_MSA_TIMING_PARAM;
   3488 
   3489 	link->dpcd_caps.max_ln_count.raw = dpcd_data[
   3490 		DP_MAX_LANE_COUNT - DP_DPCD_REV];
   3491 
   3492 	link->dpcd_caps.max_down_spread.raw = dpcd_data[
   3493 		DP_MAX_DOWNSPREAD - DP_DPCD_REV];
   3494 
   3495 	link->reported_link_cap.lane_count =
   3496 		link->dpcd_caps.max_ln_count.bits.MAX_LANE_COUNT;
   3497 	link->reported_link_cap.link_rate = dpcd_data[
   3498 		DP_MAX_LINK_RATE - DP_DPCD_REV];
   3499 	link->reported_link_cap.link_spread =
   3500 		link->dpcd_caps.max_down_spread.bits.MAX_DOWN_SPREAD ?
   3501 		LINK_SPREAD_05_DOWNSPREAD_30KHZ : LINK_SPREAD_DISABLED;
   3502 
   3503 	edp_config_cap.raw = dpcd_data[
   3504 		DP_EDP_CONFIGURATION_CAP - DP_DPCD_REV];
   3505 	link->dpcd_caps.panel_mode_edp =
   3506 		edp_config_cap.bits.ALT_SCRAMBLER_RESET;
   3507 	link->dpcd_caps.dpcd_display_control_capable =
   3508 		edp_config_cap.bits.DPCD_DISPLAY_CONTROL_CAPABLE;
   3509 
   3510 	return true;
   3511 }
   3512 
   3513 bool detect_dp_sink_caps(struct dc_link *link)
   3514 {
   3515 	return retrieve_link_cap(link);
   3516 
   3517 	/* dc init_hw has power encoder using default
   3518 	 * signal for connector. For native DP, no
   3519 	 * need to power up encoder again. If not native
   3520 	 * DP, hw_init may need check signal or power up
   3521 	 * encoder here.
   3522 	 */
   3523 	/* TODO save sink caps in link->sink */
   3524 }
   3525 
   3526 enum dc_link_rate linkRateInKHzToLinkRateMultiplier(uint32_t link_rate_in_khz)
   3527 {
   3528 	enum dc_link_rate link_rate;
   3529 	// LinkRate is normally stored as a multiplier of 0.27 Gbps per lane. Do the translation.
   3530 	switch (link_rate_in_khz) {
   3531 	case 1620000:
   3532 		link_rate = LINK_RATE_LOW;		// Rate_1 (RBR)		- 1.62 Gbps/Lane
   3533 		break;
   3534 	case 2160000:
   3535 		link_rate = LINK_RATE_RATE_2;	// Rate_2			- 2.16 Gbps/Lane
   3536 		break;
   3537 	case 2430000:
   3538 		link_rate = LINK_RATE_RATE_3;	// Rate_3			- 2.43 Gbps/Lane
   3539 		break;
   3540 	case 2700000:
   3541 		link_rate = LINK_RATE_HIGH;		// Rate_4 (HBR)		- 2.70 Gbps/Lane
   3542 		break;
   3543 	case 3240000:
   3544 		link_rate = LINK_RATE_RBR2;		// Rate_5 (RBR2)	- 3.24 Gbps/Lane
   3545 		break;
   3546 	case 4320000:
   3547 		link_rate = LINK_RATE_RATE_6;	// Rate_6			- 4.32 Gbps/Lane
   3548 		break;
   3549 	case 5400000:
   3550 		link_rate = LINK_RATE_HIGH2;	// Rate_7 (HBR2)	- 5.40 Gbps/Lane
   3551 		break;
   3552 	case 8100000:
   3553 		link_rate = LINK_RATE_HIGH3;	// Rate_8 (HBR3)	- 8.10 Gbps/Lane
   3554 		break;
   3555 	default:
   3556 		link_rate = LINK_RATE_UNKNOWN;
   3557 		break;
   3558 	}
   3559 	return link_rate;
   3560 }
   3561 
   3562 void detect_edp_sink_caps(struct dc_link *link)
   3563 {
   3564 	uint8_t supported_link_rates[16];
   3565 	uint32_t entry;
   3566 	uint32_t link_rate_in_khz;
   3567 	enum dc_link_rate link_rate = LINK_RATE_UNKNOWN;
   3568 
   3569 	retrieve_link_cap(link);
   3570 	link->dpcd_caps.edp_supported_link_rates_count = 0;
   3571 	memset(supported_link_rates, 0, sizeof(supported_link_rates));
   3572 
   3573 	if (link->dpcd_caps.dpcd_rev.raw >= DPCD_REV_14 &&
   3574 			(link->dc->config.optimize_edp_link_rate ||
   3575 			link->reported_link_cap.link_rate == LINK_RATE_UNKNOWN)) {
   3576 		// Read DPCD 00010h - 0001Fh 16 bytes at one shot
   3577 		core_link_read_dpcd(link, DP_SUPPORTED_LINK_RATES,
   3578 							supported_link_rates, sizeof(supported_link_rates));
   3579 
   3580 		for (entry = 0; entry < 16; entry += 2) {
   3581 			// DPCD register reports per-lane link rate = 16-bit link rate capability
   3582 			// value X 200 kHz. Need multiplier to find link rate in kHz.
   3583 			link_rate_in_khz = (supported_link_rates[entry+1] * 0x100 +
   3584 										supported_link_rates[entry]) * 200;
   3585 
   3586 			if (link_rate_in_khz != 0) {
   3587 				link_rate = linkRateInKHzToLinkRateMultiplier(link_rate_in_khz);
   3588 				link->dpcd_caps.edp_supported_link_rates[link->dpcd_caps.edp_supported_link_rates_count] = link_rate;
   3589 				link->dpcd_caps.edp_supported_link_rates_count++;
   3590 
   3591 				if (link->reported_link_cap.link_rate < link_rate)
   3592 					link->reported_link_cap.link_rate = link_rate;
   3593 			}
   3594 		}
   3595 	}
   3596 	link->verified_link_cap = link->reported_link_cap;
   3597 }
   3598 
   3599 void dc_link_dp_enable_hpd(const struct dc_link *link)
   3600 {
   3601 	struct link_encoder *encoder = link->link_enc;
   3602 
   3603 	if (encoder != NULL && encoder->funcs->enable_hpd != NULL)
   3604 		encoder->funcs->enable_hpd(encoder);
   3605 }
   3606 
   3607 void dc_link_dp_disable_hpd(const struct dc_link *link)
   3608 {
   3609 	struct link_encoder *encoder = link->link_enc;
   3610 
   3611 	if (encoder != NULL && encoder->funcs->enable_hpd != NULL)
   3612 		encoder->funcs->disable_hpd(encoder);
   3613 }
   3614 
   3615 static bool is_dp_phy_pattern(enum dp_test_pattern test_pattern)
   3616 {
   3617 	if ((DP_TEST_PATTERN_PHY_PATTERN_BEGIN <= test_pattern &&
   3618 			test_pattern <= DP_TEST_PATTERN_PHY_PATTERN_END) ||
   3619 			test_pattern == DP_TEST_PATTERN_VIDEO_MODE)
   3620 		return true;
   3621 	else
   3622 		return false;
   3623 }
   3624 
   3625 static void set_crtc_test_pattern(struct dc_link *link,
   3626 				struct pipe_ctx *pipe_ctx,
   3627 				enum dp_test_pattern test_pattern,
   3628 				enum dp_test_pattern_color_space test_pattern_color_space)
   3629 {
   3630 	enum controller_dp_test_pattern controller_test_pattern;
   3631 	enum dc_color_depth color_depth = pipe_ctx->
   3632 		stream->timing.display_color_depth;
   3633 	struct bit_depth_reduction_params params;
   3634 	struct output_pixel_processor *opp = pipe_ctx->stream_res.opp;
   3635 	int width = pipe_ctx->stream->timing.h_addressable +
   3636 		pipe_ctx->stream->timing.h_border_left +
   3637 		pipe_ctx->stream->timing.h_border_right;
   3638 	int height = pipe_ctx->stream->timing.v_addressable +
   3639 		pipe_ctx->stream->timing.v_border_bottom +
   3640 		pipe_ctx->stream->timing.v_border_top;
   3641 
   3642 	memset(&params, 0, sizeof(params));
   3643 
   3644 	switch (test_pattern) {
   3645 	case DP_TEST_PATTERN_COLOR_SQUARES:
   3646 		controller_test_pattern =
   3647 				CONTROLLER_DP_TEST_PATTERN_COLORSQUARES;
   3648 	break;
   3649 	case DP_TEST_PATTERN_COLOR_SQUARES_CEA:
   3650 		controller_test_pattern =
   3651 				CONTROLLER_DP_TEST_PATTERN_COLORSQUARES_CEA;
   3652 	break;
   3653 	case DP_TEST_PATTERN_VERTICAL_BARS:
   3654 		controller_test_pattern =
   3655 				CONTROLLER_DP_TEST_PATTERN_VERTICALBARS;
   3656 	break;
   3657 	case DP_TEST_PATTERN_HORIZONTAL_BARS:
   3658 		controller_test_pattern =
   3659 				CONTROLLER_DP_TEST_PATTERN_HORIZONTALBARS;
   3660 	break;
   3661 	case DP_TEST_PATTERN_COLOR_RAMP:
   3662 		controller_test_pattern =
   3663 				CONTROLLER_DP_TEST_PATTERN_COLORRAMP;
   3664 	break;
   3665 	default:
   3666 		controller_test_pattern =
   3667 				CONTROLLER_DP_TEST_PATTERN_VIDEOMODE;
   3668 	break;
   3669 	}
   3670 
   3671 	switch (test_pattern) {
   3672 	case DP_TEST_PATTERN_COLOR_SQUARES:
   3673 	case DP_TEST_PATTERN_COLOR_SQUARES_CEA:
   3674 	case DP_TEST_PATTERN_VERTICAL_BARS:
   3675 	case DP_TEST_PATTERN_HORIZONTAL_BARS:
   3676 	case DP_TEST_PATTERN_COLOR_RAMP:
   3677 	{
   3678 		/* disable bit depth reduction */
   3679 		pipe_ctx->stream->bit_depth_params = params;
   3680 		opp->funcs->opp_program_bit_depth_reduction(opp, &params);
   3681 		if (pipe_ctx->stream_res.tg->funcs->set_test_pattern)
   3682 			pipe_ctx->stream_res.tg->funcs->set_test_pattern(pipe_ctx->stream_res.tg,
   3683 				controller_test_pattern, color_depth);
   3684 		else if (opp->funcs->opp_set_disp_pattern_generator) {
   3685 			struct pipe_ctx *odm_pipe;
   3686 			enum controller_dp_color_space controller_color_space;
   3687 			int opp_cnt = 1;
   3688 			int count;
   3689 
   3690 			switch (test_pattern_color_space) {
   3691 			case DP_TEST_PATTERN_COLOR_SPACE_RGB:
   3692 				controller_color_space = CONTROLLER_DP_COLOR_SPACE_RGB;
   3693 				break;
   3694 			case DP_TEST_PATTERN_COLOR_SPACE_YCBCR601:
   3695 				controller_color_space = CONTROLLER_DP_COLOR_SPACE_YCBCR601;
   3696 				break;
   3697 			case DP_TEST_PATTERN_COLOR_SPACE_YCBCR709:
   3698 				controller_color_space = CONTROLLER_DP_COLOR_SPACE_YCBCR709;
   3699 				break;
   3700 			case DP_TEST_PATTERN_COLOR_SPACE_UNDEFINED:
   3701 			default:
   3702 				controller_color_space = CONTROLLER_DP_COLOR_SPACE_UDEFINED;
   3703 				DC_LOG_ERROR("%s: Color space must be defined for test pattern", __func__);
   3704 				ASSERT(0);
   3705 				break;
   3706 			}
   3707 
   3708 			for (odm_pipe = pipe_ctx->next_odm_pipe; odm_pipe; odm_pipe = odm_pipe->next_odm_pipe)
   3709 				opp_cnt++;
   3710 
   3711 			width /= opp_cnt;
   3712 
   3713 			for (odm_pipe = pipe_ctx->next_odm_pipe; odm_pipe; odm_pipe = odm_pipe->next_odm_pipe) {
   3714 				struct output_pixel_processor *odm_opp = odm_pipe->stream_res.opp;
   3715 
   3716 				odm_opp->funcs->opp_program_bit_depth_reduction(odm_opp, &params);
   3717 				odm_opp->funcs->opp_set_disp_pattern_generator(odm_opp,
   3718 					controller_test_pattern,
   3719 					controller_color_space,
   3720 					color_depth,
   3721 					NULL,
   3722 					width,
   3723 					height);
   3724 			}
   3725 			opp->funcs->opp_set_disp_pattern_generator(opp,
   3726 				controller_test_pattern,
   3727 				controller_color_space,
   3728 				color_depth,
   3729 				NULL,
   3730 				width,
   3731 				height);
   3732 			/* wait for dpg to blank pixel data with test pattern */
   3733 			for (count = 0; count < 1000; count++) {
   3734 				if (opp->funcs->dpg_is_blanked(opp))
   3735 					break;
   3736 				udelay(100);
   3737 			}
   3738 		}
   3739 	}
   3740 	break;
   3741 	case DP_TEST_PATTERN_VIDEO_MODE:
   3742 	{
   3743 		/* restore bitdepth reduction */
   3744 		resource_build_bit_depth_reduction_params(pipe_ctx->stream, &params);
   3745 		pipe_ctx->stream->bit_depth_params = params;
   3746 		opp->funcs->opp_program_bit_depth_reduction(opp, &params);
   3747 		if (pipe_ctx->stream_res.tg->funcs->set_test_pattern)
   3748 			pipe_ctx->stream_res.tg->funcs->set_test_pattern(pipe_ctx->stream_res.tg,
   3749 				CONTROLLER_DP_TEST_PATTERN_VIDEOMODE,
   3750 				color_depth);
   3751 		else if (opp->funcs->opp_set_disp_pattern_generator) {
   3752 			struct pipe_ctx *odm_pipe;
   3753 			int opp_cnt = 1;
   3754 
   3755 			for (odm_pipe = pipe_ctx->next_odm_pipe; odm_pipe; odm_pipe = odm_pipe->next_odm_pipe)
   3756 				opp_cnt++;
   3757 
   3758 			width /= opp_cnt;
   3759 			for (odm_pipe = pipe_ctx->next_odm_pipe; odm_pipe; odm_pipe = odm_pipe->next_odm_pipe) {
   3760 				struct output_pixel_processor *odm_opp = odm_pipe->stream_res.opp;
   3761 
   3762 				odm_opp->funcs->opp_program_bit_depth_reduction(odm_opp, &params);
   3763 				odm_opp->funcs->opp_set_disp_pattern_generator(odm_opp,
   3764 					CONTROLLER_DP_TEST_PATTERN_VIDEOMODE,
   3765 					CONTROLLER_DP_COLOR_SPACE_UDEFINED,
   3766 					color_depth,
   3767 					NULL,
   3768 					width,
   3769 					height);
   3770 			}
   3771 			opp->funcs->opp_set_disp_pattern_generator(opp,
   3772 				CONTROLLER_DP_TEST_PATTERN_VIDEOMODE,
   3773 				CONTROLLER_DP_COLOR_SPACE_UDEFINED,
   3774 				color_depth,
   3775 				NULL,
   3776 				width,
   3777 				height);
   3778 		}
   3779 	}
   3780 	break;
   3781 
   3782 	default:
   3783 	break;
   3784 	}
   3785 }
   3786 
   3787 bool dc_link_dp_set_test_pattern(
   3788 	struct dc_link *link,
   3789 	enum dp_test_pattern test_pattern,
   3790 	enum dp_test_pattern_color_space test_pattern_color_space,
   3791 	const struct link_training_settings *p_link_settings,
   3792 	const unsigned char *p_custom_pattern,
   3793 	unsigned int cust_pattern_size)
   3794 {
   3795 	struct pipe_ctx *pipes = link->dc->current_state->res_ctx.pipe_ctx;
   3796 	struct pipe_ctx *pipe_ctx = &pipes[0];
   3797 	unsigned int lane;
   3798 	unsigned int i;
   3799 	unsigned char link_qual_pattern[LANE_COUNT_DP_MAX] = {0};
   3800 	union dpcd_training_pattern training_pattern;
   3801 	enum dpcd_phy_test_patterns pattern;
   3802 
   3803 	memset(&training_pattern, 0, sizeof(training_pattern));
   3804 
   3805 	for (i = 0; i < MAX_PIPES; i++) {
   3806 		if (pipes[i].stream->link == link && !pipes[i].top_pipe && !pipes[i].prev_odm_pipe) {
   3807 			pipe_ctx = &pipes[i];
   3808 			break;
   3809 		}
   3810 	}
   3811 
   3812 	/* Reset CRTC Test Pattern if it is currently running and request
   3813 	 * is VideoMode Reset DP Phy Test Pattern if it is currently running
   3814 	 * and request is VideoMode
   3815 	 */
   3816 	if (link->test_pattern_enabled && test_pattern ==
   3817 			DP_TEST_PATTERN_VIDEO_MODE) {
   3818 		/* Set CRTC Test Pattern */
   3819 		set_crtc_test_pattern(link, pipe_ctx, test_pattern, test_pattern_color_space);
   3820 		dp_set_hw_test_pattern(link, test_pattern,
   3821 				(const uint8_t *)p_custom_pattern,
   3822 				(uint32_t)cust_pattern_size);
   3823 
   3824 		/* Unblank Stream */
   3825 		link->dc->hwss.unblank_stream(
   3826 			pipe_ctx,
   3827 			&link->verified_link_cap);
   3828 		/* TODO:m_pHwss->MuteAudioEndpoint
   3829 		 * (pPathMode->pDisplayPath, false);
   3830 		 */
   3831 
   3832 		/* Reset Test Pattern state */
   3833 		link->test_pattern_enabled = false;
   3834 
   3835 		return true;
   3836 	}
   3837 
   3838 	/* Check for PHY Test Patterns */
   3839 	if (is_dp_phy_pattern(test_pattern)) {
   3840 		/* Set DPCD Lane Settings before running test pattern */
   3841 		if (p_link_settings != NULL) {
   3842 			dp_set_hw_lane_settings(link, p_link_settings, DPRX);
   3843 			dpcd_set_lane_settings(link, p_link_settings, DPRX);
   3844 		}
   3845 
   3846 		/* Blank stream if running test pattern */
   3847 		if (test_pattern != DP_TEST_PATTERN_VIDEO_MODE) {
   3848 			/*TODO:
   3849 			 * m_pHwss->
   3850 			 * MuteAudioEndpoint(pPathMode->pDisplayPath, true);
   3851 			 */
   3852 			/* Blank stream */
   3853 			pipes->stream_res.stream_enc->funcs->dp_blank(pipe_ctx->stream_res.stream_enc);
   3854 		}
   3855 
   3856 		dp_set_hw_test_pattern(link, test_pattern,
   3857 				(const uint8_t *)p_custom_pattern,
   3858 				(uint32_t)cust_pattern_size);
   3859 
   3860 		if (test_pattern != DP_TEST_PATTERN_VIDEO_MODE) {
   3861 			/* Set Test Pattern state */
   3862 			link->test_pattern_enabled = true;
   3863 			if (p_link_settings != NULL)
   3864 				dpcd_set_link_settings(link,
   3865 						p_link_settings);
   3866 		}
   3867 
   3868 		switch (test_pattern) {
   3869 		case DP_TEST_PATTERN_VIDEO_MODE:
   3870 			pattern = PHY_TEST_PATTERN_NONE;
   3871 			break;
   3872 		case DP_TEST_PATTERN_D102:
   3873 			pattern = PHY_TEST_PATTERN_D10_2;
   3874 			break;
   3875 		case DP_TEST_PATTERN_SYMBOL_ERROR:
   3876 			pattern = PHY_TEST_PATTERN_SYMBOL_ERROR;
   3877 			break;
   3878 		case DP_TEST_PATTERN_PRBS7:
   3879 			pattern = PHY_TEST_PATTERN_PRBS7;
   3880 			break;
   3881 		case DP_TEST_PATTERN_80BIT_CUSTOM:
   3882 			pattern = PHY_TEST_PATTERN_80BIT_CUSTOM;
   3883 			break;
   3884 		case DP_TEST_PATTERN_CP2520_1:
   3885 			pattern = PHY_TEST_PATTERN_CP2520_1;
   3886 			break;
   3887 		case DP_TEST_PATTERN_CP2520_2:
   3888 			pattern = PHY_TEST_PATTERN_CP2520_2;
   3889 			break;
   3890 		case DP_TEST_PATTERN_CP2520_3:
   3891 			pattern = PHY_TEST_PATTERN_CP2520_3;
   3892 			break;
   3893 		default:
   3894 			return false;
   3895 		}
   3896 
   3897 		if (test_pattern == DP_TEST_PATTERN_VIDEO_MODE
   3898 		/*TODO:&& !pPathMode->pDisplayPath->IsTargetPoweredOn()*/)
   3899 			return false;
   3900 
   3901 		if (link->dpcd_caps.dpcd_rev.raw >= DPCD_REV_12) {
   3902 			/* tell receiver that we are sending qualification
   3903 			 * pattern DP 1.2 or later - DP receiver's link quality
   3904 			 * pattern is set using DPCD LINK_QUAL_LANEx_SET
   3905 			 * register (0x10B~0x10E)\
   3906 			 */
   3907 			for (lane = 0; lane < LANE_COUNT_DP_MAX; lane++)
   3908 				link_qual_pattern[lane] =
   3909 						(unsigned char)(pattern);
   3910 
   3911 			core_link_write_dpcd(link,
   3912 					DP_LINK_QUAL_LANE0_SET,
   3913 					link_qual_pattern,
   3914 					sizeof(link_qual_pattern));
   3915 		} else if (link->dpcd_caps.dpcd_rev.raw >= DPCD_REV_10 ||
   3916 			   link->dpcd_caps.dpcd_rev.raw == 0) {
   3917 			/* tell receiver that we are sending qualification
   3918 			 * pattern DP 1.1a or earlier - DP receiver's link
   3919 			 * quality pattern is set using
   3920 			 * DPCD TRAINING_PATTERN_SET -> LINK_QUAL_PATTERN_SET
   3921 			 * register (0x102). We will use v_1.3 when we are
   3922 			 * setting test pattern for DP 1.1.
   3923 			 */
   3924 			core_link_read_dpcd(link, DP_TRAINING_PATTERN_SET,
   3925 					    &training_pattern.raw,
   3926 					    sizeof(training_pattern));
   3927 			training_pattern.v1_3.LINK_QUAL_PATTERN_SET = pattern;
   3928 			core_link_write_dpcd(link, DP_TRAINING_PATTERN_SET,
   3929 					     &training_pattern.raw,
   3930 					     sizeof(training_pattern));
   3931 		}
   3932 	} else {
   3933 		enum dc_color_space color_space = COLOR_SPACE_UNKNOWN;
   3934 
   3935 		switch (test_pattern_color_space) {
   3936 		case DP_TEST_PATTERN_COLOR_SPACE_RGB:
   3937 			color_space = COLOR_SPACE_SRGB;
   3938 			if (test_pattern == DP_TEST_PATTERN_COLOR_SQUARES_CEA)
   3939 				color_space = COLOR_SPACE_SRGB_LIMITED;
   3940 			break;
   3941 
   3942 		case DP_TEST_PATTERN_COLOR_SPACE_YCBCR601:
   3943 			color_space = COLOR_SPACE_YCBCR601;
   3944 			if (test_pattern == DP_TEST_PATTERN_COLOR_SQUARES_CEA)
   3945 				color_space = COLOR_SPACE_YCBCR601_LIMITED;
   3946 			break;
   3947 		case DP_TEST_PATTERN_COLOR_SPACE_YCBCR709:
   3948 			color_space = COLOR_SPACE_YCBCR709;
   3949 			if (test_pattern == DP_TEST_PATTERN_COLOR_SQUARES_CEA)
   3950 				color_space = COLOR_SPACE_YCBCR709_LIMITED;
   3951 			break;
   3952 		default:
   3953 			break;
   3954 		}
   3955 		/* update MSA to requested color space */
   3956 		pipe_ctx->stream_res.stream_enc->funcs->dp_set_stream_attribute(pipe_ctx->stream_res.stream_enc,
   3957 				&pipe_ctx->stream->timing,
   3958 				color_space,
   3959 				pipe_ctx->stream->use_vsc_sdp_for_colorimetry,
   3960 				link->dpcd_caps.dprx_feature.bits.SST_SPLIT_SDP_CAP);
   3961 
   3962 		/* CRTC Patterns */
   3963 		set_crtc_test_pattern(link, pipe_ctx, test_pattern, test_pattern_color_space);
   3964 
   3965 		/* Set Test Pattern state */
   3966 		link->test_pattern_enabled = true;
   3967 	}
   3968 
   3969 	return true;
   3970 }
   3971 
   3972 void dp_enable_mst_on_sink(struct dc_link *link, bool enable)
   3973 {
   3974 	unsigned char mstmCntl;
   3975 
   3976 	core_link_read_dpcd(link, DP_MSTM_CTRL, &mstmCntl, 1);
   3977 	if (enable)
   3978 		mstmCntl |= DP_MST_EN;
   3979 	else
   3980 		mstmCntl &= (~DP_MST_EN);
   3981 
   3982 	core_link_write_dpcd(link, DP_MSTM_CTRL, &mstmCntl, 1);
   3983 }
   3984 
   3985 void dp_set_panel_mode(struct dc_link *link, enum dp_panel_mode panel_mode)
   3986 {
   3987 	union dpcd_edp_config edp_config_set;
   3988 	bool panel_mode_edp = false;
   3989 
   3990 	memset(&edp_config_set, '\0', sizeof(union dpcd_edp_config));
   3991 
   3992 	if (panel_mode != DP_PANEL_MODE_DEFAULT) {
   3993 
   3994 		switch (panel_mode) {
   3995 		case DP_PANEL_MODE_EDP:
   3996 		case DP_PANEL_MODE_SPECIAL:
   3997 			panel_mode_edp = true;
   3998 			break;
   3999 
   4000 		default:
   4001 				break;
   4002 		}
   4003 
   4004 		/*set edp panel mode in receiver*/
   4005 		core_link_read_dpcd(
   4006 			link,
   4007 			DP_EDP_CONFIGURATION_SET,
   4008 			&edp_config_set.raw,
   4009 			sizeof(edp_config_set.raw));
   4010 
   4011 		if (edp_config_set.bits.PANEL_MODE_EDP
   4012 			!= panel_mode_edp) {
   4013 			enum dc_status result = DC_ERROR_UNEXPECTED;
   4014 
   4015 			edp_config_set.bits.PANEL_MODE_EDP =
   4016 			panel_mode_edp;
   4017 			result = core_link_write_dpcd(
   4018 				link,
   4019 				DP_EDP_CONFIGURATION_SET,
   4020 				&edp_config_set.raw,
   4021 				sizeof(edp_config_set.raw));
   4022 
   4023 			ASSERT(result == DC_OK);
   4024 		}
   4025 	}
   4026 	DC_LOG_DETECTION_DP_CAPS("Link: %d eDP panel mode supported: %d "
   4027 		 "eDP panel mode enabled: %d \n",
   4028 		 link->link_index,
   4029 		 link->dpcd_caps.panel_mode_edp,
   4030 		 panel_mode_edp);
   4031 }
   4032 
   4033 enum dp_panel_mode dp_get_panel_mode(struct dc_link *link)
   4034 {
   4035 	/* We need to explicitly check that connector
   4036 	 * is not DP. Some Travis_VGA get reported
   4037 	 * by video bios as DP.
   4038 	 */
   4039 	if (link->connector_signal != SIGNAL_TYPE_DISPLAY_PORT) {
   4040 
   4041 		switch (link->dpcd_caps.branch_dev_id) {
   4042 		case DP_BRANCH_DEVICE_ID_0022B9:
   4043 			/* alternate scrambler reset is required for Travis
   4044 			 * for the case when external chip does not
   4045 			 * provide sink device id, alternate scrambler
   4046 			 * scheme will  be overriden later by querying
   4047 			 * Encoder features
   4048 			 */
   4049 			if (strncmp(
   4050 				link->dpcd_caps.branch_dev_name,
   4051 				DP_VGA_LVDS_CONVERTER_ID_2,
   4052 				sizeof(
   4053 				link->dpcd_caps.
   4054 				branch_dev_name)) == 0) {
   4055 					return DP_PANEL_MODE_SPECIAL;
   4056 			}
   4057 			break;
   4058 		case DP_BRANCH_DEVICE_ID_00001A:
   4059 			/* alternate scrambler reset is required for Travis
   4060 			 * for the case when external chip does not provide
   4061 			 * sink device id, alternate scrambler scheme will
   4062 			 * be overriden later by querying Encoder feature
   4063 			 */
   4064 			if (strncmp(link->dpcd_caps.branch_dev_name,
   4065 				DP_VGA_LVDS_CONVERTER_ID_3,
   4066 				sizeof(
   4067 				link->dpcd_caps.
   4068 				branch_dev_name)) == 0) {
   4069 					return DP_PANEL_MODE_SPECIAL;
   4070 			}
   4071 			break;
   4072 		default:
   4073 			break;
   4074 		}
   4075 	}
   4076 
   4077 	if (link->dpcd_caps.panel_mode_edp) {
   4078 		return DP_PANEL_MODE_EDP;
   4079 	}
   4080 
   4081 	return DP_PANEL_MODE_DEFAULT;
   4082 }
   4083 
   4084 void dp_set_fec_ready(struct dc_link *link, bool ready)
   4085 {
   4086 	/* FEC has to be "set ready" before the link training.
   4087 	 * The policy is to always train with FEC
   4088 	 * if the sink supports it and leave it enabled on link.
   4089 	 * If FEC is not supported, disable it.
   4090 	 */
   4091 	struct link_encoder *link_enc = link->link_enc;
   4092 	uint8_t fec_config = 0;
   4093 
   4094 	if (link->dc->debug.disable_fec ||
   4095 			IS_FPGA_MAXIMUS_DC(link->ctx->dce_environment))
   4096 		return;
   4097 
   4098 	if (link_enc->funcs->fec_set_ready &&
   4099 			link->dpcd_caps.fec_cap.bits.FEC_CAPABLE) {
   4100 		if (ready) {
   4101 			fec_config = 1;
   4102 			if (core_link_write_dpcd(link,
   4103 					DP_FEC_CONFIGURATION,
   4104 					&fec_config,
   4105 					sizeof(fec_config)) == DC_OK) {
   4106 				link_enc->funcs->fec_set_ready(link_enc, true);
   4107 				link->fec_state = dc_link_fec_ready;
   4108 			} else {
   4109 				link->link_enc->funcs->fec_set_ready(link->link_enc, false);
   4110 				link->fec_state = dc_link_fec_not_ready;
   4111 				dm_error("dpcd write failed to set fec_ready");
   4112 			}
   4113 		} else if (link->fec_state == dc_link_fec_ready) {
   4114 			fec_config = 0;
   4115 			core_link_write_dpcd(link,
   4116 					DP_FEC_CONFIGURATION,
   4117 					&fec_config,
   4118 					sizeof(fec_config));
   4119 			link->link_enc->funcs->fec_set_ready(
   4120 					link->link_enc, false);
   4121 			link->fec_state = dc_link_fec_not_ready;
   4122 		}
   4123 	}
   4124 }
   4125 
   4126 void dp_set_fec_enable(struct dc_link *link, bool enable)
   4127 {
   4128 	struct link_encoder *link_enc = link->link_enc;
   4129 
   4130 	if (link->dc->debug.disable_fec ||
   4131 			IS_FPGA_MAXIMUS_DC(link->ctx->dce_environment))
   4132 		return;
   4133 
   4134 	if (link_enc->funcs->fec_set_enable &&
   4135 			link->dpcd_caps.fec_cap.bits.FEC_CAPABLE) {
   4136 		if (link->fec_state == dc_link_fec_ready && enable) {
   4137 			/* Accord to DP spec, FEC enable sequence can first
   4138 			 * be transmitted anytime after 1000 LL codes have
   4139 			 * been transmitted on the link after link training
   4140 			 * completion. Using 1 lane RBR should have the maximum
   4141 			 * time for transmitting 1000 LL codes which is 6.173 us.
   4142 			 * So use 7 microseconds delay instead.
   4143 			 */
   4144 			udelay(7);
   4145 			link_enc->funcs->fec_set_enable(link_enc, true);
   4146 			link->fec_state = dc_link_fec_enabled;
   4147 		} else if (link->fec_state == dc_link_fec_enabled && !enable) {
   4148 			link_enc->funcs->fec_set_enable(link_enc, false);
   4149 			link->fec_state = dc_link_fec_ready;
   4150 		}
   4151 	}
   4152 }
   4153 
   4154