Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

drm/amd/display: Indirect buffer transport for FAMS2 commands

[Why]
The quantity and duration of FAMS2 commands are set to increase
in future products. This necessitates the implementation of a new
mechanism for chaining commands together, allowing all commands
to be processed within a single transaction.

[How]
The indirect buffer acts as a shared buffer on the driver side,
mapped to DMUB's internal CW7 address. Its source address and
size are sent through mailbox command to DMUB, triggering the
transaction.

Reviewed-by: Alvin Lee <alvin.lee2@amd.com>
Signed-off-by: Oleh Kuzhylnyi <okuzhyln@amd.com>
Signed-off-by: Wayne Lin <wayne.lin@amd.com>
Tested-by: Daniel Wheeler <daniel.wheeler@amd.com>
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>

authored by

Oleh Kuzhylnyi and committed by
Alex Deucher
db122ece 71e17aed

+69 -2
+1
drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
··· 2404 2404 DMUB_WINDOW_MEMORY_TYPE_FB, //DMUB_WINDOW_5_TRACEBUFF 2405 2405 DMUB_WINDOW_MEMORY_TYPE_FB, //DMUB_WINDOW_6_FW_STATE 2406 2406 DMUB_WINDOW_MEMORY_TYPE_FB, //DMUB_WINDOW_7_SCRATCH_MEM 2407 + DMUB_WINDOW_MEMORY_TYPE_FB, //DMUB_WINDOW_IB_MEM 2407 2408 DMUB_WINDOW_MEMORY_TYPE_FB, //DMUB_WINDOW_SHARED_STATE 2408 2409 }; 2409 2410 int r;
+58 -1
drivers/gpu/drm/amd/display/dc/dc_dmub_srv.c
··· 1656 1656 return result; 1657 1657 } 1658 1658 1659 - void dc_dmub_srv_fams2_update_config(struct dc *dc, 1659 + static void dc_dmub_srv_rb_based_fams2_update_config(struct dc *dc, 1660 1660 struct dc_state *context, 1661 1661 bool enable) 1662 1662 { ··· 1720 1720 } 1721 1721 1722 1722 dm_execute_dmub_cmd_list(dc->ctx, num_cmds, cmd, DM_DMUB_WAIT_TYPE_WAIT); 1723 + } 1724 + 1725 + static void dc_dmub_srv_ib_based_fams2_update_config(struct dc *dc, 1726 + struct dc_state *context, 1727 + bool enable) 1728 + { 1729 + struct dmub_fams2_config_v2 *config = (struct dmub_fams2_config_v2 *)dc->ctx->dmub_srv->dmub->ib_mem_gart.cpu_addr; 1730 + union dmub_rb_cmd cmd; 1731 + uint32_t i; 1732 + 1733 + memset(config, 0, sizeof(*config)); 1734 + memset(&cmd, 0, sizeof(cmd)); 1735 + 1736 + cmd.ib_fams2_config.header.type = DMUB_CMD__FW_ASSISTED_MCLK_SWITCH; 1737 + cmd.ib_fams2_config.header.sub_type = DMUB_CMD__FAMS2_IB_CONFIG; 1738 + 1739 + cmd.ib_fams2_config.ib_data.src.quad_part = dc->ctx->dmub_srv->dmub->ib_mem_gart.gpu_addr; 1740 + cmd.ib_fams2_config.ib_data.size = sizeof(*config); 1741 + 1742 + if (enable && context->bw_ctx.bw.dcn.fams2_global_config.features.bits.enable) { 1743 + /* copy static feature configuration overrides */ 1744 + config->global.features.bits.enable_stall_recovery = dc->debug.fams2_config.bits.enable_stall_recovery; 1745 + config->global.features.bits.enable_offload_flip = dc->debug.fams2_config.bits.enable_offload_flip; 1746 + config->global.features.bits.enable_debug = dc->debug.fams2_config.bits.enable_debug; 1747 + 1748 + /* send global configuration parameters */ 1749 + memcpy(&config->global, &context->bw_ctx.bw.dcn.fams2_global_config, 1750 + sizeof(struct dmub_cmd_fams2_global_config)); 1751 + 1752 + /* construct per-stream configs */ 1753 + for (i = 0; i < context->bw_ctx.bw.dcn.fams2_global_config.num_streams; i++) { 1754 + /* copy stream static base state */ 1755 + memcpy(&config->stream_v1[i].base, 1756 + &context->bw_ctx.bw.dcn.fams2_stream_base_params[i], 1757 + sizeof(config->stream_v1[i].base)); 1758 + 1759 + /* copy stream static sub-state */ 1760 + memcpy(&config->stream_v1[i].sub_state, 1761 + &context->bw_ctx.bw.dcn.fams2_stream_sub_params[i], 1762 + sizeof(config->stream_v1[i].sub_state)); 1763 + } 1764 + } 1765 + 1766 + config->global.features.bits.enable_visual_confirm = dc->debug.visual_confirm == VISUAL_CONFIRM_FAMS2; 1767 + config->global.features.bits.enable = enable; 1768 + 1769 + dm_execute_dmub_cmd_list(dc->ctx, 1, &cmd, DM_DMUB_WAIT_TYPE_WAIT); 1770 + } 1771 + 1772 + void dc_dmub_srv_fams2_update_config(struct dc *dc, 1773 + struct dc_state *context, 1774 + bool enable) 1775 + { 1776 + if (dc->debug.fams_version.major == 2) 1777 + dc_dmub_srv_rb_based_fams2_update_config(dc, context, enable); 1778 + if (dc->debug.fams_version.major == 3) 1779 + dc_dmub_srv_ib_based_fams2_update_config(dc, context, enable); 1723 1780 } 1724 1781 1725 1782 void dc_dmub_srv_fams2_drr_update(struct dc *dc,
+2
drivers/gpu/drm/amd/display/dmub/dmub_srv.h
··· 129 129 DMUB_WINDOW_5_TRACEBUFF, 130 130 DMUB_WINDOW_6_FW_STATE, 131 131 DMUB_WINDOW_7_SCRATCH_MEM, 132 + DMUB_WINDOW_IB_MEM, 132 133 DMUB_WINDOW_SHARED_STATE, 133 134 DMUB_WINDOW_TOTAL, 134 135 }; ··· 540 539 uint32_t fw_version; 541 540 bool is_virtual; 542 541 struct dmub_fb scratch_mem_fb; 542 + struct dmub_fb ib_mem_gart; 543 543 volatile struct dmub_shared_state_feature_block *shared_state; 544 544 volatile const struct dmub_fw_state *fw_state; 545 545
+8 -1
drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c
··· 65 65 /* Default scratch mem size. */ 66 66 #define DMUB_SCRATCH_MEM_SIZE (1024) 67 67 68 + /* Default indirect buffer size. */ 69 + #define DMUB_IB_MEM_SIZE (1280) 70 + 68 71 /* Number of windows in use. */ 69 72 #define DMUB_NUM_WINDOWS (DMUB_WINDOW_TOTAL) 70 73 /* Base addresses. */ ··· 562 559 window_sizes[DMUB_WINDOW_5_TRACEBUFF] = trace_buffer_size; 563 560 window_sizes[DMUB_WINDOW_6_FW_STATE] = fw_state_size; 564 561 window_sizes[DMUB_WINDOW_7_SCRATCH_MEM] = DMUB_SCRATCH_MEM_SIZE; 562 + window_sizes[DMUB_WINDOW_IB_MEM] = DMUB_IB_MEM_SIZE; 565 563 window_sizes[DMUB_WINDOW_SHARED_STATE] = max(DMUB_FW_HEADER_SHARED_STATE_SIZE, shared_state_size); 566 564 567 565 out->fb_size = ··· 649 645 struct dmub_fb *tracebuff_fb = params->fb[DMUB_WINDOW_5_TRACEBUFF]; 650 646 struct dmub_fb *fw_state_fb = params->fb[DMUB_WINDOW_6_FW_STATE]; 651 647 struct dmub_fb *scratch_mem_fb = params->fb[DMUB_WINDOW_7_SCRATCH_MEM]; 648 + struct dmub_fb *ib_mem_gart = params->fb[DMUB_WINDOW_IB_MEM]; 652 649 struct dmub_fb *shared_state_fb = params->fb[DMUB_WINDOW_SHARED_STATE]; 653 650 654 651 struct dmub_rb_init_params rb_params, outbox0_rb_params; ··· 660 655 return DMUB_STATUS_INVALID; 661 656 662 657 if (!inst_fb || !stack_fb || !data_fb || !bios_fb || !mail_fb || 663 - !tracebuff_fb || !fw_state_fb || !scratch_mem_fb) { 658 + !tracebuff_fb || !fw_state_fb || !scratch_mem_fb || !ib_mem_gart) { 664 659 ASSERT(0); 665 660 return DMUB_STATUS_INVALID; 666 661 } ··· 745 740 dmub->shared_state = shared_state_fb->cpu_addr; 746 741 747 742 dmub->scratch_mem_fb = *scratch_mem_fb; 743 + 744 + dmub->ib_mem_gart = *ib_mem_gart; 748 745 749 746 if (dmub->hw_funcs.setup_windows) 750 747 dmub->hw_funcs.setup_windows(dmub, &cw2, &cw3, &cw4, &cw5, &cw6, &region6);