diff --git a/src/amd/ds/amd_pps_perf.cc b/src/amd/ds/amd_pps_perf.cc index f8bc31adfb6..04a9e7f57d1 100644 --- a/src/amd/ds/amd_pps_perf.cc +++ b/src/amd/ds/amd_pps_perf.cc @@ -386,3 +386,80 @@ void AMDPerf::amdgpu_cs_destroy() free(cs); cs = NULL; } + +void AMDPerf::amdgpu_pc_wait_idle(struct radeon_cmdbuf *cmd) +{ + radeon_emit(cmd, PKT3(PKT3_EVENT_WRITE, 0, 0)); + radeon_emit(cmd, EVENT_TYPE(V_028A90_CS_PARTIAL_FLUSH | EVENT_INDEX(4))); + + radeon_emit(cmd, PKT3(PKT3_ACQUIRE_MEM, info.gfx_level > GFX9 ? 6 : 5, 0)); + radeon_emit(cmd, 0); /* CP_COHER_CNTL */ + radeon_emit(cmd, 0xffffffff); /* CP_COHER_SIZE */ + radeon_emit(cmd, 0xffffff); /* CP_COHER_SIZE_HI */ + radeon_emit(cmd, 0); /* CP_COHER_BASE */ + radeon_emit(cmd, 0); /* CP_COHER_BASE_HI */ + radeon_emit(cmd, 0x0000000A); /* POLL_INTERVAL */ + + if (info.gfx_level > GFX9) + radeon_emit(cmd, 0); /* GCR_CNTL */ + + radeon_emit(cmd, PKT3(PKT3_PFP_SYNC_ME, 0, 0)); + radeon_emit(cmd, 0); +} + +void AMDPerf::radeon_emit_inhibit_clockgating(struct radeon_cmdbuf *cmd, bool inhibit) +{ + if (info.gfx_level >= GFX11) + return; + + if (info.gfx_level >= GFX10) + radeon_set_uconfig_reg(cmd, R_037390_RLC_PERFMON_CLK_CNTL, S_037390_PERFMON_CLOCK_STATE(inhibit)); + else if (info.gfx_level >= GFX9) + radeon_set_uconfig_reg(cmd, R_0372FC_RLC_PERFMON_CLK_CNTL, S_0372FC_PERFMON_CLOCK_STATE(inhibit)); +} + +void AMDPerf::radeon_emit_spi_config_cntl(struct radeon_cmdbuf *cmd, bool enable) +{ + if (info.gfx_level >= GFX9) { + uint32_t spi_config_cntl = S_031100_GPR_WRITE_PRIORITY(0x2c688) | + S_031100_EXP_PRIORITY_ORDER(3) | + S_031100_ENABLE_SQG_TOP_EVENTS(enable) | + S_031100_ENABLE_SQG_BOP_EVENTS(enable); + if (info.gfx_level >= GFX10) + spi_config_cntl |= S_031100_PS_PKR_PRIORITY_CNTL(3); + + radeon_set_uconfig_reg(cmd, R_031100_SPI_CONFIG_CNTL, spi_config_cntl); + } else { + radeon_emit(cmd, PKT3(PKT3_COPY_DATA, 4, 0)); + radeon_emit(cmd, COPY_DATA_SRC_SEL(COPY_DATA_IMM) | COPY_DATA_DST_SEL(COPY_DATA_PERF)); + radeon_emit(cmd, S_009100_ENABLE_SQG_TOP_EVENTS(enable) | S_009100_ENABLE_SQG_BOP_EVENTS(enable)); + radeon_emit(cmd, 0); /* unused */ + radeon_emit(cmd, R_009100_SPI_CONFIG_CNTL >> 2); + radeon_emit(cmd, 0); /* unused */ + } +} + +void AMDPerf::radeon_emit_perfctr_shaders(struct radeon_cmdbuf *cmd, unsigned shaders) +{ + radeon_set_uconfig_reg_seq(cmd, R_036780_SQ_PERFCOUNTER_CTRL, 2); + radeon_emit(cmd, shaders & 0x7f); + radeon_emit(cmd, 0xffffffff); +} + +void AMDPerf::radeon_emit_instance(struct radeon_cmdbuf *cmd, int se, int instance) +{ + unsigned value = S_030800_SH_BROADCAST_WRITES(1); + + value |= (se >= 0) ? S_030800_SE_INDEX(se) : S_030800_SE_BROADCAST_WRITES(1); + value |= (instance >= 0) ? S_030800_INSTANCE_INDEX(instance) : S_030800_INSTANCE_BROADCAST_WRITES(1); + + radeon_set_uconfig_reg(cmd, R_030800_GRBM_GFX_INDEX, value); +} + +void AMDPerf::radeon_emit_windowed_counters(struct radeon_cmdbuf *cmd, bool enable) +{ + radeon_emit(cmd, PKT3(PKT3_EVENT_WRITE, 0, 0)); + radeon_emit(cmd, EVENT_TYPE(enable ? V_028A90_PERFCOUNTER_START : V_028A90_PERFCOUNTER_STOP) | EVENT_INDEX(0)); + radeon_set_sh_reg(cmd, R_00B82C_COMPUTE_PERFCOUNT_ENABLE, S_00B82C_PERFCOUNT_ENABLE(enable)); +} + diff --git a/src/amd/ds/amd_pps_perf.h b/src/amd/ds/amd_pps_perf.h index a049f80cfc7..30c6647cbeb 100644 --- a/src/amd/ds/amd_pps_perf.h +++ b/src/amd/ds/amd_pps_perf.h @@ -115,6 +115,12 @@ private: struct pps_amdgpu_bo **res_bos, uint32_t res_cnt, uint32_t ip_inst, uint32_t ring, uint64_t flags); int amdgpu_device_fence_wait(unsigned ip_inst, unsigned ring, uint64_t seq_no); + void amdgpu_pc_wait_idle(struct radeon_cmdbuf *cmd); + void radeon_emit_inhibit_clockgating(struct radeon_cmdbuf *cmd, bool inhibit); + void radeon_emit_spi_config_cntl(struct radeon_cmdbuf *cmd, bool enable); + void radeon_emit_perfctr_shaders(struct radeon_cmdbuf *cmd, unsigned shaders); + void radeon_emit_instance(struct radeon_cmdbuf *cmd, int se, int instance); + void radeon_emit_windowed_counters(struct radeon_cmdbuf *cmd, bool enable); inline void radeon_emit(struct radeon_cmdbuf *cmd, uint32_t value); inline void radeon_set_uconfig_reg(struct radeon_cmdbuf*cmd , unsigned reg, unsigned value); inline void radeon_set_uconfig_reg_seq(struct radeon_cmdbuf*cmd , unsigned reg, unsigned num);