diff --git a/tests/kfdtest/include/pm4_pkt_struct_common.h b/tests/kfdtest/include/pm4_pkt_struct_common.h index d3b78427b9..44950a7760 100644 --- a/tests/kfdtest/include/pm4_pkt_struct_common.h +++ b/tests/kfdtest/include/pm4_pkt_struct_common.h @@ -255,6 +255,97 @@ typedef struct _PM4_MEC_INDIRECT_BUFFER } PM4MEC_INDIRECT_BUFFER, *PPM4MEC_INDIRECT_BUFFER; +//--------------------MEC_WAIT_REG_MEM-------------------- + +enum MEC_WAIT_REG_MEM_function_enum { + function__mec_wait_reg_mem__always_pass = 0, + function__mec_wait_reg_mem__less_than_ref_value = 1, + function__mec_wait_reg_mem__less_than_equal_to_the_ref_value = 2, + function__mec_wait_reg_mem__equal_to_the_reference_value = 3, + function__mec_wait_reg_mem__not_equal_reference_value = 4, + function__mec_wait_reg_mem__greater_than_or_equal_reference_value = 5, + function__mec_wait_reg_mem__greater_than_reference_value = 6 }; + +enum MEC_WAIT_REG_MEM_mem_space_enum { + mem_space__mec_wait_reg_mem__register_space = 0, + mem_space__mec_wait_reg_mem__memory_space = 1 }; + +enum MEC_WAIT_REG_MEM_operation_enum { + operation__mec_wait_reg_mem__wait_reg_mem = 0, + operation__mec_wait_reg_mem__wr_wait_wr_reg = 1, + operation__mec_wait_reg_mem__wait_mem_preemptable = 3 }; + + +typedef struct PM4_MEC_WAIT_REG_MEM +{ + union + { + PM4_TYPE_3_HEADER header; ///header + uint32_t ordinal1; + }; + + union + { + struct + { + MEC_WAIT_REG_MEM_function_enum function:3; + uint32_t reserved1:1; + MEC_WAIT_REG_MEM_mem_space_enum mem_space:2; + MEC_WAIT_REG_MEM_operation_enum operation:2; + uint32_t reserved2:24; + } bitfields2; + uint32_t ordinal2; + }; + + union + { + struct + { + uint32_t reserved3:2; + uint32_t mem_poll_addr_lo:30; + } bitfields3a; + struct + { + uint32_t reg_poll_addr:18; + uint32_t reserved4:14; + } bitfields3b; + struct + { + uint32_t reg_write_addr1:18; + uint32_t reserved5:14; + } bitfields3c; + uint32_t ordinal3; + }; + + union + { + uint32_t mem_poll_addr_hi; + + struct + { + uint32_t reg_write_addr2:18; + uint32_t reserved6:14; + } bitfields4b; + uint32_t ordinal4; + }; + + uint32_t reference; + + uint32_t mask; + + union + { + struct + { + uint32_t poll_interval:16; + uint32_t reserved7:15; + uint32_t optimize_ace_offload_mode:1; + } bitfields7; + uint32_t ordinal7; + }; + +} PM4MEC_WAIT_REG_MEM, *PPM4MEC_WAIT_REG_MEM; + //--------------------MEC_WRITE_DATA-------------------- enum MEC_WRITE_DATA_dst_sel_enum { dst_sel_mec_write_data_MEM_MAPPED_REGISTER_0 = 0, dst_sel_mec_write_data_TC_L2_2 = 2, dst_sel_mec_write_data_GDS_3 = 3, dst_sel_mec_write_data_MEMORY_5 = 5 }; diff --git a/tests/kfdtest/src/PM4Packet.cpp b/tests/kfdtest/src/PM4Packet.cpp index 3571c3ee81..3d26ef3fe6 100644 --- a/tests/kfdtest/src/PM4Packet.cpp +++ b/tests/kfdtest/src/PM4Packet.cpp @@ -362,3 +362,46 @@ PM4NopPacket::PM4NopPacket(unsigned int count): m_packetSize(count * 4) { m_packetData = reinterpret_cast(AllocPacket()); InitPM4Header(*m_packetData, IT_NOP); } + +PM4WaitRegMemPacket::PM4WaitRegMemPacket(bool memory, uint64_t addr, + uint32_t ref, uint16_t pollInterval) { + InitPacket(function__mec_wait_reg_mem__equal_to_the_reference_value, + memory ? + mem_space__mec_wait_reg_mem__memory_space : + mem_space__mec_wait_reg_mem__register_space, + operation__mec_wait_reg_mem__wait_reg_mem, + addr, ref, 0xffffffff, pollInterval); +} +PM4WaitRegMemPacket::PM4WaitRegMemPacket(unsigned int function, + unsigned int space, + unsigned int operation, + uint64_t addr, uint32_t ref, + uint32_t mask, uint16_t pollInterval) { + InitPacket(function, space, operation, addr, ref, mask, pollInterval); +} + +void PM4WaitRegMemPacket::InitPacket(unsigned int function, + unsigned int space, + unsigned int operation, + uint64_t addr, uint32_t ref, + uint32_t mask, uint16_t pollInterval) { + memset(&m_packetData, 0, SizeInBytes()); + InitPM4Header(m_packetData.header, IT_WAIT_REG_MEM); + + m_packetData.bitfields2.function = (MEC_WAIT_REG_MEM_function_enum)function; + m_packetData.bitfields2.mem_space = (MEC_WAIT_REG_MEM_mem_space_enum)space; + m_packetData.bitfields2.operation = (MEC_WAIT_REG_MEM_operation_enum)operation; + + m_packetData.ordinal3 = addr; + m_packetData.mem_poll_addr_hi = addr >> 32; + + m_packetData.reference = ref; + m_packetData.mask = mask; + + m_packetData.bitfields7.poll_interval = pollInterval; + m_packetData.bitfields7.optimize_ace_offload_mode = 1; +} + +unsigned int PM4WaitRegMemPacket::SizeInBytes() const { + return sizeof(m_packetData); +} diff --git a/tests/kfdtest/src/PM4Packet.hpp b/tests/kfdtest/src/PM4Packet.hpp index c02ef290ad..e7049c3fa8 100644 --- a/tests/kfdtest/src/PM4Packet.hpp +++ b/tests/kfdtest/src/PM4Packet.hpp @@ -224,4 +224,25 @@ class PM4NopPacket : public PM4Packet { PM4_TYPE_3_HEADER *m_packetData; }; +// @class PM4WaitRegMemPacket +class PM4WaitRegMemPacket : public PM4Packet { + public: + PM4WaitRegMemPacket(void) {} + PM4WaitRegMemPacket(bool memory, uint64_t addr, uint32_t ref, uint16_t pollInterval); + PM4WaitRegMemPacket(unsigned int function, unsigned int space, unsigned int operation, + uint64_t addr, uint32_t ref, uint32_t mask, uint16_t pollInterval); + virtual ~PM4WaitRegMemPacket(void) {} + + // @returns Packet size in bytes + virtual unsigned int SizeInBytes() const; + // @returns Pointer to the packet + virtual const void *GetPacket() const { return &m_packetData; } + + void InitPacket(unsigned int function, unsigned int space, unsigned int operation, + uint64_t addr, uint32_t ref, uint32_t mask, uint16_t pollInterval); + + private: + PM4MEC_WAIT_REG_MEM m_packetData; +}; + #endif // __KFD_PM4_PACKET__H__