1 /*
2 * Copyright 2023 Advanced Micro Devices, Inc.
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
18 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
20 * OTHER DEALINGS IN THE SOFTWARE.
21 *
22 * Authors: AMD
23 *
24 */
25
26 /* FILE POLICY AND INTENDED USAGE:
27 * This file owns the programming sequence of stream's dpms state associated
28 * with the link and link's enable/disable sequences as result of the stream's
29 * dpms state change.
30 *
31 * TODO - The reason link owns stream's dpms programming sequence is
32 * because dpms programming sequence is highly dependent on underlying signal
33 * specific link protocols. This unfortunately causes link to own a portion of
34 * stream state programming sequence. This creates a gray area where the
35 * boundary between link and stream is not clearly defined.
36 */
37
38 #include "link_dpms.h"
39 #include "link_hwss.h"
40 #include "link_validation.h"
41 #include "accessories/link_dp_trace.h"
42 #include "protocols/link_dpcd.h"
43 #include "protocols/link_ddc.h"
44 #include "protocols/link_hpd.h"
45 #include "protocols/link_dp_phy.h"
46 #include "protocols/link_dp_capability.h"
47 #include "protocols/link_dp_training.h"
48 #include "protocols/link_edp_panel_control.h"
49 #include "protocols/link_dp_panel_replay.h"
50 #include "protocols/link_dp_dpia_bw.h"
51
52 #include "dm_helpers.h"
53 #include "link_enc_cfg.h"
54 #include "resource.h"
55 #include "dsc.h"
56 #include "dccg.h"
57 #include "clk_mgr.h"
58 #include "atomfirmware.h"
59 #include "vpg.h"
60
61 #define DC_LOGGER \
62 dc_logger
63 #define DC_LOGGER_INIT(logger) \
64 struct dal_logger *dc_logger = logger
65
66 #define LINK_INFO(...) \
67 DC_LOG_HW_HOTPLUG( \
68 __VA_ARGS__)
69
70 #define RETIMER_REDRIVER_INFO(...) \
71 DC_LOG_RETIMER_REDRIVER( \
72 __VA_ARGS__)
73
74 #define MAX_MTP_SLOT_COUNT 64
75 #define LINK_TRAINING_ATTEMPTS 4
76 #define PEAK_FACTOR_X1000 1006
77
link_blank_all_dp_displays(struct dc * dc)78 void link_blank_all_dp_displays(struct dc *dc)
79 {
80 unsigned int i;
81 uint8_t dpcd_power_state = '\0';
82 enum dc_status status = DC_ERROR_UNEXPECTED;
83
84 for (i = 0; i < dc->link_count; i++) {
85 if ((dc->links[i]->connector_signal != SIGNAL_TYPE_DISPLAY_PORT) ||
86 (dc->links[i]->priv == NULL) || (dc->links[i]->local_sink == NULL))
87 continue;
88
89 /* DP 2.0 spec requires that we read LTTPR caps first */
90 dp_retrieve_lttpr_cap(dc->links[i]);
91 /* if any of the displays are lit up turn them off */
92 status = core_link_read_dpcd(dc->links[i], DP_SET_POWER,
93 &dpcd_power_state, sizeof(dpcd_power_state));
94
95 if (status == DC_OK && dpcd_power_state == DP_POWER_STATE_D0)
96 link_blank_dp_stream(dc->links[i], true);
97 }
98
99 }
100
link_blank_all_edp_displays(struct dc * dc)101 void link_blank_all_edp_displays(struct dc *dc)
102 {
103 unsigned int i;
104 uint8_t dpcd_power_state = '\0';
105 enum dc_status status = DC_ERROR_UNEXPECTED;
106
107 for (i = 0; i < dc->link_count; i++) {
108 if ((dc->links[i]->connector_signal != SIGNAL_TYPE_EDP) ||
109 (!dc->links[i]->edp_sink_present))
110 continue;
111
112 /* if any of the displays are lit up turn them off */
113 status = core_link_read_dpcd(dc->links[i], DP_SET_POWER,
114 &dpcd_power_state, sizeof(dpcd_power_state));
115
116 if (status == DC_OK && dpcd_power_state == DP_POWER_STATE_D0)
117 link_blank_dp_stream(dc->links[i], true);
118 }
119 }
120
link_blank_dp_stream(struct dc_link * link,bool hw_init)121 void link_blank_dp_stream(struct dc_link *link, bool hw_init)
122 {
123 unsigned int j;
124 struct dc *dc = link->ctx->dc;
125 enum signal_type signal = link->connector_signal;
126
127 if ((signal == SIGNAL_TYPE_EDP) ||
128 (signal == SIGNAL_TYPE_DISPLAY_PORT)) {
129 if (link->ep_type == DISPLAY_ENDPOINT_PHY &&
130 link->link_enc->funcs->get_dig_frontend &&
131 link->link_enc->funcs->is_dig_enabled(link->link_enc)) {
132 int fe = link->link_enc->funcs->get_dig_frontend(link->link_enc);
133
134 if (fe != ENGINE_ID_UNKNOWN)
135 for (j = 0; j < dc->res_pool->stream_enc_count; j++) {
136 if (fe == dc->res_pool->stream_enc[j]->id) {
137 dc->res_pool->stream_enc[j]->funcs->dp_blank(link,
138 dc->res_pool->stream_enc[j]);
139 break;
140 }
141 }
142 }
143
144 if (((!dc->is_switch_in_progress_dest) && ((!link->wa_flags.dp_keep_receiver_powered) || hw_init)) &&
145 (link->type != dc_connection_none))
146 dpcd_write_rx_power_ctrl(link, false);
147 }
148 }
149
link_set_all_streams_dpms_off_for_link(struct dc_link * link)150 void link_set_all_streams_dpms_off_for_link(struct dc_link *link)
151 {
152 struct pipe_ctx *pipes[MAX_PIPES];
153 struct dc_stream_state *streams[MAX_PIPES];
154 struct dc_state *state = link->dc->current_state;
155 uint8_t count;
156 int i;
157 struct dc_stream_update stream_update;
158 bool dpms_off = true;
159 struct link_resource link_res = {0};
160
161 memset(&stream_update, 0, sizeof(stream_update));
162 stream_update.dpms_off = &dpms_off;
163
164 link_get_master_pipes_with_dpms_on(link, state, &count, pipes);
165
166 /* The subsequent call to dc_commit_updates_for_stream for a full update
167 * will release the current state and swap to a new state. Releasing the
168 * current state results in the stream pointers in the pipe_ctx structs
169 * to be zero'd. Hence, cache all streams prior to dc_commit_updates_for_stream.
170 */
171 for (i = 0; i < count; i++)
172 streams[i] = pipes[i]->stream;
173
174 for (i = 0; i < count; i++) {
175 stream_update.stream = streams[i];
176 dc_commit_updates_for_stream(link->ctx->dc, NULL, 0,
177 streams[i], &stream_update,
178 state);
179 }
180
181 /* link can be also enabled by vbios. In this case it is not recorded
182 * in pipe_ctx. Disable link phy here to make sure it is completely off
183 */
184 dp_disable_link_phy(link, &link_res, link->connector_signal);
185 }
186
link_resume(struct dc_link * link)187 void link_resume(struct dc_link *link)
188 {
189 if (link->connector_signal != SIGNAL_TYPE_VIRTUAL)
190 program_hpd_filter(link);
191 }
192
193 /* This function returns true if the pipe is used to feed video signal directly
194 * to the link.
195 */
is_master_pipe_for_link(const struct dc_link * link,const struct pipe_ctx * pipe)196 static bool is_master_pipe_for_link(const struct dc_link *link,
197 const struct pipe_ctx *pipe)
198 {
199 return resource_is_pipe_type(pipe, OTG_MASTER) &&
200 pipe->stream->link == link;
201 }
202
203 /*
204 * This function finds all master pipes feeding to a given link with dpms set to
205 * on in given dc state.
206 */
link_get_master_pipes_with_dpms_on(const struct dc_link * link,struct dc_state * state,uint8_t * count,struct pipe_ctx * pipes[MAX_PIPES])207 void link_get_master_pipes_with_dpms_on(const struct dc_link *link,
208 struct dc_state *state,
209 uint8_t *count,
210 struct pipe_ctx *pipes[MAX_PIPES])
211 {
212 int i;
213 struct pipe_ctx *pipe = NULL;
214
215 *count = 0;
216 for (i = 0; i < MAX_PIPES; i++) {
217 pipe = &state->res_ctx.pipe_ctx[i];
218
219 if (is_master_pipe_for_link(link, pipe) &&
220 pipe->stream->dpms_off == false) {
221 pipes[(*count)++] = pipe;
222 }
223 }
224 }
225
get_ext_hdmi_settings(struct pipe_ctx * pipe_ctx,enum engine_id eng_id,struct ext_hdmi_settings * settings)226 static bool get_ext_hdmi_settings(struct pipe_ctx *pipe_ctx,
227 enum engine_id eng_id,
228 struct ext_hdmi_settings *settings)
229 {
230 bool result = false;
231 int i = 0;
232 struct integrated_info *integrated_info =
233 pipe_ctx->stream->ctx->dc_bios->integrated_info;
234
235 if (integrated_info == NULL)
236 return false;
237
238 /*
239 * Get retimer settings from sbios for passing SI eye test for DCE11
240 * The setting values are varied based on board revision and port id
241 * Therefore the setting values of each ports is passed by sbios.
242 */
243
244 // Check if current bios contains ext Hdmi settings
245 if (integrated_info->gpu_cap_info & 0x20) {
246 switch (eng_id) {
247 case ENGINE_ID_DIGA:
248 settings->slv_addr = integrated_info->dp0_ext_hdmi_slv_addr;
249 settings->reg_num = integrated_info->dp0_ext_hdmi_6g_reg_num;
250 settings->reg_num_6g = integrated_info->dp0_ext_hdmi_6g_reg_num;
251 memmove(settings->reg_settings,
252 integrated_info->dp0_ext_hdmi_reg_settings,
253 sizeof(integrated_info->dp0_ext_hdmi_reg_settings));
254 memmove(settings->reg_settings_6g,
255 integrated_info->dp0_ext_hdmi_6g_reg_settings,
256 sizeof(integrated_info->dp0_ext_hdmi_6g_reg_settings));
257 result = true;
258 break;
259 case ENGINE_ID_DIGB:
260 settings->slv_addr = integrated_info->dp1_ext_hdmi_slv_addr;
261 settings->reg_num = integrated_info->dp1_ext_hdmi_6g_reg_num;
262 settings->reg_num_6g = integrated_info->dp1_ext_hdmi_6g_reg_num;
263 memmove(settings->reg_settings,
264 integrated_info->dp1_ext_hdmi_reg_settings,
265 sizeof(integrated_info->dp1_ext_hdmi_reg_settings));
266 memmove(settings->reg_settings_6g,
267 integrated_info->dp1_ext_hdmi_6g_reg_settings,
268 sizeof(integrated_info->dp1_ext_hdmi_6g_reg_settings));
269 result = true;
270 break;
271 case ENGINE_ID_DIGC:
272 settings->slv_addr = integrated_info->dp2_ext_hdmi_slv_addr;
273 settings->reg_num = integrated_info->dp2_ext_hdmi_6g_reg_num;
274 settings->reg_num_6g = integrated_info->dp2_ext_hdmi_6g_reg_num;
275 memmove(settings->reg_settings,
276 integrated_info->dp2_ext_hdmi_reg_settings,
277 sizeof(integrated_info->dp2_ext_hdmi_reg_settings));
278 memmove(settings->reg_settings_6g,
279 integrated_info->dp2_ext_hdmi_6g_reg_settings,
280 sizeof(integrated_info->dp2_ext_hdmi_6g_reg_settings));
281 result = true;
282 break;
283 case ENGINE_ID_DIGD:
284 settings->slv_addr = integrated_info->dp3_ext_hdmi_slv_addr;
285 settings->reg_num = integrated_info->dp3_ext_hdmi_6g_reg_num;
286 settings->reg_num_6g = integrated_info->dp3_ext_hdmi_6g_reg_num;
287 memmove(settings->reg_settings,
288 integrated_info->dp3_ext_hdmi_reg_settings,
289 sizeof(integrated_info->dp3_ext_hdmi_reg_settings));
290 memmove(settings->reg_settings_6g,
291 integrated_info->dp3_ext_hdmi_6g_reg_settings,
292 sizeof(integrated_info->dp3_ext_hdmi_6g_reg_settings));
293 result = true;
294 break;
295 default:
296 break;
297 }
298
299 if (result == true) {
300 // Validate settings from bios integrated info table
301 if (settings->slv_addr == 0)
302 return false;
303 if (settings->reg_num > 9)
304 return false;
305 if (settings->reg_num_6g > 3)
306 return false;
307
308 for (i = 0; i < settings->reg_num; i++) {
309 if (settings->reg_settings[i].i2c_reg_index > 0x20)
310 return false;
311 }
312
313 for (i = 0; i < settings->reg_num_6g; i++) {
314 if (settings->reg_settings_6g[i].i2c_reg_index > 0x20)
315 return false;
316 }
317 }
318 }
319
320 return result;
321 }
322
write_i2c(struct pipe_ctx * pipe_ctx,uint8_t address,uint8_t * buffer,uint32_t length)323 static bool write_i2c(struct pipe_ctx *pipe_ctx,
324 uint8_t address, uint8_t *buffer, uint32_t length)
325 {
326 struct i2c_command cmd = {0};
327 struct i2c_payload payload = {0};
328
329 memset(&payload, 0, sizeof(payload));
330 memset(&cmd, 0, sizeof(cmd));
331
332 cmd.number_of_payloads = 1;
333 cmd.engine = I2C_COMMAND_ENGINE_DEFAULT;
334 cmd.speed = pipe_ctx->stream->ctx->dc->caps.i2c_speed_in_khz;
335
336 payload.address = address;
337 payload.data = buffer;
338 payload.length = length;
339 payload.write = true;
340 cmd.payloads = &payload;
341
342 if (dm_helpers_submit_i2c(pipe_ctx->stream->ctx,
343 pipe_ctx->stream->link, &cmd))
344 return true;
345
346 return false;
347 }
348
write_i2c_retimer_setting(struct pipe_ctx * pipe_ctx,bool is_vga_mode,bool is_over_340mhz,struct ext_hdmi_settings * settings)349 static void write_i2c_retimer_setting(
350 struct pipe_ctx *pipe_ctx,
351 bool is_vga_mode,
352 bool is_over_340mhz,
353 struct ext_hdmi_settings *settings)
354 {
355 uint8_t slave_address = (settings->slv_addr >> 1);
356 uint8_t buffer[2];
357 const uint8_t apply_rx_tx_change = 0x4;
358 uint8_t offset = 0xA;
359 uint8_t value = 0;
360 int i = 0;
361 bool i2c_success = false;
362 DC_LOGGER_INIT(pipe_ctx->stream->ctx->logger);
363
364 memset(&buffer, 0, sizeof(buffer));
365
366 /* Start Ext-Hdmi programming*/
367
368 for (i = 0; i < settings->reg_num; i++) {
369 /* Apply 3G settings */
370 if (settings->reg_settings[i].i2c_reg_index <= 0x20) {
371
372 buffer[0] = settings->reg_settings[i].i2c_reg_index;
373 buffer[1] = settings->reg_settings[i].i2c_reg_val;
374 i2c_success = write_i2c(pipe_ctx, slave_address,
375 buffer, sizeof(buffer));
376 RETIMER_REDRIVER_INFO("retimer write to slave_address = 0x%x,\
377 offset = 0x%x, reg_val= 0x%x, i2c_success = %d\n",
378 slave_address, buffer[0], buffer[1], i2c_success?1:0);
379
380 if (!i2c_success)
381 goto i2c_write_fail;
382
383 /* Based on DP159 specs, APPLY_RX_TX_CHANGE bit in 0x0A
384 * needs to be set to 1 on every 0xA-0xC write.
385 */
386 if (settings->reg_settings[i].i2c_reg_index == 0xA ||
387 settings->reg_settings[i].i2c_reg_index == 0xB ||
388 settings->reg_settings[i].i2c_reg_index == 0xC) {
389
390 /* Query current value from offset 0xA */
391 if (settings->reg_settings[i].i2c_reg_index == 0xA)
392 value = settings->reg_settings[i].i2c_reg_val;
393 else {
394 i2c_success =
395 link_query_ddc_data(
396 pipe_ctx->stream->link->ddc,
397 slave_address, &offset, 1, &value, 1);
398 if (!i2c_success)
399 goto i2c_write_fail;
400 }
401
402 buffer[0] = offset;
403 /* Set APPLY_RX_TX_CHANGE bit to 1 */
404 buffer[1] = value | apply_rx_tx_change;
405 i2c_success = write_i2c(pipe_ctx, slave_address,
406 buffer, sizeof(buffer));
407 RETIMER_REDRIVER_INFO("retimer write to slave_address = 0x%x,\
408 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
409 slave_address, buffer[0], buffer[1], i2c_success?1:0);
410 if (!i2c_success)
411 goto i2c_write_fail;
412 }
413 }
414 }
415
416 /* Apply 3G settings */
417 if (is_over_340mhz) {
418 for (i = 0; i < settings->reg_num_6g; i++) {
419 /* Apply 3G settings */
420 if (settings->reg_settings[i].i2c_reg_index <= 0x20) {
421
422 buffer[0] = settings->reg_settings_6g[i].i2c_reg_index;
423 buffer[1] = settings->reg_settings_6g[i].i2c_reg_val;
424 i2c_success = write_i2c(pipe_ctx, slave_address,
425 buffer, sizeof(buffer));
426 RETIMER_REDRIVER_INFO("above 340Mhz: retimer write to slave_address = 0x%x,\
427 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
428 slave_address, buffer[0], buffer[1], i2c_success?1:0);
429
430 if (!i2c_success)
431 goto i2c_write_fail;
432
433 /* Based on DP159 specs, APPLY_RX_TX_CHANGE bit in 0x0A
434 * needs to be set to 1 on every 0xA-0xC write.
435 */
436 if (settings->reg_settings_6g[i].i2c_reg_index == 0xA ||
437 settings->reg_settings_6g[i].i2c_reg_index == 0xB ||
438 settings->reg_settings_6g[i].i2c_reg_index == 0xC) {
439
440 /* Query current value from offset 0xA */
441 if (settings->reg_settings_6g[i].i2c_reg_index == 0xA)
442 value = settings->reg_settings_6g[i].i2c_reg_val;
443 else {
444 i2c_success =
445 link_query_ddc_data(
446 pipe_ctx->stream->link->ddc,
447 slave_address, &offset, 1, &value, 1);
448 if (!i2c_success)
449 goto i2c_write_fail;
450 }
451
452 buffer[0] = offset;
453 /* Set APPLY_RX_TX_CHANGE bit to 1 */
454 buffer[1] = value | apply_rx_tx_change;
455 i2c_success = write_i2c(pipe_ctx, slave_address,
456 buffer, sizeof(buffer));
457 RETIMER_REDRIVER_INFO("retimer write to slave_address = 0x%x,\
458 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
459 slave_address, buffer[0], buffer[1], i2c_success?1:0);
460 if (!i2c_success)
461 goto i2c_write_fail;
462 }
463 }
464 }
465 }
466
467 if (is_vga_mode) {
468 /* Program additional settings if using 640x480 resolution */
469
470 /* Write offset 0xFF to 0x01 */
471 buffer[0] = 0xff;
472 buffer[1] = 0x01;
473 i2c_success = write_i2c(pipe_ctx, slave_address,
474 buffer, sizeof(buffer));
475 RETIMER_REDRIVER_INFO("retimer write to slave_address = 0x%x,\
476 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
477 slave_address, buffer[0], buffer[1], i2c_success?1:0);
478 if (!i2c_success)
479 goto i2c_write_fail;
480
481 /* Write offset 0x00 to 0x23 */
482 buffer[0] = 0x00;
483 buffer[1] = 0x23;
484 i2c_success = write_i2c(pipe_ctx, slave_address,
485 buffer, sizeof(buffer));
486 RETIMER_REDRIVER_INFO("retimer write to slave_address = 0x%x,\
487 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
488 slave_address, buffer[0], buffer[1], i2c_success?1:0);
489 if (!i2c_success)
490 goto i2c_write_fail;
491
492 /* Write offset 0xff to 0x00 */
493 buffer[0] = 0xff;
494 buffer[1] = 0x00;
495 i2c_success = write_i2c(pipe_ctx, slave_address,
496 buffer, sizeof(buffer));
497 RETIMER_REDRIVER_INFO("retimer write to slave_address = 0x%x,\
498 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
499 slave_address, buffer[0], buffer[1], i2c_success?1:0);
500 if (!i2c_success)
501 goto i2c_write_fail;
502
503 }
504
505 return;
506
507 i2c_write_fail:
508 DC_LOG_DEBUG("Set retimer failed");
509 }
510
write_i2c_default_retimer_setting(struct pipe_ctx * pipe_ctx,bool is_vga_mode,bool is_over_340mhz)511 static void write_i2c_default_retimer_setting(
512 struct pipe_ctx *pipe_ctx,
513 bool is_vga_mode,
514 bool is_over_340mhz)
515 {
516 uint8_t slave_address = (0xBA >> 1);
517 uint8_t buffer[2];
518 bool i2c_success = false;
519 DC_LOGGER_INIT(pipe_ctx->stream->ctx->logger);
520
521 memset(&buffer, 0, sizeof(buffer));
522
523 /* Program Slave Address for tuning single integrity */
524 /* Write offset 0x0A to 0x13 */
525 buffer[0] = 0x0A;
526 buffer[1] = 0x13;
527 i2c_success = write_i2c(pipe_ctx, slave_address,
528 buffer, sizeof(buffer));
529 RETIMER_REDRIVER_INFO("retimer writes default setting to slave_address = 0x%x,\
530 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
531 slave_address, buffer[0], buffer[1], i2c_success?1:0);
532 if (!i2c_success)
533 goto i2c_write_fail;
534
535 /* Write offset 0x0A to 0x17 */
536 buffer[0] = 0x0A;
537 buffer[1] = 0x17;
538 i2c_success = write_i2c(pipe_ctx, slave_address,
539 buffer, sizeof(buffer));
540 RETIMER_REDRIVER_INFO("retimer write to slave_addr = 0x%x,\
541 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
542 slave_address, buffer[0], buffer[1], i2c_success?1:0);
543 if (!i2c_success)
544 goto i2c_write_fail;
545
546 /* Write offset 0x0B to 0xDA or 0xD8 */
547 buffer[0] = 0x0B;
548 buffer[1] = is_over_340mhz ? 0xDA : 0xD8;
549 i2c_success = write_i2c(pipe_ctx, slave_address,
550 buffer, sizeof(buffer));
551 RETIMER_REDRIVER_INFO("retimer write to slave_addr = 0x%x,\
552 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
553 slave_address, buffer[0], buffer[1], i2c_success?1:0);
554 if (!i2c_success)
555 goto i2c_write_fail;
556
557 /* Write offset 0x0A to 0x17 */
558 buffer[0] = 0x0A;
559 buffer[1] = 0x17;
560 i2c_success = write_i2c(pipe_ctx, slave_address,
561 buffer, sizeof(buffer));
562 RETIMER_REDRIVER_INFO("retimer write to slave_addr = 0x%x,\
563 offset = 0x%x, reg_val= 0x%x, i2c_success = %d\n",
564 slave_address, buffer[0], buffer[1], i2c_success?1:0);
565 if (!i2c_success)
566 goto i2c_write_fail;
567
568 /* Write offset 0x0C to 0x1D or 0x91 */
569 buffer[0] = 0x0C;
570 buffer[1] = is_over_340mhz ? 0x1D : 0x91;
571 i2c_success = write_i2c(pipe_ctx, slave_address,
572 buffer, sizeof(buffer));
573 RETIMER_REDRIVER_INFO("retimer write to slave_addr = 0x%x,\
574 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
575 slave_address, buffer[0], buffer[1], i2c_success?1:0);
576 if (!i2c_success)
577 goto i2c_write_fail;
578
579 /* Write offset 0x0A to 0x17 */
580 buffer[0] = 0x0A;
581 buffer[1] = 0x17;
582 i2c_success = write_i2c(pipe_ctx, slave_address,
583 buffer, sizeof(buffer));
584 RETIMER_REDRIVER_INFO("retimer write to slave_addr = 0x%x,\
585 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
586 slave_address, buffer[0], buffer[1], i2c_success?1:0);
587 if (!i2c_success)
588 goto i2c_write_fail;
589
590
591 if (is_vga_mode) {
592 /* Program additional settings if using 640x480 resolution */
593
594 /* Write offset 0xFF to 0x01 */
595 buffer[0] = 0xff;
596 buffer[1] = 0x01;
597 i2c_success = write_i2c(pipe_ctx, slave_address,
598 buffer, sizeof(buffer));
599 RETIMER_REDRIVER_INFO("retimer write to slave_addr = 0x%x,\
600 offset = 0x%x, reg_val = 0x%x, i2c_success = %d\n",
601 slave_address, buffer[0], buffer[1], i2c_success?1:0);
602 if (!i2c_success)
603 goto i2c_write_fail;
604
605 /* Write offset 0x00 to 0x23 */
606 buffer[0] = 0x00;
607 buffer[1] = 0x23;
608 i2c_success = write_i2c(pipe_ctx, slave_address,
609 buffer, sizeof(buffer));
610 RETIMER_REDRIVER_INFO("retimer write to slave_addr = 0x%x,\
611 offset = 0x%x, reg_val= 0x%x, i2c_success = %d\n",
612 slave_address, buffer[0], buffer[1], i2c_success?1:0);
613 if (!i2c_success)
614 goto i2c_write_fail;
615
616 /* Write offset 0xff to 0x00 */
617 buffer[0] = 0xff;
618 buffer[1] = 0x00;
619 i2c_success = write_i2c(pipe_ctx, slave_address,
620 buffer, sizeof(buffer));
621 RETIMER_REDRIVER_INFO("retimer write default setting to slave_addr = 0x%x,\
622 offset = 0x%x, reg_val= 0x%x, i2c_success = %d end here\n",
623 slave_address, buffer[0], buffer[1], i2c_success?1:0);
624 if (!i2c_success)
625 goto i2c_write_fail;
626 }
627
628 return;
629
630 i2c_write_fail:
631 DC_LOG_DEBUG("Set default retimer failed");
632 }
633
write_i2c_redriver_setting(struct pipe_ctx * pipe_ctx,bool is_over_340mhz)634 static void write_i2c_redriver_setting(
635 struct pipe_ctx *pipe_ctx,
636 bool is_over_340mhz)
637 {
638 uint8_t slave_address = (0xF0 >> 1);
639 uint8_t buffer[16];
640 bool i2c_success = false;
641 DC_LOGGER_INIT(pipe_ctx->stream->ctx->logger);
642
643 memset(&buffer, 0, sizeof(buffer));
644
645 // Program Slave Address for tuning single integrity
646 buffer[3] = 0x4E;
647 buffer[4] = 0x4E;
648 buffer[5] = 0x4E;
649 buffer[6] = is_over_340mhz ? 0x4E : 0x4A;
650
651 i2c_success = write_i2c(pipe_ctx, slave_address,
652 buffer, sizeof(buffer));
653 RETIMER_REDRIVER_INFO("redriver write 0 to all 16 reg offset expect following:\n\
654 \t slave_addr = 0x%x, offset[3] = 0x%x, offset[4] = 0x%x,\
655 offset[5] = 0x%x,offset[6] is_over_340mhz = 0x%x,\
656 i2c_success = %d\n",
657 slave_address, buffer[3], buffer[4], buffer[5], buffer[6], i2c_success?1:0);
658
659 if (!i2c_success)
660 DC_LOG_DEBUG("Set redriver failed");
661 }
662
update_psp_stream_config(struct pipe_ctx * pipe_ctx,bool dpms_off)663 static void update_psp_stream_config(struct pipe_ctx *pipe_ctx, bool dpms_off)
664 {
665 struct cp_psp *cp_psp = &pipe_ctx->stream->ctx->cp_psp;
666 struct link_encoder *link_enc = pipe_ctx->link_res.dio_link_enc;
667 struct cp_psp_stream_config config = {0};
668 enum dp_panel_mode panel_mode =
669 dp_get_panel_mode(pipe_ctx->stream->link);
670
671 if (cp_psp == NULL || cp_psp->funcs.update_stream_config == NULL)
672 return;
673 if (!pipe_ctx->stream->ctx->dc->config.unify_link_enc_assignment)
674 link_enc = link_enc_cfg_get_link_enc(pipe_ctx->stream->link);
675 ASSERT(link_enc);
676 if (link_enc == NULL)
677 return;
678
679 /* otg instance */
680 config.otg_inst = (uint8_t) pipe_ctx->stream_res.tg->inst;
681
682 /* dig front end */
683 config.dig_fe = (uint8_t) pipe_ctx->stream_res.stream_enc->stream_enc_inst;
684
685 /* stream encoder index */
686 config.stream_enc_idx = pipe_ctx->stream_res.stream_enc->id - ENGINE_ID_DIGA;
687 if (dp_is_128b_132b_signal(pipe_ctx))
688 config.stream_enc_idx =
689 pipe_ctx->stream_res.hpo_dp_stream_enc->id - ENGINE_ID_HPO_DP_0;
690
691 /* dig back end */
692 config.dig_be = pipe_ctx->stream->link->link_enc_hw_inst;
693
694 /* link encoder index */
695 config.link_enc_idx = link_enc->transmitter - TRANSMITTER_UNIPHY_A;
696 if (dp_is_128b_132b_signal(pipe_ctx))
697 config.link_enc_idx = pipe_ctx->link_res.hpo_dp_link_enc->inst;
698
699 /* dio output index is dpia index for DPIA endpoint & dcio index by default */
700 if (pipe_ctx->stream->link->ep_type == DISPLAY_ENDPOINT_USB4_DPIA)
701 config.dio_output_idx = pipe_ctx->stream->link->link_id.enum_id - ENUM_ID_1;
702 else
703 config.dio_output_idx = link_enc->transmitter - TRANSMITTER_UNIPHY_A;
704
705
706 /* phy index */
707 config.phy_idx = resource_transmitter_to_phy_idx(
708 pipe_ctx->stream->link->dc, link_enc->transmitter);
709 if (pipe_ctx->stream->link->ep_type == DISPLAY_ENDPOINT_USB4_DPIA)
710 /* USB4 DPIA doesn't use PHY in our soc, initialize it to 0 */
711 config.phy_idx = 0;
712
713 /* stream properties */
714 config.assr_enabled = (panel_mode == DP_PANEL_MODE_EDP) ? 1 : 0;
715 config.mst_enabled = (pipe_ctx->stream->signal ==
716 SIGNAL_TYPE_DISPLAY_PORT_MST) ? 1 : 0;
717 config.dp2_enabled = dp_is_128b_132b_signal(pipe_ctx) ? 1 : 0;
718 config.usb4_enabled = (pipe_ctx->stream->link->ep_type == DISPLAY_ENDPOINT_USB4_DPIA) ?
719 1 : 0;
720 config.dpms_off = dpms_off;
721
722 /* dm stream context */
723 config.dm_stream_ctx = pipe_ctx->stream->dm_stream_context;
724
725 cp_psp->funcs.update_stream_config(cp_psp->handle, &config);
726 }
727
set_avmute(struct pipe_ctx * pipe_ctx,bool enable)728 static void set_avmute(struct pipe_ctx *pipe_ctx, bool enable)
729 {
730 struct dc *dc = pipe_ctx->stream->ctx->dc;
731
732 if (!dc_is_hdmi_signal(pipe_ctx->stream->signal))
733 return;
734
735 dc->hwss.set_avmute(pipe_ctx, enable);
736 }
737
enable_mst_on_sink(struct dc_link * link,bool enable)738 static void enable_mst_on_sink(struct dc_link *link, bool enable)
739 {
740 unsigned char mstmCntl = 0;
741
742 core_link_read_dpcd(link, DP_MSTM_CTRL, &mstmCntl, 1);
743 if (enable)
744 mstmCntl |= DP_MST_EN;
745 else
746 mstmCntl &= (~DP_MST_EN);
747
748 core_link_write_dpcd(link, DP_MSTM_CTRL, &mstmCntl, 1);
749 }
750
dsc_optc_config_log(struct display_stream_compressor * dsc,struct dsc_optc_config * config)751 static void dsc_optc_config_log(struct display_stream_compressor *dsc,
752 struct dsc_optc_config *config)
753 {
754 uint32_t precision = 1 << 28;
755 uint32_t bytes_per_pixel_int = config->bytes_per_pixel / precision;
756 uint32_t bytes_per_pixel_mod = config->bytes_per_pixel % precision;
757 uint64_t ll_bytes_per_pix_fraq = bytes_per_pixel_mod;
758 DC_LOGGER_INIT(dsc->ctx->logger);
759
760 /* 7 fractional digits decimal precision for bytes per pixel is enough because DSC
761 * bits per pixel precision is 1/16th of a pixel, which means bytes per pixel precision is
762 * 1/16/8 = 1/128 of a byte, or 0.0078125 decimal
763 */
764 ll_bytes_per_pix_fraq *= 10000000;
765 ll_bytes_per_pix_fraq /= precision;
766
767 DC_LOG_DSC("\tbytes_per_pixel 0x%08x (%d.%07d)",
768 config->bytes_per_pixel, bytes_per_pixel_int, (uint32_t)ll_bytes_per_pix_fraq);
769 DC_LOG_DSC("\tis_pixel_format_444 %d", config->is_pixel_format_444);
770 DC_LOG_DSC("\tslice_width %d", config->slice_width);
771 }
772
dp_set_dsc_on_rx(struct pipe_ctx * pipe_ctx,bool enable)773 static bool dp_set_dsc_on_rx(struct pipe_ctx *pipe_ctx, bool enable)
774 {
775 struct dc *dc = pipe_ctx->stream->ctx->dc;
776 struct dc_stream_state *stream = pipe_ctx->stream;
777 bool result = false;
778
779 if (dc_is_virtual_signal(stream->signal))
780 result = true;
781 else
782 result = dm_helpers_dp_write_dsc_enable(dc->ctx, stream, enable);
783 return result;
784 }
785
dp_set_hblank_reduction_on_rx(struct pipe_ctx * pipe_ctx)786 static bool dp_set_hblank_reduction_on_rx(struct pipe_ctx *pipe_ctx)
787 {
788 struct dc *dc = pipe_ctx->stream->ctx->dc;
789 struct dc_stream_state *stream = pipe_ctx->stream;
790 bool result = false;
791
792 if (dc_is_virtual_signal(stream->signal))
793 result = true;
794 else
795 result = dm_helpers_dp_write_hblank_reduction(dc->ctx, stream);
796 return result;
797 }
798
799
800 /* The stream with these settings can be sent (unblanked) only after DSC was enabled on RX first,
801 * i.e. after dp_enable_dsc_on_rx() had been called
802 */
link_set_dsc_on_stream(struct pipe_ctx * pipe_ctx,bool enable)803 void link_set_dsc_on_stream(struct pipe_ctx *pipe_ctx, bool enable)
804 {
805 /* TODO: Move this to HWSS as this is hardware programming sequence not a
806 * link layer sequence
807 */
808 struct display_stream_compressor *dsc = pipe_ctx->stream_res.dsc;
809 struct dc *dc = pipe_ctx->stream->ctx->dc;
810 struct dc_stream_state *stream = pipe_ctx->stream;
811 struct pipe_ctx *odm_pipe;
812 int opp_cnt = 1;
813 struct dccg *dccg = dc->res_pool->dccg;
814 /* It has been found that when DSCCLK is lower than 16Mhz, we will get DCN
815 * register access hung. When DSCCLk is based on refclk, DSCCLk is always a
816 * fixed value higher than 16Mhz so the issue doesn't occur. When DSCCLK is
817 * generated by DTO, DSCCLK would be based on 1/3 dispclk. For small timings
818 * with DSC such as 480p60Hz, the dispclk could be low enough to trigger
819 * this problem. We are implementing a workaround here to keep using dscclk
820 * based on fixed value refclk when timing is smaller than 3x16Mhz (i.e
821 * 48Mhz) pixel clock to avoid hitting this problem.
822 */
823 bool should_use_dto_dscclk = (dccg->funcs->set_dto_dscclk != NULL) &&
824 stream->timing.pix_clk_100hz > 480000;
825 DC_LOGGER_INIT(dsc->ctx->logger);
826
827 for (odm_pipe = pipe_ctx->next_odm_pipe; odm_pipe; odm_pipe = odm_pipe->next_odm_pipe)
828 opp_cnt++;
829
830 if (enable) {
831 struct dsc_config dsc_cfg;
832 struct dsc_optc_config dsc_optc_cfg = {0};
833 enum optc_dsc_mode optc_dsc_mode;
834
835 /* Enable DSC hw block */
836 dsc_cfg.pic_width = (stream->timing.h_addressable + pipe_ctx->dsc_padding_params.dsc_hactive_padding +
837 stream->timing.h_border_left + stream->timing.h_border_right) / opp_cnt;
838 dsc_cfg.pic_height = stream->timing.v_addressable + stream->timing.v_border_top + stream->timing.v_border_bottom;
839 dsc_cfg.pixel_encoding = stream->timing.pixel_encoding;
840 dsc_cfg.color_depth = stream->timing.display_color_depth;
841 dsc_cfg.is_odm = pipe_ctx->next_odm_pipe ? true : false;
842 dsc_cfg.dc_dsc_cfg = stream->timing.dsc_cfg;
843 ASSERT(dsc_cfg.dc_dsc_cfg.num_slices_h % opp_cnt == 0);
844 dsc_cfg.dc_dsc_cfg.num_slices_h /= opp_cnt;
845 dsc_cfg.dsc_padding = 0;
846
847 if (should_use_dto_dscclk)
848 dccg->funcs->set_dto_dscclk(dccg, dsc->inst, dsc_cfg.dc_dsc_cfg.num_slices_h);
849 dsc->funcs->dsc_set_config(dsc, &dsc_cfg, &dsc_optc_cfg);
850 dsc->funcs->dsc_enable(dsc, pipe_ctx->stream_res.opp->inst);
851 for (odm_pipe = pipe_ctx->next_odm_pipe; odm_pipe; odm_pipe = odm_pipe->next_odm_pipe) {
852 struct display_stream_compressor *odm_dsc = odm_pipe->stream_res.dsc;
853
854 if (should_use_dto_dscclk)
855 dccg->funcs->set_dto_dscclk(dccg, odm_dsc->inst, dsc_cfg.dc_dsc_cfg.num_slices_h);
856 odm_dsc->funcs->dsc_set_config(odm_dsc, &dsc_cfg, &dsc_optc_cfg);
857 odm_dsc->funcs->dsc_enable(odm_dsc, odm_pipe->stream_res.opp->inst);
858 }
859 dsc_cfg.dc_dsc_cfg.num_slices_h *= opp_cnt;
860 dsc_cfg.pic_width *= opp_cnt;
861 dsc_cfg.dsc_padding = pipe_ctx->dsc_padding_params.dsc_hactive_padding;
862
863 optc_dsc_mode = dsc_optc_cfg.is_pixel_format_444 ? OPTC_DSC_ENABLED_444 : OPTC_DSC_ENABLED_NATIVE_SUBSAMPLED;
864
865 /* Enable DSC in encoder */
866 if (dc_is_dp_signal(stream->signal) && !dp_is_128b_132b_signal(pipe_ctx)) {
867 DC_LOG_DSC("Setting stream encoder DSC config for engine %d:", (int)pipe_ctx->stream_res.stream_enc->id);
868 dsc_optc_config_log(dsc, &dsc_optc_cfg);
869 if (pipe_ctx->stream_res.stream_enc->funcs->dp_set_dsc_config)
870 pipe_ctx->stream_res.stream_enc->funcs->dp_set_dsc_config(pipe_ctx->stream_res.stream_enc,
871 optc_dsc_mode,
872 dsc_optc_cfg.bytes_per_pixel,
873 dsc_optc_cfg.slice_width);
874
875 /* PPS SDP is set elsewhere because it has to be done after DIG FE is connected to DIG BE */
876 }
877
878 /* Enable DSC in OPTC */
879 DC_LOG_DSC("Setting optc DSC config for tg instance %d:", pipe_ctx->stream_res.tg->inst);
880 dsc_optc_config_log(dsc, &dsc_optc_cfg);
881 pipe_ctx->stream_res.tg->funcs->set_dsc_config(pipe_ctx->stream_res.tg,
882 optc_dsc_mode,
883 dsc_optc_cfg.bytes_per_pixel,
884 dsc_optc_cfg.slice_width);
885 } else {
886 /* disable DSC in OPTC */
887 pipe_ctx->stream_res.tg->funcs->set_dsc_config(
888 pipe_ctx->stream_res.tg,
889 OPTC_DSC_DISABLED, 0, 0);
890
891 /* disable DSC in stream encoder */
892 if (dc_is_dp_signal(stream->signal)) {
893 if (dp_is_128b_132b_signal(pipe_ctx))
894 pipe_ctx->stream_res.hpo_dp_stream_enc->funcs->dp_set_dsc_pps_info_packet(
895 pipe_ctx->stream_res.hpo_dp_stream_enc,
896 false,
897 NULL,
898 true);
899 else {
900 if (pipe_ctx->stream_res.stream_enc->funcs->dp_set_dsc_config)
901 pipe_ctx->stream_res.stream_enc->funcs->dp_set_dsc_config(
902 pipe_ctx->stream_res.stream_enc,
903 OPTC_DSC_DISABLED, 0, 0);
904 pipe_ctx->stream_res.stream_enc->funcs->dp_set_dsc_pps_info_packet(
905 pipe_ctx->stream_res.stream_enc, false, NULL, true);
906 }
907 }
908
909 /* disable DSC block */
910 for (odm_pipe = pipe_ctx; odm_pipe; odm_pipe = odm_pipe->next_odm_pipe) {
911 odm_pipe->stream_res.dsc->funcs->dsc_disconnect(odm_pipe->stream_res.dsc);
912 /*
913 * TODO - dsc_disconnect is a double buffered register.
914 * by the time we call dsc_disable, dsc may still remain
915 * connected to OPP. In this case OPTC will no longer
916 * get correct pixel data because DSCC is off. However
917 * we also can't wait for the disconnect pending
918 * complete, because this function can be called
919 * with/without OTG master lock acquired. When the lock
920 * is acquired we will never get pending complete until
921 * we release the lock later. So there is no easy way to
922 * solve this problem especially when the lock is
923 * acquired. DSC is a front end hw block it should be
924 * programmed as part of front end sequence, where the
925 * commit sequence without lock and update sequence
926 * with lock are completely separated. However because
927 * we are programming dsc as part of back end link
928 * programming sequence, we don't know if front end OPTC
929 * master lock is acquired. The back end should be
930 * agnostic to front end lock. DSC programming shouldn't
931 * belong to this sequence.
932 */
933 odm_pipe->stream_res.dsc->funcs->dsc_disable(odm_pipe->stream_res.dsc);
934 if (dccg->funcs->set_ref_dscclk)
935 dccg->funcs->set_ref_dscclk(dccg, odm_pipe->stream_res.dsc->inst);
936 }
937 }
938 }
939
940 /*
941 * For dynamic bpp change case, dsc is programmed with MASTER_UPDATE_LOCK enabled;
942 * hence PPS info packet update need to use frame update instead of immediate update.
943 * Added parameter immediate_update for this purpose.
944 * The decision to use frame update is hard-coded in function dp_update_dsc_config(),
945 * which is the only place where a "false" would be passed in for param immediate_update.
946 *
947 * immediate_update is only applicable when DSC is enabled.
948 */
link_set_dsc_pps_packet(struct pipe_ctx * pipe_ctx,bool enable,bool immediate_update)949 bool link_set_dsc_pps_packet(struct pipe_ctx *pipe_ctx, bool enable, bool immediate_update)
950 {
951 struct display_stream_compressor *dsc = pipe_ctx->stream_res.dsc;
952 struct dc_stream_state *stream = pipe_ctx->stream;
953
954 if (!pipe_ctx->stream->timing.flags.DSC)
955 return false;
956
957 if (!dsc)
958 return false;
959
960 DC_LOGGER_INIT(dsc->ctx->logger);
961
962 if (enable) {
963 struct dsc_config dsc_cfg;
964 uint8_t dsc_packed_pps[128];
965
966 memset(&dsc_cfg, 0, sizeof(dsc_cfg));
967 memset(dsc_packed_pps, 0, 128);
968
969 /* Enable DSC hw block */
970 dsc_cfg.pic_width = stream->timing.h_addressable + stream->timing.h_border_left + stream->timing.h_border_right;
971 dsc_cfg.pic_height = stream->timing.v_addressable + stream->timing.v_border_top + stream->timing.v_border_bottom;
972 dsc_cfg.pixel_encoding = stream->timing.pixel_encoding;
973 dsc_cfg.color_depth = stream->timing.display_color_depth;
974 dsc_cfg.is_odm = pipe_ctx->next_odm_pipe ? true : false;
975 dsc_cfg.dc_dsc_cfg = stream->timing.dsc_cfg;
976 dsc_cfg.dsc_padding = pipe_ctx->dsc_padding_params.dsc_hactive_padding;
977
978 dsc->funcs->dsc_get_packed_pps(dsc, &dsc_cfg, &dsc_packed_pps[0]);
979 memcpy(&stream->dsc_packed_pps[0], &dsc_packed_pps[0], sizeof(stream->dsc_packed_pps));
980 if (dc_is_dp_signal(stream->signal)) {
981 DC_LOG_DSC("Setting stream encoder DSC PPS SDP for engine %d\n", (int)pipe_ctx->stream_res.stream_enc->id);
982 if (dp_is_128b_132b_signal(pipe_ctx))
983 pipe_ctx->stream_res.hpo_dp_stream_enc->funcs->dp_set_dsc_pps_info_packet(
984 pipe_ctx->stream_res.hpo_dp_stream_enc,
985 true,
986 &dsc_packed_pps[0],
987 immediate_update);
988 else
989 pipe_ctx->stream_res.stream_enc->funcs->dp_set_dsc_pps_info_packet(
990 pipe_ctx->stream_res.stream_enc,
991 true,
992 &dsc_packed_pps[0],
993 immediate_update);
994 }
995 } else {
996 /* disable DSC PPS in stream encoder */
997 memset(&stream->dsc_packed_pps[0], 0, sizeof(stream->dsc_packed_pps));
998 if (dc_is_dp_signal(stream->signal)) {
999 if (dp_is_128b_132b_signal(pipe_ctx))
1000 pipe_ctx->stream_res.hpo_dp_stream_enc->funcs->dp_set_dsc_pps_info_packet(
1001 pipe_ctx->stream_res.hpo_dp_stream_enc,
1002 false,
1003 NULL,
1004 true);
1005 else
1006 pipe_ctx->stream_res.stream_enc->funcs->dp_set_dsc_pps_info_packet(
1007 pipe_ctx->stream_res.stream_enc, false, NULL, true);
1008 }
1009 }
1010
1011 return true;
1012 }
1013
link_set_dsc_enable(struct pipe_ctx * pipe_ctx,bool enable)1014 bool link_set_dsc_enable(struct pipe_ctx *pipe_ctx, bool enable)
1015 {
1016 struct display_stream_compressor *dsc = pipe_ctx->stream_res.dsc;
1017 bool result = false;
1018
1019 if (!pipe_ctx->stream->timing.flags.DSC)
1020 goto out;
1021 if (!dsc)
1022 goto out;
1023
1024 if (enable) {
1025 {
1026 link_set_dsc_on_stream(pipe_ctx, true);
1027 result = true;
1028 }
1029 } else {
1030 dp_set_dsc_on_rx(pipe_ctx, false);
1031 link_set_dsc_on_stream(pipe_ctx, false);
1032 result = true;
1033 }
1034 out:
1035 return result;
1036 }
1037
link_update_dsc_config(struct pipe_ctx * pipe_ctx)1038 bool link_update_dsc_config(struct pipe_ctx *pipe_ctx)
1039 {
1040 struct display_stream_compressor *dsc = pipe_ctx->stream_res.dsc;
1041
1042 if (!pipe_ctx->stream->timing.flags.DSC)
1043 return false;
1044 if (!dsc)
1045 return false;
1046
1047 link_set_dsc_on_stream(pipe_ctx, true);
1048 link_set_dsc_pps_packet(pipe_ctx, true, false);
1049 return true;
1050 }
1051
enable_stream_features(struct pipe_ctx * pipe_ctx)1052 static void enable_stream_features(struct pipe_ctx *pipe_ctx)
1053 {
1054 struct dc_stream_state *stream = pipe_ctx->stream;
1055
1056 if (pipe_ctx->stream->signal != SIGNAL_TYPE_DISPLAY_PORT_MST) {
1057 struct dc_link *link = stream->link;
1058 union down_spread_ctrl old_downspread;
1059 union down_spread_ctrl new_downspread;
1060
1061 memset(&old_downspread, 0, sizeof(old_downspread));
1062
1063 core_link_read_dpcd(link, DP_DOWNSPREAD_CTRL,
1064 &old_downspread.raw, sizeof(old_downspread));
1065
1066 new_downspread.raw = old_downspread.raw;
1067
1068 new_downspread.bits.IGNORE_MSA_TIMING_PARAM =
1069 (stream->ignore_msa_timing_param) ? 1 : 0;
1070
1071 if (new_downspread.raw != old_downspread.raw) {
1072 core_link_write_dpcd(link, DP_DOWNSPREAD_CTRL,
1073 &new_downspread.raw, sizeof(new_downspread));
1074 }
1075
1076 } else {
1077 dm_helpers_mst_enable_stream_features(stream);
1078 }
1079 }
1080
log_vcp_x_y(const struct dc_link * link,struct fixed31_32 avg_time_slots_per_mtp)1081 static void log_vcp_x_y(const struct dc_link *link, struct fixed31_32 avg_time_slots_per_mtp)
1082 {
1083 const uint32_t VCP_Y_PRECISION = 1000;
1084 uint64_t vcp_x, vcp_y;
1085 DC_LOGGER_INIT(link->ctx->logger);
1086
1087 // Add 0.5*(1/VCP_Y_PRECISION) to round up to decimal precision
1088 avg_time_slots_per_mtp = dc_fixpt_add(
1089 avg_time_slots_per_mtp,
1090 dc_fixpt_from_fraction(
1091 1,
1092 2*VCP_Y_PRECISION));
1093
1094 vcp_x = dc_fixpt_floor(
1095 avg_time_slots_per_mtp);
1096 vcp_y = dc_fixpt_floor(
1097 dc_fixpt_mul_int(
1098 dc_fixpt_sub_int(
1099 avg_time_slots_per_mtp,
1100 dc_fixpt_floor(
1101 avg_time_slots_per_mtp)),
1102 VCP_Y_PRECISION));
1103
1104
1105 if (link->type == dc_connection_mst_branch)
1106 DC_LOG_DP2("MST Update Payload: set_throttled_vcp_size slot X.Y for MST stream "
1107 "X: %llu "
1108 "Y: %llu/%d",
1109 vcp_x,
1110 vcp_y,
1111 VCP_Y_PRECISION);
1112 else
1113 DC_LOG_DP2("SST Update Payload: set_throttled_vcp_size slot X.Y for SST stream "
1114 "X: %llu "
1115 "Y: %llu/%d",
1116 vcp_x,
1117 vcp_y,
1118 VCP_Y_PRECISION);
1119 }
1120
get_pbn_per_slot(struct dc_stream_state * stream)1121 static struct fixed31_32 get_pbn_per_slot(struct dc_stream_state *stream)
1122 {
1123 struct fixed31_32 mbytes_per_sec;
1124 uint32_t link_rate_in_mbytes_per_sec = dp_link_bandwidth_kbps(stream->link,
1125 &stream->link->cur_link_settings);
1126 link_rate_in_mbytes_per_sec /= 8000; /* Kbits to MBytes */
1127
1128 mbytes_per_sec = dc_fixpt_from_int(link_rate_in_mbytes_per_sec);
1129
1130 return dc_fixpt_div_int(mbytes_per_sec, 54);
1131 }
1132
get_pbn_from_bw_in_kbps(uint64_t kbps)1133 static struct fixed31_32 get_pbn_from_bw_in_kbps(uint64_t kbps)
1134 {
1135 struct fixed31_32 peak_kbps;
1136 uint32_t numerator = 0;
1137 uint32_t denominator = 1;
1138
1139 /*
1140 * The 1.006 factor (margin 5300ppm + 300ppm ~ 0.6% as per spec) is not
1141 * required when determining PBN/time slot utilization on the link between
1142 * us and the branch, since that overhead is already accounted for in
1143 * the get_pbn_per_slot function.
1144 *
1145 * The unit of 54/64Mbytes/sec is an arbitrary unit chosen based on
1146 * common multiplier to render an integer PBN for all link rate/lane
1147 * counts combinations
1148 * calculate
1149 * peak_kbps *= (64/54)
1150 * peak_kbps /= (8 * 1000) convert to bytes
1151 */
1152
1153 numerator = 64;
1154 denominator = 54 * 8 * 1000;
1155 kbps *= numerator;
1156 peak_kbps = dc_fixpt_from_fraction(kbps, denominator);
1157
1158 return peak_kbps;
1159 }
1160
get_pbn_from_timing(struct pipe_ctx * pipe_ctx)1161 static struct fixed31_32 get_pbn_from_timing(struct pipe_ctx *pipe_ctx)
1162 {
1163 uint64_t kbps;
1164 enum dc_link_encoding_format link_encoding;
1165
1166 if (dp_is_128b_132b_signal(pipe_ctx))
1167 link_encoding = DC_LINK_ENCODING_DP_128b_132b;
1168 else
1169 link_encoding = DC_LINK_ENCODING_DP_8b_10b;
1170
1171 kbps = dc_bandwidth_in_kbps_from_timing(&pipe_ctx->stream->timing, link_encoding);
1172 return get_pbn_from_bw_in_kbps(kbps);
1173 }
1174
1175
1176 // TODO - DP2.0 Link: Fix get_lane_status to handle LTTPR offset (SST and MST)
get_lane_status(struct dc_link * link,uint32_t lane_count,union lane_status * status,union lane_align_status_updated * status_updated)1177 static void get_lane_status(
1178 struct dc_link *link,
1179 uint32_t lane_count,
1180 union lane_status *status,
1181 union lane_align_status_updated *status_updated)
1182 {
1183 unsigned int lane;
1184 uint8_t dpcd_buf[3] = {0};
1185
1186 if (status == NULL || status_updated == NULL) {
1187 return;
1188 }
1189
1190 core_link_read_dpcd(
1191 link,
1192 DP_LANE0_1_STATUS,
1193 dpcd_buf,
1194 sizeof(dpcd_buf));
1195
1196 for (lane = 0; lane < lane_count; lane++) {
1197 status[lane].raw = dp_get_nibble_at_index(&dpcd_buf[0], lane);
1198 }
1199
1200 status_updated->raw = dpcd_buf[2];
1201 }
1202
poll_for_allocation_change_trigger(struct dc_link * link)1203 static bool poll_for_allocation_change_trigger(struct dc_link *link)
1204 {
1205 /*
1206 * wait for ACT handled
1207 */
1208 int i;
1209 const int act_retries = 30;
1210 enum act_return_status result = ACT_FAILED;
1211 enum dc_connection_type display_connected = (link->type != dc_connection_none);
1212 union payload_table_update_status update_status = {0};
1213 union lane_status dpcd_lane_status[LANE_COUNT_DP_MAX];
1214 union lane_align_status_updated lane_status_updated;
1215 DC_LOGGER_INIT(link->ctx->logger);
1216
1217 if (!display_connected || link->aux_access_disabled)
1218 return true;
1219 for (i = 0; i < act_retries; i++) {
1220 get_lane_status(link, link->cur_link_settings.lane_count, dpcd_lane_status, &lane_status_updated);
1221
1222 if (!dp_is_cr_done(link->cur_link_settings.lane_count, dpcd_lane_status) ||
1223 !dp_is_ch_eq_done(link->cur_link_settings.lane_count, dpcd_lane_status) ||
1224 !dp_is_symbol_locked(link->cur_link_settings.lane_count, dpcd_lane_status) ||
1225 !dp_is_interlane_aligned(lane_status_updated)) {
1226 DC_LOG_ERROR("SST Update Payload: Link loss occurred while "
1227 "polling for ACT handled.");
1228 result = ACT_LINK_LOST;
1229 break;
1230 }
1231 core_link_read_dpcd(
1232 link,
1233 DP_PAYLOAD_TABLE_UPDATE_STATUS,
1234 &update_status.raw,
1235 1);
1236
1237 if (update_status.bits.ACT_HANDLED == 1) {
1238 DC_LOG_DP2("SST Update Payload: ACT handled by downstream.");
1239 result = ACT_SUCCESS;
1240 break;
1241 }
1242
1243 fsleep(5000);
1244 }
1245
1246 if (result == ACT_FAILED) {
1247 DC_LOG_ERROR("SST Update Payload: ACT still not handled after retries, "
1248 "continue on. Something is wrong with the branch.");
1249 }
1250
1251 return (result == ACT_SUCCESS);
1252 }
1253
update_mst_stream_alloc_table(struct dc_link * link,struct stream_encoder * stream_enc,struct hpo_dp_stream_encoder * hpo_dp_stream_enc,const struct dc_dp_mst_stream_allocation_table * proposed_table)1254 static void update_mst_stream_alloc_table(
1255 struct dc_link *link,
1256 struct stream_encoder *stream_enc,
1257 struct hpo_dp_stream_encoder *hpo_dp_stream_enc, // TODO: Rename stream_enc to dio_stream_enc?
1258 const struct dc_dp_mst_stream_allocation_table *proposed_table)
1259 {
1260 struct link_mst_stream_allocation work_table[MAX_CONTROLLER_NUM] = { 0 };
1261 struct link_mst_stream_allocation *dc_alloc;
1262
1263 int i;
1264 int j;
1265
1266 /* if DRM proposed_table has more than one new payload */
1267 ASSERT(proposed_table->stream_count -
1268 link->mst_stream_alloc_table.stream_count < 2);
1269
1270 /* copy proposed_table to link, add stream encoder */
1271 for (i = 0; i < proposed_table->stream_count; i++) {
1272
1273 for (j = 0; j < link->mst_stream_alloc_table.stream_count; j++) {
1274 dc_alloc =
1275 &link->mst_stream_alloc_table.stream_allocations[j];
1276
1277 if (dc_alloc->vcp_id ==
1278 proposed_table->stream_allocations[i].vcp_id) {
1279
1280 work_table[i] = *dc_alloc;
1281 work_table[i].slot_count = proposed_table->stream_allocations[i].slot_count;
1282 break; /* exit j loop */
1283 }
1284 }
1285
1286 /* new vcp_id */
1287 if (j == link->mst_stream_alloc_table.stream_count) {
1288 work_table[i].vcp_id =
1289 proposed_table->stream_allocations[i].vcp_id;
1290 work_table[i].slot_count =
1291 proposed_table->stream_allocations[i].slot_count;
1292 work_table[i].stream_enc = stream_enc;
1293 work_table[i].hpo_dp_stream_enc = hpo_dp_stream_enc;
1294 }
1295 }
1296
1297 /* update link->mst_stream_alloc_table with work_table */
1298 link->mst_stream_alloc_table.stream_count =
1299 proposed_table->stream_count;
1300 for (i = 0; i < MAX_CONTROLLER_NUM; i++)
1301 link->mst_stream_alloc_table.stream_allocations[i] =
1302 work_table[i];
1303 }
1304
remove_stream_from_alloc_table(struct dc_link * link,struct stream_encoder * dio_stream_enc,struct hpo_dp_stream_encoder * hpo_dp_stream_enc)1305 static void remove_stream_from_alloc_table(
1306 struct dc_link *link,
1307 struct stream_encoder *dio_stream_enc,
1308 struct hpo_dp_stream_encoder *hpo_dp_stream_enc)
1309 {
1310 int i = 0;
1311 struct link_mst_stream_allocation_table *table =
1312 &link->mst_stream_alloc_table;
1313
1314 if (hpo_dp_stream_enc) {
1315 for (; i < table->stream_count; i++)
1316 if (hpo_dp_stream_enc == table->stream_allocations[i].hpo_dp_stream_enc)
1317 break;
1318 } else {
1319 for (; i < table->stream_count; i++)
1320 if (dio_stream_enc == table->stream_allocations[i].stream_enc)
1321 break;
1322 }
1323
1324 if (i < table->stream_count) {
1325 i++;
1326 for (; i < table->stream_count; i++)
1327 table->stream_allocations[i-1] = table->stream_allocations[i];
1328 memset(&table->stream_allocations[table->stream_count-1], 0,
1329 sizeof(struct link_mst_stream_allocation));
1330 table->stream_count--;
1331 }
1332 }
1333
print_mst_streams(struct dc_link * link)1334 static void print_mst_streams(struct dc_link *link)
1335 {
1336 int i;
1337
1338 DC_LOGGER_INIT(link->ctx->logger);
1339
1340 DC_LOG_MST("%s stream_count: %d:\n",
1341 __func__,
1342 link->mst_stream_alloc_table.stream_count);
1343
1344 for (i = 0; i < MAX_CONTROLLER_NUM; i++) {
1345 DC_LOG_MST("stream_enc[%d]: %p\n", i,
1346 (void *) link->mst_stream_alloc_table.stream_allocations[i].stream_enc);
1347 DC_LOG_MST("stream[%d].hpo_dp_stream_enc: %p\n", i,
1348 (void *) link->mst_stream_alloc_table.stream_allocations[i].hpo_dp_stream_enc);
1349 DC_LOG_MST("stream[%d].vcp_id: %d\n", i,
1350 link->mst_stream_alloc_table.stream_allocations[i].vcp_id);
1351 DC_LOG_MST("stream[%d].slot_count: %d\n", i,
1352 link->mst_stream_alloc_table.stream_allocations[i].slot_count);
1353 }
1354 }
1355
deallocate_mst_payload(struct pipe_ctx * pipe_ctx)1356 static enum dc_status deallocate_mst_payload(struct pipe_ctx *pipe_ctx)
1357 {
1358 struct dc_stream_state *stream = pipe_ctx->stream;
1359 struct dc_link *link = stream->link;
1360 struct dc_dp_mst_stream_allocation_table proposed_table = {0};
1361 struct fixed31_32 avg_time_slots_per_mtp = dc_fixpt_from_int(0);
1362 bool mst_mode = (link->type == dc_connection_mst_branch);
1363 const struct link_hwss *link_hwss = get_link_hwss(link, &pipe_ctx->link_res);
1364 const struct dc_link_settings empty_link_settings = {0};
1365 DC_LOGGER_INIT(link->ctx->logger);
1366
1367 /* deallocate_mst_payload is called before disable link. When mode or
1368 * disable/enable monitor, new stream is created which is not in link
1369 * stream[] yet. For this, payload is not allocated yet, so de-alloc
1370 * should not done. For new mode set, map_resources will get engine
1371 * for new stream, so stream_enc->id should be validated until here.
1372 */
1373
1374 /* slot X.Y */
1375 if (link_hwss->ext.set_throttled_vcp_size)
1376 link_hwss->ext.set_throttled_vcp_size(pipe_ctx, avg_time_slots_per_mtp);
1377 if (link_hwss->ext.set_hblank_min_symbol_width)
1378 link_hwss->ext.set_hblank_min_symbol_width(pipe_ctx,
1379 &empty_link_settings,
1380 avg_time_slots_per_mtp);
1381
1382 if (mst_mode) {
1383 /* when link is in mst mode, reply on mst manager to remove
1384 * payload
1385 */
1386 if (dm_helpers_dp_mst_write_payload_allocation_table(
1387 stream->ctx,
1388 stream,
1389 &proposed_table,
1390 false))
1391 update_mst_stream_alloc_table(
1392 link,
1393 pipe_ctx->stream_res.stream_enc,
1394 pipe_ctx->stream_res.hpo_dp_stream_enc,
1395 &proposed_table);
1396 else
1397 DC_LOG_WARNING("Failed to update MST allocation table for idx %d\n",
1398 pipe_ctx->pipe_idx);
1399 } else {
1400 /* when link is no longer in mst mode (mst hub unplugged),
1401 * remove payload with default dc logic
1402 */
1403 remove_stream_from_alloc_table(link, pipe_ctx->stream_res.stream_enc,
1404 pipe_ctx->stream_res.hpo_dp_stream_enc);
1405 }
1406
1407 print_mst_streams(link);
1408
1409 /* update mst stream allocation table hardware state */
1410 if (link_hwss->ext.update_stream_allocation_table == NULL ||
1411 link_dp_get_encoding_format(&link->cur_link_settings) == DP_UNKNOWN_ENCODING) {
1412 DC_LOG_DEBUG("Unknown encoding format\n");
1413 return DC_ERROR_UNEXPECTED;
1414 }
1415
1416 link_hwss->ext.update_stream_allocation_table(link, &pipe_ctx->link_res,
1417 &link->mst_stream_alloc_table);
1418
1419 if (mst_mode)
1420 dm_helpers_dp_mst_poll_for_allocation_change_trigger(
1421 stream->ctx,
1422 stream);
1423
1424 dm_helpers_dp_mst_update_mst_mgr_for_deallocation(
1425 stream->ctx,
1426 stream);
1427
1428 return DC_OK;
1429 }
1430
1431 /* convert link_mst_stream_alloc_table to dm dp_mst_stream_alloc_table
1432 * because stream_encoder is not exposed to dm
1433 */
allocate_mst_payload(struct pipe_ctx * pipe_ctx)1434 static enum dc_status allocate_mst_payload(struct pipe_ctx *pipe_ctx)
1435 {
1436 struct dc_stream_state *stream = pipe_ctx->stream;
1437 struct dc_link *link = stream->link;
1438 struct dc_dp_mst_stream_allocation_table proposed_table = {0};
1439 struct fixed31_32 avg_time_slots_per_mtp;
1440 struct fixed31_32 pbn;
1441 struct fixed31_32 pbn_per_slot;
1442 enum act_return_status ret;
1443 const struct link_hwss *link_hwss = get_link_hwss(link, &pipe_ctx->link_res);
1444 DC_LOGGER_INIT(link->ctx->logger);
1445
1446 /* enable_link_dp_mst already check link->enabled_stream_count
1447 * and stream is in link->stream[]. This is called during set mode,
1448 * stream_enc is available.
1449 */
1450
1451 /* get calculate VC payload for stream: stream_alloc */
1452 if (dm_helpers_dp_mst_write_payload_allocation_table(
1453 stream->ctx,
1454 stream,
1455 &proposed_table,
1456 true))
1457 update_mst_stream_alloc_table(
1458 link,
1459 pipe_ctx->stream_res.stream_enc,
1460 pipe_ctx->stream_res.hpo_dp_stream_enc,
1461 &proposed_table);
1462 else
1463 DC_LOG_WARNING("Failed to update MST allocation table for idx %d\n",
1464 pipe_ctx->pipe_idx);
1465
1466 print_mst_streams(link);
1467
1468 ASSERT(proposed_table.stream_count > 0);
1469
1470 /* program DP source TX for payload */
1471 if (link_hwss->ext.update_stream_allocation_table == NULL ||
1472 link_dp_get_encoding_format(&link->cur_link_settings) == DP_UNKNOWN_ENCODING) {
1473 DC_LOG_ERROR("Failure: unknown encoding format\n");
1474 return DC_ERROR_UNEXPECTED;
1475 }
1476
1477 link_hwss->ext.update_stream_allocation_table(link,
1478 &pipe_ctx->link_res,
1479 &link->mst_stream_alloc_table);
1480
1481 /* send down message */
1482 ret = dm_helpers_dp_mst_poll_for_allocation_change_trigger(
1483 stream->ctx,
1484 stream);
1485
1486 if (ret != ACT_LINK_LOST)
1487 dm_helpers_dp_mst_send_payload_allocation(
1488 stream->ctx,
1489 stream);
1490
1491 /* slot X.Y for only current stream */
1492 pbn_per_slot = get_pbn_per_slot(stream);
1493 if (pbn_per_slot.value == 0) {
1494 DC_LOG_ERROR("Failure: pbn_per_slot==0 not allowed. Cannot continue, returning DC_UNSUPPORTED_VALUE.\n");
1495 return DC_UNSUPPORTED_VALUE;
1496 }
1497 pbn = get_pbn_from_timing(pipe_ctx);
1498 avg_time_slots_per_mtp = dc_fixpt_div(pbn, pbn_per_slot);
1499
1500 log_vcp_x_y(link, avg_time_slots_per_mtp);
1501
1502 if (link_hwss->ext.set_throttled_vcp_size)
1503 link_hwss->ext.set_throttled_vcp_size(pipe_ctx, avg_time_slots_per_mtp);
1504 if (link_hwss->ext.set_hblank_min_symbol_width)
1505 link_hwss->ext.set_hblank_min_symbol_width(pipe_ctx,
1506 &link->cur_link_settings,
1507 avg_time_slots_per_mtp);
1508
1509 return DC_OK;
1510 }
1511
link_calculate_sst_avg_time_slots_per_mtp(const struct dc_stream_state * stream,const struct dc_link * link)1512 struct fixed31_32 link_calculate_sst_avg_time_slots_per_mtp(
1513 const struct dc_stream_state *stream,
1514 const struct dc_link *link)
1515 {
1516 struct fixed31_32 link_bw_effective =
1517 dc_fixpt_from_int(
1518 dp_link_bandwidth_kbps(link, &link->cur_link_settings));
1519 struct fixed31_32 timeslot_bw_effective =
1520 dc_fixpt_div_int(link_bw_effective, MAX_MTP_SLOT_COUNT);
1521 struct fixed31_32 timing_bw =
1522 dc_fixpt_from_int(
1523 dc_bandwidth_in_kbps_from_timing(&stream->timing,
1524 dc_link_get_highest_encoding_format(link)));
1525 struct fixed31_32 avg_time_slots_per_mtp =
1526 dc_fixpt_div(timing_bw, timeslot_bw_effective);
1527
1528 return avg_time_slots_per_mtp;
1529 }
1530
1531
write_128b_132b_sst_payload_allocation_table(const struct dc_stream_state * stream,struct dc_link * link,struct link_mst_stream_allocation_table * proposed_table,bool allocate)1532 static bool write_128b_132b_sst_payload_allocation_table(
1533 const struct dc_stream_state *stream,
1534 struct dc_link *link,
1535 struct link_mst_stream_allocation_table *proposed_table,
1536 bool allocate)
1537 {
1538 const uint8_t vc_id = 1; /// VC ID always 1 for SST
1539 const uint8_t start_time_slot = 0; /// Always start at time slot 0 for SST
1540 bool result = false;
1541 uint8_t req_slot_count = 0;
1542 struct fixed31_32 avg_time_slots_per_mtp = { 0 };
1543 union payload_table_update_status update_status = { 0 };
1544 const uint32_t max_retries = 30;
1545 uint32_t retries = 0;
1546 enum dc_connection_type display_connected = (link->type != dc_connection_none);
1547 DC_LOGGER_INIT(link->ctx->logger);
1548
1549 if (allocate) {
1550 avg_time_slots_per_mtp = link_calculate_sst_avg_time_slots_per_mtp(stream, link);
1551 req_slot_count = dc_fixpt_ceil(avg_time_slots_per_mtp);
1552 /// Validation should filter out modes that exceed link BW
1553 ASSERT(req_slot_count <= MAX_MTP_SLOT_COUNT);
1554 if (req_slot_count > MAX_MTP_SLOT_COUNT)
1555 return false;
1556 } else {
1557 /// Leave req_slot_count = 0 if allocate is false.
1558 }
1559
1560 proposed_table->stream_count = 1; /// Always 1 stream for SST
1561 proposed_table->stream_allocations[0].slot_count = req_slot_count;
1562 proposed_table->stream_allocations[0].vcp_id = vc_id;
1563
1564 if (!display_connected || link->aux_access_disabled)
1565 return true;
1566
1567 /// Write DPCD 2C0 = 1 to start updating
1568 update_status.bits.VC_PAYLOAD_TABLE_UPDATED = 1;
1569 core_link_write_dpcd(
1570 link,
1571 DP_PAYLOAD_TABLE_UPDATE_STATUS,
1572 &update_status.raw,
1573 1);
1574
1575 /// Program the changes in DPCD 1C0 - 1C2
1576 ASSERT(vc_id == 1);
1577 core_link_write_dpcd(
1578 link,
1579 DP_PAYLOAD_ALLOCATE_SET,
1580 &vc_id,
1581 1);
1582
1583 ASSERT(start_time_slot == 0);
1584 core_link_write_dpcd(
1585 link,
1586 DP_PAYLOAD_ALLOCATE_START_TIME_SLOT,
1587 &start_time_slot,
1588 1);
1589
1590 core_link_write_dpcd(
1591 link,
1592 DP_PAYLOAD_ALLOCATE_TIME_SLOT_COUNT,
1593 &req_slot_count,
1594 1);
1595
1596 /// Poll till DPCD 2C0 read 1
1597 /// Try for at least 150ms (30 retries, with 5ms delay after each attempt)
1598
1599 while (retries < max_retries) {
1600 if (core_link_read_dpcd(
1601 link,
1602 DP_PAYLOAD_TABLE_UPDATE_STATUS,
1603 &update_status.raw,
1604 1) == DC_OK) {
1605 if (update_status.bits.VC_PAYLOAD_TABLE_UPDATED == 1) {
1606 DC_LOG_DP2("SST Update Payload: downstream payload table updated.");
1607 result = true;
1608 break;
1609 }
1610 } else {
1611 union dpcd_rev dpcdRev = {0};
1612
1613 if (core_link_read_dpcd(
1614 link,
1615 DP_DPCD_REV,
1616 &dpcdRev.raw,
1617 1) != DC_OK) {
1618 DC_LOG_ERROR("SST Update Payload: Unable to read DPCD revision "
1619 "of sink while polling payload table "
1620 "updated status bit.");
1621 break;
1622 }
1623 }
1624 retries++;
1625 fsleep(5000);
1626 }
1627
1628 if (!result && retries == max_retries) {
1629 DC_LOG_ERROR("SST Update Payload: Payload table not updated after retries, "
1630 "continue on. Something is wrong with the branch.");
1631 // TODO - DP2.0 Payload: Read and log the payload table from downstream branch
1632 }
1633
1634 return result;
1635 }
1636
1637 /*
1638 * Payload allocation/deallocation for SST introduced in DP2.0
1639 */
update_sst_payload(struct pipe_ctx * pipe_ctx,bool allocate)1640 static enum dc_status update_sst_payload(struct pipe_ctx *pipe_ctx,
1641 bool allocate)
1642 {
1643 struct dc_stream_state *stream = pipe_ctx->stream;
1644 struct dc_link *link = stream->link;
1645 struct link_mst_stream_allocation_table proposed_table = {0};
1646 struct fixed31_32 avg_time_slots_per_mtp;
1647 const struct dc_link_settings empty_link_settings = {0};
1648 const struct link_hwss *link_hwss = get_link_hwss(link, &pipe_ctx->link_res);
1649 DC_LOGGER_INIT(link->ctx->logger);
1650
1651 /* slot X.Y for SST payload deallocate */
1652 if (!allocate) {
1653 avg_time_slots_per_mtp = dc_fixpt_from_int(0);
1654
1655 log_vcp_x_y(link, avg_time_slots_per_mtp);
1656
1657 if (link_hwss->ext.set_throttled_vcp_size)
1658 link_hwss->ext.set_throttled_vcp_size(pipe_ctx,
1659 avg_time_slots_per_mtp);
1660 if (link_hwss->ext.set_hblank_min_symbol_width)
1661 link_hwss->ext.set_hblank_min_symbol_width(pipe_ctx,
1662 &empty_link_settings,
1663 avg_time_slots_per_mtp);
1664 }
1665
1666 /* calculate VC payload and update branch with new payload allocation table*/
1667 if (!write_128b_132b_sst_payload_allocation_table(
1668 stream,
1669 link,
1670 &proposed_table,
1671 allocate)) {
1672 DC_LOG_ERROR("SST Update Payload: Failed to update "
1673 "allocation table for "
1674 "pipe idx: %d\n",
1675 pipe_ctx->pipe_idx);
1676 return DC_FAIL_DP_PAYLOAD_ALLOCATION;
1677 }
1678
1679 proposed_table.stream_allocations[0].hpo_dp_stream_enc = pipe_ctx->stream_res.hpo_dp_stream_enc;
1680
1681 ASSERT(proposed_table.stream_count == 1);
1682
1683 //TODO - DP2.0 Logging: Instead of hpo_dp_stream_enc pointer, log instance id
1684 DC_LOG_DP2("SST Update Payload: hpo_dp_stream_enc: %p "
1685 "vcp_id: %d "
1686 "slot_count: %d\n",
1687 (void *) proposed_table.stream_allocations[0].hpo_dp_stream_enc,
1688 proposed_table.stream_allocations[0].vcp_id,
1689 proposed_table.stream_allocations[0].slot_count);
1690
1691 /* program DP source TX for payload */
1692 link_hwss->ext.update_stream_allocation_table(link, &pipe_ctx->link_res,
1693 &proposed_table);
1694
1695 /* poll for ACT handled */
1696 if (!poll_for_allocation_change_trigger(link)) {
1697 // Failures will result in blackscreen and errors logged
1698 BREAK_TO_DEBUGGER();
1699 }
1700
1701 /* slot X.Y for SST payload allocate */
1702 if (allocate && link_dp_get_encoding_format(&link->cur_link_settings) ==
1703 DP_128b_132b_ENCODING) {
1704 avg_time_slots_per_mtp = link_calculate_sst_avg_time_slots_per_mtp(stream, link);
1705
1706 log_vcp_x_y(link, avg_time_slots_per_mtp);
1707
1708 if (link_hwss->ext.set_throttled_vcp_size)
1709 link_hwss->ext.set_throttled_vcp_size(pipe_ctx,
1710 avg_time_slots_per_mtp);
1711 if (link_hwss->ext.set_hblank_min_symbol_width)
1712 link_hwss->ext.set_hblank_min_symbol_width(pipe_ctx,
1713 &link->cur_link_settings,
1714 avg_time_slots_per_mtp);
1715 }
1716
1717 /* Always return DC_OK.
1718 * If part of sequence fails, log failure(s) and show blackscreen
1719 */
1720 return DC_OK;
1721 }
1722
link_reduce_mst_payload(struct pipe_ctx * pipe_ctx,uint32_t bw_in_kbps)1723 enum dc_status link_reduce_mst_payload(struct pipe_ctx *pipe_ctx, uint32_t bw_in_kbps)
1724 {
1725 struct dc_stream_state *stream = pipe_ctx->stream;
1726 struct dc_link *link = stream->link;
1727 struct fixed31_32 avg_time_slots_per_mtp;
1728 struct fixed31_32 pbn;
1729 struct fixed31_32 pbn_per_slot;
1730 struct dc_dp_mst_stream_allocation_table proposed_table = {0};
1731 const struct link_hwss *link_hwss = get_link_hwss(link, &pipe_ctx->link_res);
1732 DC_LOGGER_INIT(link->ctx->logger);
1733
1734 /* decrease throttled vcp size */
1735 pbn_per_slot = get_pbn_per_slot(stream);
1736 pbn = get_pbn_from_bw_in_kbps(bw_in_kbps);
1737 avg_time_slots_per_mtp = dc_fixpt_div(pbn, pbn_per_slot);
1738
1739 if (link_hwss->ext.set_throttled_vcp_size)
1740 link_hwss->ext.set_throttled_vcp_size(pipe_ctx, avg_time_slots_per_mtp);
1741 if (link_hwss->ext.set_hblank_min_symbol_width)
1742 link_hwss->ext.set_hblank_min_symbol_width(pipe_ctx,
1743 &link->cur_link_settings,
1744 avg_time_slots_per_mtp);
1745
1746 /* send ALLOCATE_PAYLOAD sideband message with updated pbn */
1747 dm_helpers_dp_mst_send_payload_allocation(
1748 stream->ctx,
1749 stream);
1750
1751 /* notify immediate branch device table update */
1752 if (dm_helpers_dp_mst_write_payload_allocation_table(
1753 stream->ctx,
1754 stream,
1755 &proposed_table,
1756 true)) {
1757 /* update mst stream allocation table software state */
1758 update_mst_stream_alloc_table(
1759 link,
1760 pipe_ctx->stream_res.stream_enc,
1761 pipe_ctx->stream_res.hpo_dp_stream_enc,
1762 &proposed_table);
1763 } else {
1764 DC_LOG_WARNING("Failed to update MST allocation table for idx %d\n",
1765 pipe_ctx->pipe_idx);
1766 }
1767
1768 print_mst_streams(link);
1769
1770 ASSERT(proposed_table.stream_count > 0);
1771
1772 /* update mst stream allocation table hardware state */
1773 if (link_hwss->ext.update_stream_allocation_table == NULL ||
1774 link_dp_get_encoding_format(&link->cur_link_settings) == DP_UNKNOWN_ENCODING) {
1775 DC_LOG_ERROR("Failure: unknown encoding format\n");
1776 return DC_ERROR_UNEXPECTED;
1777 }
1778
1779 link_hwss->ext.update_stream_allocation_table(link, &pipe_ctx->link_res,
1780 &link->mst_stream_alloc_table);
1781
1782 /* poll for immediate branch device ACT handled */
1783 dm_helpers_dp_mst_poll_for_allocation_change_trigger(
1784 stream->ctx,
1785 stream);
1786
1787 return DC_OK;
1788 }
1789
link_increase_mst_payload(struct pipe_ctx * pipe_ctx,uint32_t bw_in_kbps)1790 enum dc_status link_increase_mst_payload(struct pipe_ctx *pipe_ctx, uint32_t bw_in_kbps)
1791 {
1792 struct dc_stream_state *stream = pipe_ctx->stream;
1793 struct dc_link *link = stream->link;
1794 struct fixed31_32 avg_time_slots_per_mtp;
1795 struct fixed31_32 pbn;
1796 struct fixed31_32 pbn_per_slot;
1797 struct dc_dp_mst_stream_allocation_table proposed_table = {0};
1798 enum act_return_status ret;
1799 const struct link_hwss *link_hwss = get_link_hwss(link, &pipe_ctx->link_res);
1800 DC_LOGGER_INIT(link->ctx->logger);
1801
1802 /* notify immediate branch device table update */
1803 if (dm_helpers_dp_mst_write_payload_allocation_table(
1804 stream->ctx,
1805 stream,
1806 &proposed_table,
1807 true)) {
1808 /* update mst stream allocation table software state */
1809 update_mst_stream_alloc_table(
1810 link,
1811 pipe_ctx->stream_res.stream_enc,
1812 pipe_ctx->stream_res.hpo_dp_stream_enc,
1813 &proposed_table);
1814 }
1815
1816 print_mst_streams(link);
1817
1818 ASSERT(proposed_table.stream_count > 0);
1819
1820 /* update mst stream allocation table hardware state */
1821 if (link_hwss->ext.update_stream_allocation_table == NULL ||
1822 link_dp_get_encoding_format(&link->cur_link_settings) == DP_UNKNOWN_ENCODING) {
1823 DC_LOG_ERROR("Failure: unknown encoding format\n");
1824 return DC_ERROR_UNEXPECTED;
1825 }
1826
1827 link_hwss->ext.update_stream_allocation_table(link, &pipe_ctx->link_res,
1828 &link->mst_stream_alloc_table);
1829
1830 /* poll for immediate branch device ACT handled */
1831 ret = dm_helpers_dp_mst_poll_for_allocation_change_trigger(
1832 stream->ctx,
1833 stream);
1834
1835 if (ret != ACT_LINK_LOST) {
1836 /* send ALLOCATE_PAYLOAD sideband message with updated pbn */
1837 dm_helpers_dp_mst_send_payload_allocation(
1838 stream->ctx,
1839 stream);
1840 }
1841
1842 /* increase throttled vcp size */
1843 pbn = get_pbn_from_bw_in_kbps(bw_in_kbps);
1844 pbn_per_slot = get_pbn_per_slot(stream);
1845 avg_time_slots_per_mtp = dc_fixpt_div(pbn, pbn_per_slot);
1846
1847 if (link_hwss->ext.set_throttled_vcp_size)
1848 link_hwss->ext.set_throttled_vcp_size(pipe_ctx, avg_time_slots_per_mtp);
1849 if (link_hwss->ext.set_hblank_min_symbol_width)
1850 link_hwss->ext.set_hblank_min_symbol_width(pipe_ctx,
1851 &link->cur_link_settings,
1852 avg_time_slots_per_mtp);
1853
1854 return DC_OK;
1855 }
1856
disable_link_dp(struct dc_link * link,const struct link_resource * link_res,enum signal_type signal)1857 static void disable_link_dp(struct dc_link *link,
1858 const struct link_resource *link_res,
1859 enum signal_type signal)
1860 {
1861 struct dc_link_settings link_settings = link->cur_link_settings;
1862
1863 if (signal == SIGNAL_TYPE_DISPLAY_PORT_MST &&
1864 link->mst_stream_alloc_table.stream_count > 0)
1865 /* disable MST link only when last vc payload is deallocated */
1866 return;
1867
1868 dp_disable_link_phy(link, link_res, signal);
1869
1870 if (link->connector_signal == SIGNAL_TYPE_EDP) {
1871 if (!link->skip_implict_edp_power_control)
1872 link->dc->hwss.edp_power_control(link, false);
1873 }
1874
1875 if (signal == SIGNAL_TYPE_DISPLAY_PORT_MST && link->sink_count == 0)
1876 /* set the sink to SST mode after disabling the link */
1877 enable_mst_on_sink(link, false);
1878
1879 if (link_dp_get_encoding_format(&link_settings) ==
1880 DP_8b_10b_ENCODING) {
1881 dp_set_fec_enable(link, link_res, false);
1882 dp_set_fec_ready(link, link_res, false);
1883 }
1884 }
1885
disable_link(struct dc_link * link,const struct link_resource * link_res,enum signal_type signal)1886 static void disable_link(struct dc_link *link,
1887 const struct link_resource *link_res,
1888 enum signal_type signal)
1889 {
1890 if (dc_is_dp_signal(signal)) {
1891 disable_link_dp(link, link_res, signal);
1892 } else if (signal == SIGNAL_TYPE_VIRTUAL) {
1893 link->dc->hwss.disable_link_output(link, link_res, SIGNAL_TYPE_DISPLAY_PORT);
1894 } else {
1895 link->dc->hwss.disable_link_output(link, link_res, signal);
1896 }
1897
1898 if (signal == SIGNAL_TYPE_DISPLAY_PORT_MST) {
1899 /* MST disable link only when no stream use the link */
1900 if (link->mst_stream_alloc_table.stream_count <= 0)
1901 link->link_status.link_active = false;
1902 } else {
1903 link->link_status.link_active = false;
1904 }
1905 }
1906
enable_link_hdmi(struct pipe_ctx * pipe_ctx)1907 static void enable_link_hdmi(struct pipe_ctx *pipe_ctx)
1908 {
1909 struct dc_stream_state *stream = pipe_ctx->stream;
1910 struct dc_link *link = stream->link;
1911 enum dc_color_depth display_color_depth;
1912 enum engine_id eng_id;
1913 struct ext_hdmi_settings settings = {0};
1914 bool is_over_340mhz = false;
1915 bool is_vga_mode = (stream->timing.h_addressable == 640)
1916 && (stream->timing.v_addressable == 480);
1917 struct dc *dc = pipe_ctx->stream->ctx->dc;
1918 const struct link_hwss *link_hwss = get_link_hwss(link, &pipe_ctx->link_res);
1919
1920 if (stream->phy_pix_clk == 0)
1921 stream->phy_pix_clk = stream->timing.pix_clk_100hz / 10;
1922 if (stream->phy_pix_clk > 340000)
1923 is_over_340mhz = true;
1924 if (dc_is_tmds_signal(stream->signal) && stream->phy_pix_clk > 6000000UL) {
1925 ASSERT(false);
1926 return;
1927 }
1928
1929 if (dc_is_hdmi_signal(pipe_ctx->stream->signal)) {
1930 unsigned short masked_chip_caps = pipe_ctx->stream->link->chip_caps &
1931 AMD_EXT_DISPLAY_PATH_CAPS__EXT_CHIP_MASK;
1932 if (masked_chip_caps == AMD_EXT_DISPLAY_PATH_CAPS__HDMI20_TISN65DP159RSBT) {
1933 /* DP159, Retimer settings */
1934 eng_id = pipe_ctx->stream_res.stream_enc->id;
1935
1936 if (get_ext_hdmi_settings(pipe_ctx, eng_id, &settings)) {
1937 write_i2c_retimer_setting(pipe_ctx,
1938 is_vga_mode, is_over_340mhz, &settings);
1939 } else {
1940 write_i2c_default_retimer_setting(pipe_ctx,
1941 is_vga_mode, is_over_340mhz);
1942 }
1943 } else if (masked_chip_caps == AMD_EXT_DISPLAY_PATH_CAPS__HDMI20_PI3EQX1204) {
1944 /* PI3EQX1204, Redriver settings */
1945 write_i2c_redriver_setting(pipe_ctx, is_over_340mhz);
1946 }
1947 }
1948
1949 if (dc_is_hdmi_signal(pipe_ctx->stream->signal))
1950 write_scdc_data(
1951 stream->link->ddc,
1952 stream->phy_pix_clk,
1953 stream->timing.flags.LTE_340MCSC_SCRAMBLE);
1954
1955 memset(&stream->link->cur_link_settings, 0,
1956 sizeof(struct dc_link_settings));
1957
1958 display_color_depth = stream->timing.display_color_depth;
1959 if (stream->timing.pixel_encoding == PIXEL_ENCODING_YCBCR422)
1960 display_color_depth = COLOR_DEPTH_888;
1961
1962 /* We need to enable stream encoder for TMDS first to apply 1/4 TMDS
1963 * character clock in case that beyond 340MHz.
1964 */
1965 if (dc_is_hdmi_tmds_signal(pipe_ctx->stream->signal) || dc_is_dvi_signal(pipe_ctx->stream->signal))
1966 link_hwss->setup_stream_encoder(pipe_ctx);
1967
1968 dc->hwss.enable_tmds_link_output(
1969 link,
1970 &pipe_ctx->link_res,
1971 pipe_ctx->stream->signal,
1972 pipe_ctx->clock_source->id,
1973 display_color_depth,
1974 stream->phy_pix_clk);
1975
1976 if (dc_is_hdmi_signal(pipe_ctx->stream->signal))
1977 read_scdc_data(link->ddc);
1978 }
1979
enable_link_dp(struct dc_state * state,struct pipe_ctx * pipe_ctx)1980 static enum dc_status enable_link_dp(struct dc_state *state,
1981 struct pipe_ctx *pipe_ctx)
1982 {
1983 struct dc_stream_state *stream = pipe_ctx->stream;
1984 enum dc_status status;
1985 bool skip_video_pattern;
1986 struct dc_link *link = stream->link;
1987 const struct dc_link_settings *link_settings =
1988 &pipe_ctx->link_config.dp_link_settings;
1989 bool fec_enable;
1990 int i;
1991 bool apply_seamless_boot_optimization = false;
1992 uint32_t bl_oled_enable_delay = 50; // in ms
1993 uint32_t post_oui_delay = 30; // 30ms
1994 /* Reduce link bandwidth between failed link training attempts. */
1995 bool do_fallback = false;
1996 int lt_attempts = LINK_TRAINING_ATTEMPTS;
1997
1998 // Increase retry count if attempting DP1.x on FIXED_VS link
1999 if (((link->chip_caps & AMD_EXT_DISPLAY_PATH_CAPS__EXT_CHIP_MASK) == AMD_EXT_DISPLAY_PATH_CAPS__DP_FIXED_VS_EN) &&
2000 link_dp_get_encoding_format(link_settings) == DP_8b_10b_ENCODING)
2001 lt_attempts = 10;
2002
2003 // check for seamless boot
2004 for (i = 0; i < state->stream_count; i++) {
2005 if (state->streams[i]->apply_seamless_boot_optimization) {
2006 apply_seamless_boot_optimization = true;
2007 break;
2008 }
2009 }
2010
2011 /* Train with fallback when enabling DPIA link. Conventional links are
2012 * trained with fallback during sink detection.
2013 */
2014 if (link->ep_type == DISPLAY_ENDPOINT_USB4_DPIA &&
2015 !link->dc->config.enable_dpia_pre_training)
2016 do_fallback = true;
2017
2018 /*
2019 * Temporary w/a to get DP2.0 link rates to work with SST.
2020 * TODO DP2.0 - Workaround: Remove w/a if and when the issue is resolved.
2021 */
2022 if (link_dp_get_encoding_format(link_settings) == DP_128b_132b_ENCODING &&
2023 pipe_ctx->stream->signal == SIGNAL_TYPE_DISPLAY_PORT &&
2024 link->dc->debug.set_mst_en_for_sst) {
2025 enable_mst_on_sink(link, true);
2026 } else if (link->dpcd_caps.is_mst_capable &&
2027 pipe_ctx->stream->signal == SIGNAL_TYPE_DISPLAY_PORT) {
2028 /* disable mst on sink */
2029 enable_mst_on_sink(link, false);
2030 }
2031
2032 if (pipe_ctx->stream->signal == SIGNAL_TYPE_EDP) {
2033 /*in case it is not on*/
2034 if (!link->dc->config.edp_no_power_sequencing)
2035 link->dc->hwss.edp_power_control(link, true);
2036 link->dc->hwss.edp_wait_for_hpd_ready(link, true);
2037 }
2038
2039 if (link_dp_get_encoding_format(link_settings) == DP_128b_132b_ENCODING) {
2040 /* TODO - DP2.0 HW: calculate 32 symbol clock for HPO encoder */
2041 } else {
2042 pipe_ctx->stream_res.pix_clk_params.requested_sym_clk =
2043 link_settings->link_rate * LINK_RATE_REF_FREQ_IN_KHZ;
2044 if (state->clk_mgr && !apply_seamless_boot_optimization)
2045 state->clk_mgr->funcs->update_clocks(state->clk_mgr,
2046 state, false);
2047 }
2048
2049 // during mode switch we do DP_SET_POWER off then on, and OUI is lost
2050 dpcd_set_source_specific_data(link);
2051 if (link->dpcd_sink_ext_caps.raw != 0) {
2052 post_oui_delay += link->panel_config.pps.extra_post_OUI_ms;
2053 msleep(post_oui_delay);
2054 }
2055
2056 // similarly, mode switch can cause loss of cable ID
2057 dpcd_write_cable_id_to_dprx(link);
2058
2059 skip_video_pattern = true;
2060
2061 if (link_settings->link_rate == LINK_RATE_LOW)
2062 skip_video_pattern = false;
2063
2064 if (stream->sink_patches.oled_optimize_display_on)
2065 set_default_brightness_aux(link);
2066
2067 if (perform_link_training_with_retries(link_settings,
2068 skip_video_pattern,
2069 lt_attempts,
2070 pipe_ctx,
2071 pipe_ctx->stream->signal,
2072 do_fallback)) {
2073 status = DC_OK;
2074 } else {
2075 status = DC_FAIL_DP_LINK_TRAINING;
2076 }
2077
2078 if (link->preferred_training_settings.fec_enable)
2079 fec_enable = *link->preferred_training_settings.fec_enable;
2080 else
2081 fec_enable = true;
2082
2083 if (link_dp_get_encoding_format(link_settings) == DP_8b_10b_ENCODING)
2084 dp_set_fec_enable(link, &pipe_ctx->link_res, fec_enable);
2085
2086 // during mode set we do DP_SET_POWER off then on, aux writes are lost
2087 if (link->dpcd_sink_ext_caps.bits.oled == 1 ||
2088 link->dpcd_sink_ext_caps.bits.sdr_aux_backlight_control == 1 ||
2089 link->dpcd_sink_ext_caps.bits.hdr_aux_backlight_control == 1) {
2090 if (!stream->sink_patches.oled_optimize_display_on) {
2091 set_default_brightness_aux(link);
2092 if (link->dpcd_sink_ext_caps.bits.oled == 1)
2093 msleep(bl_oled_enable_delay);
2094 edp_backlight_enable_aux(link, true);
2095 } else {
2096 edp_backlight_enable_aux(link, true);
2097 }
2098 }
2099
2100 return status;
2101 }
2102
enable_link_edp(struct dc_state * state,struct pipe_ctx * pipe_ctx)2103 static enum dc_status enable_link_edp(
2104 struct dc_state *state,
2105 struct pipe_ctx *pipe_ctx)
2106 {
2107 return enable_link_dp(state, pipe_ctx);
2108 }
2109
enable_link_lvds(struct pipe_ctx * pipe_ctx)2110 static void enable_link_lvds(struct pipe_ctx *pipe_ctx)
2111 {
2112 struct dc_stream_state *stream = pipe_ctx->stream;
2113 struct dc_link *link = stream->link;
2114 struct dc *dc = stream->ctx->dc;
2115
2116 if (stream->phy_pix_clk == 0)
2117 stream->phy_pix_clk = stream->timing.pix_clk_100hz / 10;
2118
2119 memset(&stream->link->cur_link_settings, 0,
2120 sizeof(struct dc_link_settings));
2121 dc->hwss.enable_lvds_link_output(
2122 link,
2123 &pipe_ctx->link_res,
2124 pipe_ctx->clock_source->id,
2125 stream->phy_pix_clk);
2126
2127 }
2128
enable_link_dp_mst(struct dc_state * state,struct pipe_ctx * pipe_ctx)2129 static enum dc_status enable_link_dp_mst(
2130 struct dc_state *state,
2131 struct pipe_ctx *pipe_ctx)
2132 {
2133 struct dc_link *link = pipe_ctx->stream->link;
2134 unsigned char mstm_cntl = 0;
2135
2136 /* sink signal type after MST branch is MST. Multiple MST sinks
2137 * share one link. Link DP PHY is enable or training only once.
2138 */
2139 if (link->link_status.link_active)
2140 return DC_OK;
2141
2142 /* clear payload table */
2143 core_link_read_dpcd(link, DP_MSTM_CTRL, &mstm_cntl, 1);
2144 if (mstm_cntl & DP_MST_EN)
2145 dm_helpers_dp_mst_clear_payload_allocation_table(link->ctx, link);
2146
2147 /* to make sure the pending down rep can be processed
2148 * before enabling the link
2149 */
2150 dm_helpers_dp_mst_poll_pending_down_reply(link->ctx, link);
2151
2152 /* set the sink to MST mode before enabling the link */
2153 enable_mst_on_sink(link, true);
2154
2155 return enable_link_dp(state, pipe_ctx);
2156 }
2157
enable_link_analog(struct dc_state * state,struct pipe_ctx * pipe_ctx)2158 static enum dc_status enable_link_analog(
2159 struct dc_state *state,
2160 struct pipe_ctx *pipe_ctx)
2161 {
2162 struct dc_link *link = pipe_ctx->stream->link;
2163
2164 link->dc->hwss.enable_analog_link_output(
2165 link, pipe_ctx->stream->timing.pix_clk_100hz);
2166
2167 return DC_OK;
2168 }
2169
enable_link_virtual(struct pipe_ctx * pipe_ctx)2170 static enum dc_status enable_link_virtual(struct pipe_ctx *pipe_ctx)
2171 {
2172 struct dc_link *link = pipe_ctx->stream->link;
2173
2174 link->dc->hwss.enable_dp_link_output(link,
2175 &pipe_ctx->link_res,
2176 SIGNAL_TYPE_DISPLAY_PORT,
2177 pipe_ctx->clock_source->id,
2178 &pipe_ctx->link_config.dp_link_settings);
2179 return DC_OK;
2180 }
2181
enable_link(struct dc_state * state,struct pipe_ctx * pipe_ctx)2182 static enum dc_status enable_link(
2183 struct dc_state *state,
2184 struct pipe_ctx *pipe_ctx)
2185 {
2186 enum dc_status status = DC_ERROR_UNEXPECTED;
2187 struct dc_stream_state *stream = pipe_ctx->stream;
2188 struct dc_link *link = NULL;
2189
2190 if (stream == NULL)
2191 return DC_ERROR_UNEXPECTED;
2192 link = stream->link;
2193
2194 /* There's some scenarios where driver is unloaded with display
2195 * still enabled. When driver is reloaded, it may cause a display
2196 * to not light up if there is a mismatch between old and new
2197 * link settings. Need to call disable first before enabling at
2198 * new link settings.
2199 */
2200 if (link->link_status.link_active)
2201 disable_link(link, &pipe_ctx->link_res, pipe_ctx->stream->signal);
2202
2203 switch (pipe_ctx->stream->signal) {
2204 case SIGNAL_TYPE_DISPLAY_PORT:
2205 status = enable_link_dp(state, pipe_ctx);
2206 break;
2207 case SIGNAL_TYPE_EDP:
2208 status = enable_link_edp(state, pipe_ctx);
2209 break;
2210 case SIGNAL_TYPE_DISPLAY_PORT_MST:
2211 status = enable_link_dp_mst(state, pipe_ctx);
2212 msleep(200);
2213 break;
2214 case SIGNAL_TYPE_DVI_SINGLE_LINK:
2215 case SIGNAL_TYPE_DVI_DUAL_LINK:
2216 case SIGNAL_TYPE_HDMI_TYPE_A:
2217 enable_link_hdmi(pipe_ctx);
2218 status = DC_OK;
2219 break;
2220 case SIGNAL_TYPE_LVDS:
2221 enable_link_lvds(pipe_ctx);
2222 status = DC_OK;
2223 break;
2224 case SIGNAL_TYPE_RGB:
2225 status = enable_link_analog(state, pipe_ctx);
2226 break;
2227 case SIGNAL_TYPE_VIRTUAL:
2228 status = enable_link_virtual(pipe_ctx);
2229 break;
2230 default:
2231 break;
2232 }
2233
2234 if (status == DC_OK) {
2235 pipe_ctx->stream->link->link_status.link_active = true;
2236 }
2237
2238 return status;
2239 }
2240
allocate_usb4_bandwidth_for_stream(struct dc_stream_state * stream,int bw)2241 static bool allocate_usb4_bandwidth_for_stream(struct dc_stream_state *stream, int bw)
2242 {
2243 struct dc_link *link = stream->sink->link;
2244 int req_bw = bw;
2245
2246 DC_LOGGER_INIT(link->ctx->logger);
2247
2248 if (!link->dpia_bw_alloc_config.bw_alloc_enabled)
2249 return false;
2250
2251 if (stream->signal == SIGNAL_TYPE_DISPLAY_PORT_MST) {
2252 int sink_index = 0;
2253 int i = 0;
2254
2255 for (i = 0; i < link->sink_count; i++) {
2256 if (link->remote_sinks[i] == NULL)
2257 continue;
2258
2259 if (stream->sink->sink_id != link->remote_sinks[i]->sink_id)
2260 req_bw += link->dpia_bw_alloc_config.remote_sink_req_bw[i];
2261 else
2262 sink_index = i;
2263 }
2264
2265 link->dpia_bw_alloc_config.remote_sink_req_bw[sink_index] = bw;
2266 }
2267
2268 link->dpia_bw_alloc_config.dp_overhead = link_dpia_get_dp_overhead(link);
2269 req_bw += link->dpia_bw_alloc_config.dp_overhead;
2270
2271 link_dp_dpia_allocate_usb4_bandwidth_for_stream(link, req_bw);
2272
2273 if (stream->signal == SIGNAL_TYPE_DISPLAY_PORT_MST) {
2274 int i = 0;
2275
2276 for (i = 0; i < link->sink_count; i++) {
2277 if (link->remote_sinks[i] == NULL)
2278 continue;
2279 DC_LOG_DEBUG("%s, remote_sink=%s, request_bw=%d\n", __func__,
2280 (const char *)(&link->remote_sinks[i]->edid_caps.display_name[0]),
2281 link->dpia_bw_alloc_config.remote_sink_req_bw[i]);
2282 }
2283 }
2284
2285 return true;
2286 }
2287
allocate_usb4_bandwidth(struct dc_stream_state * stream)2288 static bool allocate_usb4_bandwidth(struct dc_stream_state *stream)
2289 {
2290 bool ret;
2291
2292 int bw = dc_bandwidth_in_kbps_from_timing(&stream->timing,
2293 dc_link_get_highest_encoding_format(stream->sink->link));
2294
2295 ret = allocate_usb4_bandwidth_for_stream(stream, bw);
2296
2297 return ret;
2298 }
2299
deallocate_usb4_bandwidth(struct dc_stream_state * stream)2300 static bool deallocate_usb4_bandwidth(struct dc_stream_state *stream)
2301 {
2302 bool ret;
2303
2304 ret = allocate_usb4_bandwidth_for_stream(stream, 0);
2305
2306 return ret;
2307 }
2308
link_set_dpms_off(struct pipe_ctx * pipe_ctx)2309 void link_set_dpms_off(struct pipe_ctx *pipe_ctx)
2310 {
2311 struct dc *dc = pipe_ctx->stream->ctx->dc;
2312 struct dc_stream_state *stream = pipe_ctx->stream;
2313 struct dc_link *link = stream->sink->link;
2314 struct vpg *vpg = pipe_ctx->stream_res.stream_enc->vpg;
2315 enum dp_panel_mode panel_mode_dp = dp_get_panel_mode(link);
2316
2317 DC_LOGGER_INIT(pipe_ctx->stream->ctx->logger);
2318
2319 ASSERT(is_master_pipe_for_link(link, pipe_ctx));
2320
2321 if (dp_is_128b_132b_signal(pipe_ctx))
2322 vpg = pipe_ctx->stream_res.hpo_dp_stream_enc->vpg;
2323 if (dc_is_virtual_signal(pipe_ctx->stream->signal))
2324 return;
2325
2326 if (pipe_ctx->stream->sink) {
2327 if (pipe_ctx->stream->sink->sink_signal != SIGNAL_TYPE_VIRTUAL &&
2328 pipe_ctx->stream->sink->sink_signal != SIGNAL_TYPE_NONE) {
2329 DC_LOG_DC("%s pipe_ctx dispname=%s signal=%x link=%d sink_count=%d\n", __func__,
2330 pipe_ctx->stream->sink->edid_caps.display_name,
2331 pipe_ctx->stream->signal, link->link_index, link->sink_count);
2332 }
2333 }
2334
2335 if (!pipe_ctx->stream->sink->edid_caps.panel_patch.skip_avmute) {
2336 if (dc_is_hdmi_signal(pipe_ctx->stream->signal))
2337 set_avmute(pipe_ctx, true);
2338 }
2339
2340 dc->hwss.disable_audio_stream(pipe_ctx);
2341
2342 update_psp_stream_config(pipe_ctx, true);
2343 dc->hwss.blank_stream(pipe_ctx);
2344
2345 if (pipe_ctx->link_config.dp_tunnel_settings.should_use_dp_bw_allocation)
2346 deallocate_usb4_bandwidth(pipe_ctx->stream);
2347
2348 if (pipe_ctx->stream->signal == SIGNAL_TYPE_DISPLAY_PORT_MST)
2349 deallocate_mst_payload(pipe_ctx);
2350 else if (dc_is_dp_sst_signal(pipe_ctx->stream->signal) &&
2351 dp_is_128b_132b_signal(pipe_ctx))
2352 update_sst_payload(pipe_ctx, false);
2353
2354 if (dc_is_hdmi_signal(pipe_ctx->stream->signal)) {
2355 struct ext_hdmi_settings settings = {0};
2356 enum engine_id eng_id = pipe_ctx->stream_res.stream_enc->id;
2357
2358 unsigned short masked_chip_caps = link->chip_caps &
2359 AMD_EXT_DISPLAY_PATH_CAPS__EXT_CHIP_MASK;
2360 //Need to inform that sink is going to use legacy HDMI mode.
2361 write_scdc_data(
2362 link->ddc,
2363 165000,//vbios only handles 165Mhz.
2364 false);
2365 if (masked_chip_caps == AMD_EXT_DISPLAY_PATH_CAPS__HDMI20_TISN65DP159RSBT) {
2366 /* DP159, Retimer settings */
2367 if (get_ext_hdmi_settings(pipe_ctx, eng_id, &settings))
2368 write_i2c_retimer_setting(pipe_ctx,
2369 false, false, &settings);
2370 else
2371 write_i2c_default_retimer_setting(pipe_ctx,
2372 false, false);
2373 } else if (masked_chip_caps == AMD_EXT_DISPLAY_PATH_CAPS__HDMI20_PI3EQX1204) {
2374 /* PI3EQX1204, Redriver settings */
2375 write_i2c_redriver_setting(pipe_ctx, false);
2376 }
2377 }
2378
2379 if (pipe_ctx->stream->signal == SIGNAL_TYPE_DISPLAY_PORT &&
2380 !dp_is_128b_132b_signal(pipe_ctx)) {
2381
2382 /* In DP1.x SST mode, our encoder will go to TPS1
2383 * when link is on but stream is off.
2384 * Disabling link before stream will avoid exposing TPS1 pattern
2385 * during the disable sequence as it will confuse some receivers
2386 * state machine.
2387 * In DP2 or MST mode, our encoder will stay video active
2388 */
2389 disable_link(pipe_ctx->stream->link, &pipe_ctx->link_res, pipe_ctx->stream->signal);
2390 dc->hwss.disable_stream(pipe_ctx);
2391 } else {
2392 dc->hwss.disable_stream(pipe_ctx);
2393 disable_link(pipe_ctx->stream->link, &pipe_ctx->link_res, pipe_ctx->stream->signal);
2394 }
2395 edp_set_panel_assr(link, pipe_ctx, &panel_mode_dp, false);
2396
2397 if (pipe_ctx->stream->timing.flags.DSC) {
2398 if (dc_is_dp_signal(pipe_ctx->stream->signal))
2399 link_set_dsc_enable(pipe_ctx, false);
2400 }
2401 if (dp_is_128b_132b_signal(pipe_ctx)) {
2402 if (pipe_ctx->stream_res.tg->funcs->set_out_mux)
2403 pipe_ctx->stream_res.tg->funcs->set_out_mux(pipe_ctx->stream_res.tg, OUT_MUX_DIO);
2404 }
2405
2406 if (vpg && vpg->funcs->vpg_powerdown)
2407 vpg->funcs->vpg_powerdown(vpg);
2408
2409 /* for psp not exist case */
2410 if (link->connector_signal == SIGNAL_TYPE_EDP && dc->debug.psp_disabled_wa) {
2411 /* reset internal save state to default since eDP is off */
2412 enum dp_panel_mode panel_mode = dp_get_panel_mode(pipe_ctx->stream->link);
2413 /* since current psp not loaded, we need to reset it to default */
2414 link->panel_mode = panel_mode;
2415 }
2416 }
2417
link_set_dpms_on(struct dc_state * state,struct pipe_ctx * pipe_ctx)2418 void link_set_dpms_on(
2419 struct dc_state *state,
2420 struct pipe_ctx *pipe_ctx)
2421 {
2422 struct dc *dc = pipe_ctx->stream->ctx->dc;
2423 struct dc_stream_state *stream = pipe_ctx->stream;
2424 struct dc_link *link = stream->sink->link;
2425 enum dc_status status;
2426 struct link_encoder *link_enc = pipe_ctx->link_res.dio_link_enc;
2427 enum otg_out_mux_dest otg_out_dest = OUT_MUX_DIO;
2428 struct vpg *vpg = pipe_ctx->stream_res.stream_enc->vpg;
2429 const struct link_hwss *link_hwss = get_link_hwss(link, &pipe_ctx->link_res);
2430 bool apply_edp_fast_boot_optimization =
2431 pipe_ctx->stream->apply_edp_fast_boot_optimization;
2432
2433 DC_LOGGER_INIT(pipe_ctx->stream->ctx->logger);
2434
2435 ASSERT(is_master_pipe_for_link(link, pipe_ctx));
2436
2437 if (dp_is_128b_132b_signal(pipe_ctx))
2438 vpg = pipe_ctx->stream_res.hpo_dp_stream_enc->vpg;
2439 if (dc_is_virtual_signal(pipe_ctx->stream->signal))
2440 return;
2441
2442 if (pipe_ctx->stream->sink) {
2443 if (pipe_ctx->stream->sink->sink_signal != SIGNAL_TYPE_VIRTUAL &&
2444 pipe_ctx->stream->sink->sink_signal != SIGNAL_TYPE_NONE) {
2445 DC_LOG_DC("%s pipe_ctx dispname=%s signal=%x link=%d sink_count=%d\n", __func__,
2446 pipe_ctx->stream->sink->edid_caps.display_name,
2447 pipe_ctx->stream->signal,
2448 link->link_index,
2449 link->sink_count);
2450 }
2451 }
2452
2453 if (!dc->config.unify_link_enc_assignment)
2454 link_enc = link_enc_cfg_get_link_enc(link);
2455 ASSERT(link_enc);
2456
2457 if (!dc_is_virtual_signal(pipe_ctx->stream->signal)
2458 && !dp_is_128b_132b_signal(pipe_ctx)) {
2459 if (link_enc)
2460 link_enc->funcs->setup(
2461 link_enc,
2462 pipe_ctx->stream->signal);
2463 }
2464
2465 pipe_ctx->stream->link->link_state_valid = true;
2466
2467 if (pipe_ctx->stream_res.tg->funcs->set_out_mux) {
2468 if (dp_is_128b_132b_signal(pipe_ctx))
2469 otg_out_dest = OUT_MUX_HPO_DP;
2470 else
2471 otg_out_dest = OUT_MUX_DIO;
2472 pipe_ctx->stream_res.tg->funcs->set_out_mux(pipe_ctx->stream_res.tg, otg_out_dest);
2473 }
2474
2475 link_hwss->setup_stream_attribute(pipe_ctx);
2476
2477 pipe_ctx->stream->apply_edp_fast_boot_optimization = false;
2478
2479 // Enable VPG before building infoframe
2480 if (vpg && vpg->funcs->vpg_poweron)
2481 vpg->funcs->vpg_poweron(vpg);
2482
2483 resource_build_info_frame(pipe_ctx);
2484 dc->hwss.update_info_frame(pipe_ctx);
2485
2486 if (dc_is_dp_signal(pipe_ctx->stream->signal))
2487 dp_trace_source_sequence(link, DPCD_SOURCE_SEQ_AFTER_UPDATE_INFO_FRAME);
2488
2489 /* Do not touch link on seamless boot optimization. */
2490 if (pipe_ctx->stream->apply_seamless_boot_optimization) {
2491 pipe_ctx->stream->dpms_off = false;
2492
2493 /* Still enable stream features & audio on seamless boot for DP external displays */
2494 if (pipe_ctx->stream->signal == SIGNAL_TYPE_DISPLAY_PORT) {
2495 enable_stream_features(pipe_ctx);
2496 dc->hwss.enable_audio_stream(pipe_ctx);
2497 }
2498
2499 update_psp_stream_config(pipe_ctx, false);
2500 return;
2501 }
2502
2503 /* eDP lit up by bios already, no need to enable again. */
2504 if (pipe_ctx->stream->signal == SIGNAL_TYPE_EDP &&
2505 apply_edp_fast_boot_optimization &&
2506 !pipe_ctx->stream->timing.flags.DSC &&
2507 !pipe_ctx->next_odm_pipe) {
2508 pipe_ctx->stream->dpms_off = false;
2509 update_psp_stream_config(pipe_ctx, false);
2510
2511 if (link->is_dds) {
2512 uint32_t post_oui_delay = 30; // 30ms
2513
2514 dpcd_set_source_specific_data(link);
2515 msleep(post_oui_delay);
2516 }
2517
2518 return;
2519 }
2520
2521 if (pipe_ctx->stream->dpms_off)
2522 return;
2523
2524 /* For Dp tunneling link, a pending HPD means that we have a race condition between processing
2525 * current link and processing the pending HPD. If we enable the link now, we may end up with a
2526 * link that is not actually connected to a sink. So we skip enabling the link in this case.
2527 */
2528 if (link->ep_type == DISPLAY_ENDPOINT_USB4_DPIA && link->is_hpd_pending) {
2529 DC_LOG_DEBUG("%s, Link%d HPD is pending, not enable it.\n", __func__, link->link_index);
2530 return;
2531 }
2532
2533 /* Have to setup DSC before DIG FE and BE are connected (which happens before the
2534 * link training). This is to make sure the bandwidth sent to DIG BE won't be
2535 * bigger than what the link and/or DIG BE can handle. VBID[6]/CompressedStream_flag
2536 * will be automatically set at a later time when the video is enabled
2537 * (DP_VID_STREAM_EN = 1).
2538 */
2539 if (pipe_ctx->stream->timing.flags.DSC) {
2540 if (dc_is_dp_signal(pipe_ctx->stream->signal) ||
2541 dc_is_virtual_signal(pipe_ctx->stream->signal))
2542 link_set_dsc_enable(pipe_ctx, true);
2543 }
2544
2545 if (link->replay_settings.config.replay_supported && !dc_is_embedded_signal(link->connector_signal))
2546 dp_setup_replay(link, stream);
2547
2548 status = enable_link(state, pipe_ctx);
2549
2550 if (status != DC_OK) {
2551 DC_LOG_WARNING("enabling link %u failed: %d\n",
2552 pipe_ctx->stream->link->link_index,
2553 status);
2554
2555 /* Abort stream enable *unless* the failure was due to
2556 * DP link training - some DP monitors will recover and
2557 * show the stream anyway. But MST displays can't proceed
2558 * without link training.
2559 */
2560 if (status != DC_FAIL_DP_LINK_TRAINING ||
2561 pipe_ctx->stream->signal == SIGNAL_TYPE_DISPLAY_PORT_MST) {
2562 if (false == stream->link->link_status.link_active)
2563 disable_link(stream->link, &pipe_ctx->link_res,
2564 pipe_ctx->stream->signal);
2565 BREAK_TO_DEBUGGER();
2566 return;
2567 }
2568 }
2569
2570 /* turn off otg test pattern if enable */
2571 if (pipe_ctx->stream_res.tg->funcs->set_test_pattern)
2572 pipe_ctx->stream_res.tg->funcs->set_test_pattern(pipe_ctx->stream_res.tg,
2573 CONTROLLER_DP_TEST_PATTERN_VIDEOMODE,
2574 COLOR_DEPTH_UNDEFINED);
2575
2576 /* This second call is needed to reconfigure the DIG
2577 * as a workaround for the incorrect value being applied
2578 * from transmitter control.
2579 */
2580 if (!(dc_is_virtual_signal(pipe_ctx->stream->signal) ||
2581 dp_is_128b_132b_signal(pipe_ctx))) {
2582
2583 if (link_enc)
2584 link_enc->funcs->setup(
2585 link_enc,
2586 pipe_ctx->stream->signal);
2587
2588 }
2589
2590 dc->hwss.enable_stream(pipe_ctx);
2591
2592 /* Set DPS PPS SDP (AKA "info frames") */
2593 if (pipe_ctx->stream->timing.flags.DSC) {
2594 if (dc_is_dp_signal(pipe_ctx->stream->signal) ||
2595 dc_is_virtual_signal(pipe_ctx->stream->signal)) {
2596 dp_set_dsc_on_rx(pipe_ctx, true);
2597 link_set_dsc_pps_packet(pipe_ctx, true, true);
2598 }
2599 }
2600
2601 if (dc_is_dp_signal(pipe_ctx->stream->signal))
2602 dp_set_hblank_reduction_on_rx(pipe_ctx);
2603
2604 if (pipe_ctx->link_config.dp_tunnel_settings.should_use_dp_bw_allocation)
2605 allocate_usb4_bandwidth(pipe_ctx->stream);
2606
2607 if (pipe_ctx->stream->signal == SIGNAL_TYPE_DISPLAY_PORT_MST)
2608 allocate_mst_payload(pipe_ctx);
2609 else if (dc_is_dp_sst_signal(pipe_ctx->stream->signal) &&
2610 dp_is_128b_132b_signal(pipe_ctx))
2611 update_sst_payload(pipe_ctx, true);
2612
2613 /* Corruption was observed on systems with display mux when stream gets
2614 * enabled after the mux switch. Having a small delay between link
2615 * training and stream unblank resolves the corruption issue.
2616 * This is workaround.
2617 */
2618 if (pipe_ctx->stream->signal == SIGNAL_TYPE_EDP &&
2619 link->is_display_mux_present)
2620 msleep(20);
2621
2622 dc->hwss.unblank_stream(pipe_ctx,
2623 &pipe_ctx->stream->link->cur_link_settings);
2624
2625 if (stream->sink_patches.delay_ignore_msa > 0)
2626 msleep(stream->sink_patches.delay_ignore_msa);
2627
2628 if (dc_is_dp_signal(pipe_ctx->stream->signal))
2629 enable_stream_features(pipe_ctx);
2630 update_psp_stream_config(pipe_ctx, false);
2631
2632 dc->hwss.enable_audio_stream(pipe_ctx);
2633
2634 if (dc_is_hdmi_signal(pipe_ctx->stream->signal)) {
2635 set_avmute(pipe_ctx, false);
2636 }
2637 }
2638