mirror of
https://github.com/intel/compute-runtime.git
synced 2026-01-05 09:09:04 +08:00
Fail when handle cannot be obtain for an allocation
If a handle cannot be obtained, like PRIME_HANDLE_TO_FD, then properly check for the error and propagate it upwards. Signed-off-by: Jaime Arteaga <jaime.a.arteaga.molina@intel.com>
This commit is contained in:
committed by
Compute-Runtime-Automation
parent
acb8186744
commit
4391ad21bb
@@ -169,10 +169,10 @@ class GraphicsAllocation : public IDNode<GraphicsAllocation> {
|
||||
bool isResidencyTaskCountBelow(uint32_t taskCount, uint32_t contextId) const { return !isResident(contextId) || getResidencyTaskCount(contextId) < taskCount; }
|
||||
|
||||
virtual std::string getAllocationInfoString() const;
|
||||
virtual uint64_t peekInternalHandle(MemoryManager *memoryManager) { return 0llu; }
|
||||
virtual int peekInternalHandle(MemoryManager *memoryManager, uint64_t &handle) { return 0; }
|
||||
|
||||
virtual uint64_t peekInternalHandle(MemoryManager *memoryManager, uint32_t handleId) {
|
||||
return 0u;
|
||||
virtual int peekInternalHandle(MemoryManager *memoryManager, uint32_t handleId, uint64_t &handle) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
virtual uint32_t getNumHandles() {
|
||||
|
||||
@@ -37,20 +37,24 @@ std::string DrmAllocation::getAllocationInfoString() const {
|
||||
return ss.str();
|
||||
}
|
||||
|
||||
uint64_t DrmAllocation::peekInternalHandle(MemoryManager *memoryManager) {
|
||||
if (handles[0] != std::numeric_limits<uint32_t>::max()) {
|
||||
return handles[0];
|
||||
}
|
||||
handles[0] = static_cast<uint64_t>((static_cast<DrmMemoryManager *>(memoryManager))->obtainFdFromHandle(getBO()->peekHandle(), this->rootDeviceIndex));
|
||||
return handles[0];
|
||||
int DrmAllocation::peekInternalHandle(MemoryManager *memoryManager, uint64_t &handle) {
|
||||
return peekInternalHandle(memoryManager, 0u, handle);
|
||||
}
|
||||
|
||||
uint64_t DrmAllocation::peekInternalHandle(MemoryManager *memoryManager, uint32_t handleId) {
|
||||
if (handles[handleId] != std::numeric_limits<uint32_t>::max()) {
|
||||
return handles[handleId];
|
||||
int DrmAllocation::peekInternalHandle(MemoryManager *memoryManager, uint32_t handleId, uint64_t &handle) {
|
||||
if (handles[handleId] != std::numeric_limits<uint64_t>::max()) {
|
||||
handle = handles[handleId];
|
||||
return 0;
|
||||
}
|
||||
handles[handleId] = static_cast<uint64_t>((static_cast<DrmMemoryManager *>(memoryManager))->obtainFdFromHandle(getBufferObjectToModify(handleId)->peekHandle(), this->rootDeviceIndex));
|
||||
return handles[handleId];
|
||||
|
||||
int64_t ret = static_cast<int64_t>((static_cast<DrmMemoryManager *>(memoryManager))->obtainFdFromHandle(getBufferObjectToModify(handleId)->peekHandle(), this->rootDeviceIndex));
|
||||
if (ret < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
handle = handles[handleId] = ret;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void DrmAllocation::setCachePolicy(CachePolicy memType) {
|
||||
|
||||
@@ -40,7 +40,7 @@ class DrmAllocation : public GraphicsAllocation {
|
||||
DrmAllocation(uint32_t rootDeviceIndex, size_t numGmms, AllocationType allocationType, BufferObject *bo, void *ptrIn, size_t sizeIn, osHandle sharedHandle, MemoryPool pool, uint64_t canonizedGpuAddress)
|
||||
: GraphicsAllocation(rootDeviceIndex, numGmms, allocationType, ptrIn, sizeIn, sharedHandle, pool, MemoryManager::maxOsContextCount, canonizedGpuAddress), bufferObjects(EngineLimits::maxHandleCount) {
|
||||
bufferObjects[0] = bo;
|
||||
handles.resize(EngineLimits::maxHandleCount, std::numeric_limits<uint32_t>::max());
|
||||
handles.resize(EngineLimits::maxHandleCount, std::numeric_limits<uint64_t>::max());
|
||||
}
|
||||
|
||||
DrmAllocation(uint32_t rootDeviceIndex, AllocationType allocationType, BufferObject *bo, void *ptrIn, uint64_t canonizedGpuAddress, size_t sizeIn, MemoryPool pool)
|
||||
@@ -49,7 +49,7 @@ class DrmAllocation : public GraphicsAllocation {
|
||||
DrmAllocation(uint32_t rootDeviceIndex, size_t numGmms, AllocationType allocationType, BufferObject *bo, void *ptrIn, uint64_t canonizedGpuAddress, size_t sizeIn, MemoryPool pool)
|
||||
: GraphicsAllocation(rootDeviceIndex, numGmms, allocationType, ptrIn, canonizedGpuAddress, 0, sizeIn, pool, MemoryManager::maxOsContextCount), bufferObjects(EngineLimits::maxHandleCount) {
|
||||
bufferObjects[0] = bo;
|
||||
handles.resize(EngineLimits::maxHandleCount, std::numeric_limits<uint32_t>::max());
|
||||
handles.resize(EngineLimits::maxHandleCount, std::numeric_limits<uint64_t>::max());
|
||||
}
|
||||
|
||||
DrmAllocation(uint32_t rootDeviceIndex, AllocationType allocationType, BufferObjects &bos, void *ptrIn, uint64_t canonizedGpuAddress, size_t sizeIn, MemoryPool pool)
|
||||
@@ -58,7 +58,7 @@ class DrmAllocation : public GraphicsAllocation {
|
||||
DrmAllocation(uint32_t rootDeviceIndex, size_t numGmms, AllocationType allocationType, BufferObjects &bos, void *ptrIn, uint64_t canonizedGpuAddress, size_t sizeIn, MemoryPool pool)
|
||||
: GraphicsAllocation(rootDeviceIndex, numGmms, allocationType, ptrIn, canonizedGpuAddress, 0, sizeIn, pool, MemoryManager::maxOsContextCount),
|
||||
bufferObjects(bos) {
|
||||
handles.resize(EngineLimits::maxHandleCount, std::numeric_limits<uint32_t>::max());
|
||||
handles.resize(EngineLimits::maxHandleCount, std::numeric_limits<uint64_t>::max());
|
||||
}
|
||||
|
||||
~DrmAllocation() override;
|
||||
@@ -74,7 +74,7 @@ class DrmAllocation : public GraphicsAllocation {
|
||||
const BufferObjects &getBOs() const {
|
||||
return this->bufferObjects;
|
||||
}
|
||||
BufferObject *&getBufferObjectToModify(uint32_t handleIndex) {
|
||||
MOCKABLE_VIRTUAL BufferObject *&getBufferObjectToModify(uint32_t handleIndex) {
|
||||
return bufferObjects[handleIndex];
|
||||
}
|
||||
|
||||
@@ -90,9 +90,9 @@ class DrmAllocation : public GraphicsAllocation {
|
||||
this->numHandles = numHandles;
|
||||
}
|
||||
|
||||
uint64_t peekInternalHandle(MemoryManager *memoryManager) override;
|
||||
int peekInternalHandle(MemoryManager *memoryManager, uint64_t &handle) override;
|
||||
|
||||
uint64_t peekInternalHandle(MemoryManager *memoryManager, uint32_t handleId) override;
|
||||
int peekInternalHandle(MemoryManager *memoryManager, uint32_t handleId, uint64_t &handle) override;
|
||||
|
||||
bool setCacheRegion(Drm *drm, CacheRegion regionIndex);
|
||||
bool setCacheAdvice(Drm *drm, size_t regionSize, CacheRegion regionIndex);
|
||||
|
||||
@@ -978,7 +978,11 @@ GraphicsAllocation *DrmMemoryManager::createGraphicsAllocationFromExistingStorag
|
||||
properties.size = defaultAlloc->getUnderlyingBufferSize();
|
||||
properties.gpuAddress = castToUint64(ptr);
|
||||
|
||||
auto internalHandle = defaultAlloc->peekInternalHandle(this);
|
||||
uint64_t internalHandle = 0;
|
||||
int ret = defaultAlloc->peekInternalHandle(this, internalHandle);
|
||||
if (ret < 0) {
|
||||
return nullptr;
|
||||
}
|
||||
return createUSMHostAllocationFromSharedHandle(static_cast<osHandle>(internalHandle), properties, true);
|
||||
} else {
|
||||
return allocateGraphicsMemoryWithProperties(properties, ptr);
|
||||
@@ -1114,7 +1118,10 @@ int DrmMemoryManager::obtainFdFromHandle(int boHandle, uint32_t rootDeviceIndex)
|
||||
openFd.flags = ioctlHelper->getFlagsForPrimeHandleToFd();
|
||||
openFd.handle = boHandle;
|
||||
|
||||
ioctlHelper->ioctl(DrmIoctl::PrimeHandleToFd, &openFd);
|
||||
int ret = ioctlHelper->ioctl(DrmIoctl::PrimeHandleToFd, &openFd);
|
||||
if (ret < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
return openFd.fileDescriptor;
|
||||
}
|
||||
|
||||
@@ -72,8 +72,9 @@ class WddmAllocation : public GraphicsAllocation {
|
||||
handles[handleIndex] = handle;
|
||||
}
|
||||
|
||||
uint64_t peekInternalHandle(MemoryManager *memoryManager) override {
|
||||
return ntSecureHandle;
|
||||
int peekInternalHandle(MemoryManager *memoryManager, uint64_t &handle) override {
|
||||
handle = ntSecureHandle;
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint64_t *getSharedHandleToModify() {
|
||||
|
||||
@@ -557,8 +557,10 @@ void WddmMemoryManager::freeGraphicsMemoryImpl(GraphicsAllocation *gfxAllocation
|
||||
for (auto handleId = 0u; handleId < gfxAllocation->getNumGmms(); handleId++) {
|
||||
delete gfxAllocation->getGmm(handleId);
|
||||
}
|
||||
if (input->peekInternalHandle(nullptr) != 0u) {
|
||||
[[maybe_unused]] auto status = SysCalls::closeHandle(reinterpret_cast<void *>(reinterpret_cast<uintptr_t *>(input->peekInternalHandle(nullptr))));
|
||||
uint64_t handle = 0;
|
||||
int ret = input->peekInternalHandle(nullptr, handle);
|
||||
if (ret == 0) {
|
||||
[[maybe_unused]] auto status = SysCalls::closeHandle(reinterpret_cast<void *>(reinterpret_cast<uintptr_t *>(handle)));
|
||||
DEBUG_BREAK_IF(!status);
|
||||
}
|
||||
|
||||
|
||||
@@ -160,6 +160,15 @@ class TestedDrmMemoryManager : public MemoryManagerCreate<DrmMemoryManager> {
|
||||
|
||||
bool failOnfindAndReferenceSharedBufferObject = false;
|
||||
|
||||
bool failOnObtainFdFromHandle = false;
|
||||
|
||||
int obtainFdFromHandle(int boHandle, uint32_t rootDeviceIndex) override {
|
||||
if (failOnObtainFdFromHandle) {
|
||||
return -1;
|
||||
}
|
||||
return DrmMemoryManager::obtainFdFromHandle(boHandle, rootDeviceIndex);
|
||||
}
|
||||
|
||||
ExecutionEnvironment *executionEnvironment = nullptr;
|
||||
|
||||
protected:
|
||||
|
||||
@@ -227,7 +227,9 @@ TEST(GraphicsAllocationTest, givenAlwaysResidentAllocationWhenUpdateTaskCountThe
|
||||
|
||||
TEST(GraphicsAllocationTest, givenDefaultGraphicsAllocationWhenInternalHandleIsBeingObtainedThenZeroIsReturned) {
|
||||
MockGraphicsAllocation graphicsAllocation;
|
||||
EXPECT_EQ(0llu, graphicsAllocation.peekInternalHandle(nullptr));
|
||||
uint64_t handle = 0;
|
||||
graphicsAllocation.peekInternalHandle(nullptr, handle);
|
||||
EXPECT_EQ(0ull, handle);
|
||||
}
|
||||
|
||||
TEST(GraphicsAllocationTest, givenDefaultGraphicsAllocationWhenGettingNumHandlesThenZeroIsReturned) {
|
||||
|
||||
@@ -131,6 +131,46 @@ TEST_F(DrmMemoryManagerLocalMemoryPrelimTest, givenMultiRootDeviceEnvironmentAnd
|
||||
executionEnvironment->rootDeviceEnvironments[0]->osInterface.reset(osInterface);
|
||||
}
|
||||
|
||||
TEST_F(DrmMemoryManagerLocalMemoryPrelimTest, givenMultiRootDeviceEnvironmentAndMemoryInfoWhenCreateMultiGraphicsAllocationAndObtainFdFromHandleFailsThenNullptrIsReturned) {
|
||||
uint32_t rootDevicesNumber = 3u;
|
||||
MultiGraphicsAllocation multiGraphics(rootDevicesNumber);
|
||||
RootDeviceIndicesContainer rootDeviceIndices;
|
||||
auto osInterface = executionEnvironment->rootDeviceEnvironments[0]->osInterface.release();
|
||||
|
||||
executionEnvironment->prepareRootDeviceEnvironments(rootDevicesNumber);
|
||||
for (uint32_t i = 0; i < rootDevicesNumber; i++) {
|
||||
executionEnvironment->rootDeviceEnvironments[i]->setHwInfo(defaultHwInfo.get());
|
||||
executionEnvironment->rootDeviceEnvironments[i]->initGmm();
|
||||
auto mock = new DrmQueryMock(*executionEnvironment->rootDeviceEnvironments[i]);
|
||||
|
||||
std::vector<MemoryRegion> regionInfo(2);
|
||||
regionInfo[0].region = {drm_i915_gem_memory_class::I915_MEMORY_CLASS_SYSTEM, 0};
|
||||
regionInfo[1].region = {drm_i915_gem_memory_class::I915_MEMORY_CLASS_DEVICE, DrmMockHelper::getEngineOrMemoryInstanceValue(0, 0)};
|
||||
|
||||
mock->memoryInfo.reset(new MemoryInfo(regionInfo, *mock));
|
||||
mock->queryEngineInfo();
|
||||
mock->ioctlCallsCount = 0;
|
||||
executionEnvironment->rootDeviceEnvironments[i]->osInterface = std::make_unique<OSInterface>();
|
||||
executionEnvironment->rootDeviceEnvironments[i]->osInterface->setDriverModel(std::unique_ptr<DriverModel>(mock));
|
||||
executionEnvironment->rootDeviceEnvironments[i]->memoryOperationsInterface = DrmMemoryOperationsHandler::create(*mock, 0u);
|
||||
executionEnvironment->rootDeviceEnvironments[i]->initGmm();
|
||||
|
||||
rootDeviceIndices.push_back(i);
|
||||
}
|
||||
|
||||
memoryManager = new TestedDrmMemoryManager(true, false, false, *executionEnvironment);
|
||||
executionEnvironment->memoryManager.reset(memoryManager);
|
||||
|
||||
size_t size = 4096u;
|
||||
AllocationProperties properties(rootDeviceIndex, true, size, AllocationType::BUFFER_HOST_MEMORY, false, {});
|
||||
|
||||
memoryManager->failOnObtainFdFromHandle = true;
|
||||
auto ptr = memoryManager->createMultiGraphicsAllocationInSystemMemoryPool(rootDeviceIndices, properties, multiGraphics);
|
||||
EXPECT_EQ(ptr, nullptr);
|
||||
|
||||
executionEnvironment->rootDeviceEnvironments[0]->osInterface.reset(osInterface);
|
||||
}
|
||||
|
||||
TEST_F(DrmMemoryManagerLocalMemoryPrelimTest, givenMultiRootDeviceEnvironmentAndMemoryInfoWhenCreateMultiGraphicsAllocationAndImportFailsThenNullptrIsReturned) {
|
||||
uint32_t rootDevicesNumber = 3u;
|
||||
MultiGraphicsAllocation multiGraphics(rootDevicesNumber);
|
||||
|
||||
@@ -452,7 +452,25 @@ TEST_F(DrmMemoryManagerTest, whenPeekInternalHandleIsCalledThenBoIsReturned) {
|
||||
mock->outputFd = 1337;
|
||||
auto allocation = static_cast<DrmAllocation *>(this->memoryManager->allocateGraphicsMemoryWithProperties(createAllocationProperties(rootDeviceIndex, 10 * MemoryConstants::pageSize, true)));
|
||||
ASSERT_NE(allocation->getBO(), nullptr);
|
||||
ASSERT_EQ(allocation->peekInternalHandle(this->memoryManager), static_cast<uint64_t>(1337));
|
||||
uint64_t handle = 0;
|
||||
int ret = allocation->peekInternalHandle(this->memoryManager, handle);
|
||||
ASSERT_EQ(ret, 0);
|
||||
ASSERT_EQ(handle, static_cast<uint64_t>(1337));
|
||||
|
||||
memoryManager->freeGraphicsMemory(allocation);
|
||||
}
|
||||
|
||||
TEST_F(DrmMemoryManagerTest, whenPeekInternalHandleIsCalledAndObtainFdFromHandleFailsThenErrorIsReturned) {
|
||||
mock->ioctl_expected.gemUserptr = 1;
|
||||
mock->ioctl_expected.gemWait = 1;
|
||||
mock->ioctl_expected.gemClose = 1;
|
||||
mock->outputFd = 1337;
|
||||
auto allocation = static_cast<DrmAllocation *>(this->memoryManager->allocateGraphicsMemoryWithProperties(createAllocationProperties(rootDeviceIndex, 10 * MemoryConstants::pageSize, true)));
|
||||
ASSERT_NE(allocation->getBO(), nullptr);
|
||||
memoryManager->failOnObtainFdFromHandle = true;
|
||||
uint64_t handle = 0;
|
||||
int ret = allocation->peekInternalHandle(this->memoryManager, handle);
|
||||
ASSERT_EQ(ret, -1);
|
||||
|
||||
memoryManager->freeGraphicsMemory(allocation);
|
||||
}
|
||||
@@ -469,11 +487,18 @@ TEST_F(DrmMemoryManagerTest, whenCallingPeekInternalHandleSeveralTimesThenSameHa
|
||||
ASSERT_NE(allocation->getBO(), nullptr);
|
||||
|
||||
EXPECT_EQ(mock->outputFd, static_cast<int32_t>(expectedFd));
|
||||
uint64_t handle0 = allocation->peekInternalHandle(this->memoryManager);
|
||||
uint64_t handle0 = 0;
|
||||
int ret = allocation->peekInternalHandle(this->memoryManager, handle0);
|
||||
ASSERT_EQ(ret, 0);
|
||||
EXPECT_NE(mock->outputFd, static_cast<int32_t>(expectedFd));
|
||||
|
||||
uint64_t handle1 = allocation->peekInternalHandle(this->memoryManager);
|
||||
uint64_t handle2 = allocation->peekInternalHandle(this->memoryManager);
|
||||
uint64_t handle1 = 0;
|
||||
uint64_t handle2 = 0;
|
||||
|
||||
ret = allocation->peekInternalHandle(this->memoryManager, handle1);
|
||||
ASSERT_EQ(ret, 0);
|
||||
ret = allocation->peekInternalHandle(this->memoryManager, handle2);
|
||||
ASSERT_EQ(ret, 0);
|
||||
|
||||
ASSERT_EQ(handle0, expectedFd);
|
||||
ASSERT_EQ(handle1, expectedFd);
|
||||
@@ -491,8 +516,11 @@ TEST_F(DrmMemoryManagerTest, whenPeekInternalHandleWithHandleIdIsCalledThenBoIsR
|
||||
auto allocation = static_cast<DrmAllocation *>(this->memoryManager->allocateGraphicsMemoryWithProperties(createAllocationProperties(rootDeviceIndex, 10 * MemoryConstants::pageSize, true)));
|
||||
ASSERT_NE(allocation->getBO(), nullptr);
|
||||
|
||||
uint64_t handle = 0;
|
||||
uint32_t handleId = 0;
|
||||
ASSERT_EQ(allocation->peekInternalHandle(this->memoryManager, handleId), static_cast<uint64_t>(1337));
|
||||
int ret = allocation->peekInternalHandle(this->memoryManager, handleId, handle);
|
||||
ASSERT_EQ(ret, 0);
|
||||
ASSERT_EQ(handle, static_cast<uint64_t>(1337));
|
||||
|
||||
memoryManager->freeGraphicsMemory(allocation);
|
||||
}
|
||||
@@ -510,11 +538,17 @@ TEST_F(DrmMemoryManagerTest, whenCallingPeekInternalHandleWithIdSeveralTimesThen
|
||||
|
||||
EXPECT_EQ(mock->outputFd, static_cast<int32_t>(expectedFd));
|
||||
uint32_t handleId = 0;
|
||||
uint64_t handle0 = allocation->peekInternalHandle(this->memoryManager, handleId);
|
||||
uint64_t handle0 = 0;
|
||||
int ret = allocation->peekInternalHandle(this->memoryManager, handleId, handle0);
|
||||
ASSERT_EQ(ret, 0);
|
||||
EXPECT_NE(mock->outputFd, static_cast<int32_t>(expectedFd));
|
||||
|
||||
uint64_t handle1 = allocation->peekInternalHandle(this->memoryManager, handleId);
|
||||
uint64_t handle2 = allocation->peekInternalHandle(this->memoryManager, handleId);
|
||||
uint64_t handle1 = 0;
|
||||
uint64_t handle2 = 0;
|
||||
ret = allocation->peekInternalHandle(this->memoryManager, handleId, handle1);
|
||||
ASSERT_EQ(ret, 0);
|
||||
ret = allocation->peekInternalHandle(this->memoryManager, handleId, handle2);
|
||||
ASSERT_EQ(ret, 0);
|
||||
|
||||
ASSERT_EQ(handle0, expectedFd);
|
||||
ASSERT_EQ(handle1, expectedFd);
|
||||
@@ -3163,6 +3197,29 @@ TEST(DrmMemoryManagerWithExplicitExpectationsTest2, whenObtainFdFromHandleIsCall
|
||||
}
|
||||
}
|
||||
|
||||
TEST(DrmMemoryManagerWithExplicitExpectationsTest2, whenFailingToObtainFdFromHandleThenErrorIsReturned) {
|
||||
auto executionEnvironment = std::make_unique<MockExecutionEnvironment>();
|
||||
executionEnvironment->prepareRootDeviceEnvironments(4u);
|
||||
for (auto i = 0u; i < 4u; i++) {
|
||||
executionEnvironment->rootDeviceEnvironments[i]->setHwInfo(defaultHwInfo.get());
|
||||
auto mock = new DrmMockCustom(*executionEnvironment->rootDeviceEnvironments[0]);
|
||||
executionEnvironment->rootDeviceEnvironments[i]->osInterface = std::make_unique<OSInterface>();
|
||||
executionEnvironment->rootDeviceEnvironments[i]->osInterface->setDriverModel(std::unique_ptr<DriverModel>(mock));
|
||||
executionEnvironment->rootDeviceEnvironments[i]->initGmm();
|
||||
}
|
||||
auto memoryManager = std::make_unique<TestedDrmMemoryManager>(false, false, false, *executionEnvironment);
|
||||
for (auto i = 0u; i < 4u; i++) {
|
||||
auto mock = executionEnvironment->rootDeviceEnvironments[i]->osInterface->getDriverModel()->as<DrmMockCustom>();
|
||||
|
||||
int boHandle = 3;
|
||||
mock->outputFd = -1;
|
||||
mock->ioctl_res = -1;
|
||||
mock->ioctl_expected.handleToPrimeFd = 1;
|
||||
auto fdHandle = memoryManager->obtainFdFromHandle(boHandle, i);
|
||||
EXPECT_EQ(-1, fdHandle);
|
||||
}
|
||||
}
|
||||
|
||||
TEST_F(DrmMemoryManagerTest, givenSvmCpuAllocationWhenSizeAndAlignmentProvidedThenAllocateMemoryAndReserveGpuVa) {
|
||||
mock->ioctl_expected.gemUserptr = 1;
|
||||
mock->ioctl_expected.gemWait = 1;
|
||||
|
||||
Reference in New Issue
Block a user