Refactor waitOnCompletionFence method in DrmMemoryManager

get completion address and value from command stream receiver

Related-To: NEO-6643

Signed-off-by: Mateusz Jablonski <mateusz.jablonski@intel.com>
This commit is contained in:
Mateusz Jablonski
2022-03-30 12:40:09 +00:00
committed by Compute-Runtime-Automation
parent e32f624bf4
commit 9d502dea25
9 changed files with 59 additions and 35 deletions

View File

@ -51,10 +51,10 @@ struct DrmCommandStreamMultiTileMemExecFixture {
executionEnvironment->prepareRootDeviceEnvironments(1u);
executionEnvironment->rootDeviceEnvironments[0]->setHwInfo(NEO::defaultHwInfo.get());
executionEnvironment->initializeMemoryManager();
device.reset(MockDevice::create<MockDevice>(executionEnvironment, 0));
osContext = std::make_unique<OsContextLinux>(*mock, 0u, EngineDescriptorHelper::getDefaultDescriptor(device->getDeviceBitfield()));
osContext->ensureContextInitialized();
VariableBackup<UltHwConfig> backup(&ultHwConfig);
ultHwConfig.useHwCsr = true;
device.reset(MockDevice::create<MockDevice>(executionEnvironment, 0));
}
void TearDown() {
@ -64,7 +64,6 @@ struct DrmCommandStreamMultiTileMemExecFixture {
DebugManagerStateRestore dbgRestore;
std::unique_ptr<VariableBackup<bool>> osLocalMemoryBackup;
std::unique_ptr<MockDevice> device;
std::unique_ptr<OsContext> osContext;
MockExecutionEnvironment *executionEnvironment = nullptr;
DrmMockCustom *mock = nullptr;
DrmMemoryManager *memoryManager = nullptr;
@ -73,7 +72,11 @@ struct DrmCommandStreamMultiTileMemExecFixture {
using DrmCommandStreamMultiTileMemExecTest = Test<DrmCommandStreamMultiTileMemExecFixture>;
HWCMDTEST_F(IGFX_XE_HP_CORE, DrmCommandStreamMultiTileMemExecTest, GivenDrmSupportsCompletionFenceAndVmBindWhenCallingCsrExecThenMultipleTagAllocationIsPassed) {
auto osContext = std::make_unique<OsContextLinux>(*mock, 0u, EngineDescriptorHelper::getDefaultDescriptor(device->getDeviceBitfield()));
osContext->ensureContextInitialized();
auto *testCsr = new TestedDrmCommandStreamReceiver<FamilyType>(*executionEnvironment, 0, device->getDeviceBitfield());
auto device = std::unique_ptr<MockDevice>(MockDevice::create<MockDevice>(executionEnvironment, 0));
device->resetCommandStreamReceiver(testCsr);
EXPECT_EQ(2u, testCsr->activePartitions);
testCsr->setupContext(*osContext.get());

View File

@ -5920,27 +5920,4 @@ TEST_F(DrmMemoryManagerTest, givenCompletionFenceEnabledWhenHandlingCompletionOf
memoryManager->freeGraphicsMemory(allocation);
}
HWTEST_F(DrmMemoryManagerTest, givenCompletionFenceEnabledWhenHandlingCompletionAndTagAddressIsNullThenDoNotCallWaitUserFence) {
mock->ioctl_expected.total = -1;
VariableBackup<bool> backupFenceSupported{&mock->completionFenceSupported, true};
VariableBackup<bool> backupVmBindCallParent{&mock->isVmBindAvailableCall.callParent, false};
VariableBackup<bool> backupVmBindReturnValue{&mock->isVmBindAvailableCall.returnValue, true};
auto allocation = memoryManager->allocateGraphicsMemoryWithProperties(MockAllocationProperties{rootDeviceIndex, 1024, AllocationType::COMMAND_BUFFER});
auto engine = memoryManager->getRegisteredEngines()[0];
allocation->updateTaskCount(2, engine.osContext->getContextId());
auto testCsr = static_cast<TestedDrmCommandStreamReceiver<FamilyType> *>(engine.commandStreamReceiver);
auto backupTagAddress = testCsr->tagAddress;
testCsr->tagAddress = nullptr;
memoryManager->handleFenceCompletion(allocation);
EXPECT_EQ(0u, mock->waitUserFenceCall.called);
testCsr->tagAddress = backupTagAddress;
memoryManager->freeGraphicsMemory(allocation);
}
} // namespace NEO

View File

@ -319,6 +319,14 @@ class CommandStreamReceiver {
MOCKABLE_VIRTUAL bool isGpuHangDetected() const;
virtual uint64_t getCompletionAddress() {
return 0;
}
virtual uint32_t getCompletionValue(const GraphicsAllocation &gfxAllocation) {
return 0;
}
protected:
void cleanupResources();
void printDeviceIndex();

View File

@ -62,6 +62,10 @@ class DrmCommandStreamReceiver : public DeviceCommandStreamReceiver<GfxFamily> {
gemCloseWorkerOperationMode = gemCloseWorkerMode::gemCloseWorkerInactive;
}
uint64_t getCompletionAddress() override;
uint32_t getCompletionValue(const GraphicsAllocation &gfxAllocation) override;
void printBOsForSubmit(ResidencyContainer &allocationsForResidency, GraphicsAllocation &cmdBufferAllocation);
using CommandStreamReceiver::pageTableManager;

View File

@ -316,4 +316,16 @@ inline bool DrmCommandStreamReceiver<GfxFamily>::isUserFenceWaitActive() {
return (this->drm->isVmBindAvailable() && useUserFenceWait);
}
template <typename GfxFamily>
uint64_t DrmCommandStreamReceiver<GfxFamily>::getCompletionAddress() {
uint64_t completionFenceAddress = castToUint64(const_cast<uint32_t *>(getTagAddress()));
completionFenceAddress += Drm::completionFenceOffset;
return completionFenceAddress;
}
template <typename GfxFamily>
uint32_t DrmCommandStreamReceiver<GfxFamily>::getCompletionValue(const GraphicsAllocation &gfxAllocation) {
auto osContextId = osContext->getContextId();
return gfxAllocation.getTaskCount(osContextId);
}
} // namespace NEO

View File

@ -1526,14 +1526,13 @@ void DrmMemoryManager::waitOnCompletionFence(GraphicsAllocation *allocation) {
uint32_t activeHwContexts = csr->getActivePartitions();
auto osContextId = osContext->getContextId();
auto allocationTaskCount = allocation->getTaskCount(osContextId);
uint64_t completionFenceAddress = castToUint64(const_cast<uint32_t *>(csr->getTagAddress()));
auto allocationTaskCount = csr->getCompletionValue(*allocation);
uint64_t completionFenceAddress = csr->getCompletionAddress();
if (completionFenceAddress == 0) {
continue;
}
if (allocation->isUsedByOsContext(osContextId)) {
completionFenceAddress += Drm::completionFenceOffset;
Drm &drm = getDrm(csr->getRootDeviceIndex());
auto &ctxVector = static_cast<const OsContextLinux *>(osContext)->getDrmContextIds();

View File

@ -64,6 +64,13 @@ struct CommandStreamReceiverTest : public DeviceFixture,
InternalAllocationStorage *internalAllocationStorage;
};
TEST_F(CommandStreamReceiverTest, givenOsAgnosticCsrWhenGettingCompletionValueOrAddressThenZeroIsReturned) {
EXPECT_EQ(0u, commandStreamReceiver->getCompletionAddress());
MockGraphicsAllocation allocation{};
EXPECT_EQ(0u, commandStreamReceiver->getCompletionValue(allocation));
}
HWTEST_F(CommandStreamReceiverTest, WhenCreatingCsrThenDefaultValuesAreSet) {
auto &csr = pDevice->getUltCommandStreamReceiver<FamilyType>();
EXPECT_EQ(0u, csr.peekTaskLevel());

View File

@ -9,7 +9,7 @@ set(NEO_CORE_OS_INTERFACE_TESTS_LINUX
${CMAKE_CURRENT_SOURCE_DIR}/device_factory_tests_linux.cpp
${CMAKE_CURRENT_SOURCE_DIR}/device_factory_tests_linux.h
${CMAKE_CURRENT_SOURCE_DIR}/drm_bind_tests.cpp
${CMAKE_CURRENT_SOURCE_DIR}/drm_command_stream_l0_tests.cpp
${CMAKE_CURRENT_SOURCE_DIR}/drm_command_stream_tests.cpp
${CMAKE_CURRENT_SOURCE_DIR}${BRANCH_DIR_SUFFIX}drm_engine_info_tests.cpp
${CMAKE_CURRENT_SOURCE_DIR}/drm_mock_impl.h
${CMAKE_CURRENT_SOURCE_DIR}/drm_query_topology_upstream_tests.cpp

View File

@ -17,6 +17,7 @@
#include "shared/test/common/libult/linux/drm_mock.h"
#include "shared/test/common/mocks/linux/mock_drm_command_stream_receiver.h"
#include "shared/test/common/mocks/mock_execution_environment.h"
#include "shared/test/common/mocks/mock_graphics_allocation.h"
#include "shared/test/common/os_interface/linux/device_command_stream_fixture.h"
#include "shared/test/common/test_macros/test.h"
@ -28,7 +29,7 @@ extern ApiSpecificConfig::ApiType apiTypeForUlts;
} //namespace NEO
using namespace NEO;
class DrmCommandStreamTestL0 : public ::testing::Test {
class DrmCommandStreamTest : public ::testing::Test {
public:
template <typename GfxFamily>
void SetUpT() {
@ -89,13 +90,26 @@ class DrmCommandStreamTestL0 : public ::testing::Test {
};
template <typename GfxFamily>
struct MockDrmCsrL0 : public DrmCommandStreamReceiver<GfxFamily> {
struct MockDrmCsr : public DrmCommandStreamReceiver<GfxFamily> {
using DrmCommandStreamReceiver<GfxFamily>::DrmCommandStreamReceiver;
using DrmCommandStreamReceiver<GfxFamily>::dispatchMode;
};
HWTEST_TEMPLATED_F(DrmCommandStreamTestL0, givenL0ApiConfigWhenCreatingDrmCsrThenEnableImmediateDispatch) {
HWTEST_TEMPLATED_F(DrmCommandStreamTest, givenL0ApiConfigWhenCreatingDrmCsrThenEnableImmediateDispatch) {
VariableBackup<ApiSpecificConfig::ApiType> backup(&apiTypeForUlts, ApiSpecificConfig::L0);
MockDrmCsrL0<FamilyType> csr(executionEnvironment, 0, 1, gemCloseWorkerMode::gemCloseWorkerInactive);
MockDrmCsr<FamilyType> csr(executionEnvironment, 0, 1, gemCloseWorkerMode::gemCloseWorkerInactive);
EXPECT_EQ(DispatchMode::ImmediateDispatch, csr.dispatchMode);
}
HWTEST_TEMPLATED_F(DrmCommandStreamTest, whenGettingCompletionValueThenTaskCountOfAllocationIsReturned) {
MockGraphicsAllocation allocation{};
uint32_t expectedValue = 0x1234;
allocation.updateTaskCount(expectedValue, osContext->getContextId());
EXPECT_EQ(expectedValue, csr->getCompletionValue(allocation));
}
HWTEST_TEMPLATED_F(DrmCommandStreamTest, whenGettingCompletionAddressThenOffsettedTagAddressIsReturned) {
uint64_t tagAddress = castToUint64(const_cast<uint32_t *>(csr->getTagAddress()));
auto expectedAddress = tagAddress + Drm::completionFenceOffset;
EXPECT_EQ(expectedAddress, csr->getCompletionAddress());
}