Support low priority command queues

Related-to: LOCI-1124
Signed-off-by: Young Jin Yoon <young.jin.yoon@intel.com>
This commit is contained in:
Young Jin Yoon
2020-12-15 10:22:16 -08:00
committed by Compute-Runtime-Automation
parent 5440c83539
commit 571007cfe9
5 changed files with 114 additions and 3 deletions

View File

@@ -122,6 +122,7 @@ struct Device : _ze_device_handle_t {
virtual void setSysmanHandle(SysmanDevice *pSysmanDevice) = 0;
virtual SysmanDevice *getSysmanHandle() = 0;
virtual ze_result_t getCsrForOrdinalAndIndex(NEO::CommandStreamReceiver **csr, uint32_t ordinal, uint32_t index) = 0;
virtual ze_result_t getCsrForLowPriority(NEO::CommandStreamReceiver **csr) = 0;
virtual ze_result_t mapOrdinalForAvailableEngineGroup(uint32_t *ordinal) = 0;
};

View File

@@ -110,9 +110,13 @@ ze_result_t DeviceImp::createCommandQueue(const ze_command_queue_desc_t *desc,
NEO::CommandStreamReceiver *csr = nullptr;
uint32_t engineGroupIndex = desc->ordinal;
mapOrdinalForAvailableEngineGroup(&engineGroupIndex);
auto ret = getCsrForOrdinalAndIndex(&csr, desc->ordinal, desc->index);
if (ret != ZE_RESULT_SUCCESS) {
return ret;
if (desc->priority == ZE_COMMAND_QUEUE_PRIORITY_PRIORITY_LOW) {
getCsrForLowPriority(&csr);
} else {
auto ret = getCsrForOrdinalAndIndex(&csr, desc->ordinal, desc->index);
if (ret != ZE_RESULT_SUCCESS) {
return ret;
}
}
UNRECOVERABLE_IF(csr == nullptr);
@@ -775,6 +779,27 @@ ze_result_t DeviceImp::getCsrForOrdinalAndIndex(NEO::CommandStreamReceiver **csr
}
return ZE_RESULT_SUCCESS;
}
ze_result_t DeviceImp::getCsrForLowPriority(NEO::CommandStreamReceiver **csr) {
if (this->getNEODevice()->getNumAvailableDevices() > 1) {
for (auto &it : neoDevice->getDeviceById(0)->getEngines()) {
if (it.osContext->isLowPriority()) {
*csr = it.commandStreamReceiver;
return ZE_RESULT_SUCCESS;
}
}
} else {
for (auto &it : neoDevice->getEngines()) {
if (it.osContext->isLowPriority()) {
*csr = it.commandStreamReceiver;
return ZE_RESULT_SUCCESS;
}
}
}
// if the code falls through, we have no low priority context created by neoDevice.
UNRECOVERABLE_IF(true);
}
ze_result_t DeviceImp::mapOrdinalForAvailableEngineGroup(uint32_t *ordinal) {
NEO::Device *neoDevice = this->neoDevice;
if (this->getNEODevice()->getNumAvailableDevices() > 1) {

View File

@@ -74,6 +74,7 @@ struct DeviceImp : public Device {
void setSysmanHandle(SysmanDevice *pSysman) override;
SysmanDevice *getSysmanHandle() override;
ze_result_t getCsrForOrdinalAndIndex(NEO::CommandStreamReceiver **csr, uint32_t ordinal, uint32_t index) override;
ze_result_t getCsrForLowPriority(NEO::CommandStreamReceiver **csr) override;
ze_result_t mapOrdinalForAvailableEngineGroup(uint32_t *ordinal) override;
NEO::Device *neoDevice = nullptr;

View File

@@ -235,6 +235,10 @@ struct Mock<Device> : public Device {
return ZE_RESULT_SUCCESS;
}
ze_result_t getCsrForLowPriority(NEO::CommandStreamReceiver **csr) override {
return ZE_RESULT_SUCCESS;
}
ze_result_t mapOrdinalForAvailableEngineGroup(uint32_t *ordinal) override {
return ZE_RESULT_SUCCESS;
}

View File

@@ -504,6 +504,86 @@ HWTEST_F(CommandQueueIndirectAllocations, givenCommandQueueWhenExecutingCommandL
commandQueue->destroy();
}
using DeviceCreateCommandQueueTest = Test<DeviceFixture>;
TEST_F(DeviceCreateCommandQueueTest, givenLowPriorityDescWhenCreateCommandQueueIsCalledThenLowPriorityCsrIsAssigned) {
ze_command_queue_desc_t desc{};
desc.ordinal = 0u;
desc.index = 0u;
desc.priority = ZE_COMMAND_QUEUE_PRIORITY_PRIORITY_LOW;
ze_command_queue_handle_t commandQueueHandle = {};
ze_result_t res = device->createCommandQueue(&desc, &commandQueueHandle);
EXPECT_EQ(ZE_RESULT_SUCCESS, res);
auto commandQueue = static_cast<CommandQueueImp *>(L0::CommandQueue::fromHandle(commandQueueHandle));
EXPECT_NE(commandQueue, nullptr);
EXPECT_TRUE(commandQueue->getCsr()->getOsContext().isLowPriority());
NEO::CommandStreamReceiver *csr = nullptr;
device->getCsrForLowPriority(&csr);
EXPECT_EQ(commandQueue->getCsr(), csr);
commandQueue->destroy();
}
TEST_F(DeviceCreateCommandQueueTest, givenNormalPriorityDescWhenCreateCommandQueueIsCalledWithValidArgumentThenCsrIsAssignedWithOrdinalAndIndex) {
ze_command_queue_desc_t desc{};
desc.ordinal = 0u;
desc.index = 0u;
desc.priority = ZE_COMMAND_QUEUE_PRIORITY_NORMAL;
ze_command_queue_handle_t commandQueueHandle = {};
ze_result_t res = device->createCommandQueue(&desc, &commandQueueHandle);
EXPECT_EQ(ZE_RESULT_SUCCESS, res);
auto commandQueue = static_cast<CommandQueueImp *>(L0::CommandQueue::fromHandle(commandQueueHandle));
EXPECT_NE(commandQueue, nullptr);
EXPECT_FALSE(commandQueue->getCsr()->getOsContext().isLowPriority());
NEO::CommandStreamReceiver *csr = nullptr;
device->getCsrForOrdinalAndIndex(&csr, 0u, 0u);
EXPECT_EQ(commandQueue->getCsr(), csr);
commandQueue->destroy();
}
TEST_F(DeviceCreateCommandQueueTest, givenLowPriorityDescAndWithoutLowPriorityCsrWhenCreateCommandQueueIsCalledThenAbortIsThrown) {
// remove low priority EngineControl objects for negative testing
neoDevice->engines.erase(std::remove_if(
neoDevice->engines.begin(),
neoDevice->engines.end(),
[](EngineControl &p) { return p.osContext->isLowPriority(); }));
ze_command_queue_desc_t desc{};
desc.ordinal = 0u;
desc.index = 0u;
desc.priority = ZE_COMMAND_QUEUE_PRIORITY_PRIORITY_LOW;
ze_command_queue_handle_t commandQueueHandle = {};
ze_result_t res{};
EXPECT_THROW(res = device->createCommandQueue(&desc, &commandQueueHandle), std::exception);
}
using MultiDeviceCreateCommandQueueTest = Test<MultiDeviceFixture>;
TEST_F(MultiDeviceCreateCommandQueueTest, givenLowPriorityDescWhenCreateCommandQueueIsCalledThenLowPriorityCsrIsAssigned) {
auto device = driverHandle->devices[0];
ze_command_queue_desc_t desc{};
desc.ordinal = 0u;
desc.index = 0u;
desc.priority = ZE_COMMAND_QUEUE_PRIORITY_PRIORITY_LOW;
ze_command_queue_handle_t commandQueueHandle = {};
ze_result_t res = device->createCommandQueue(&desc, &commandQueueHandle);
EXPECT_EQ(ZE_RESULT_SUCCESS, res);
auto commandQueue = static_cast<CommandQueueImp *>(L0::CommandQueue::fromHandle(commandQueueHandle));
EXPECT_NE(commandQueue, nullptr);
EXPECT_TRUE(commandQueue->getCsr()->getOsContext().isLowPriority());
NEO::CommandStreamReceiver *csr = nullptr;
device->getCsrForLowPriority(&csr);
EXPECT_EQ(commandQueue->getCsr(), csr);
commandQueue->destroy();
}
using ContextCreateCommandQueueTest = Test<ContextFixture>;
TEST_F(ContextCreateCommandQueueTest, givenCallToContextCreateCommandQueueThenCallSucceeds) {