1 /*
2 * Copyright (C) 2021 Intel Corporation
3 *
4 * SPDX-License-Identifier: MIT
5 *
6 */
7
8 #include "opencl/source/memory_manager/migration_controller.h"
9
10 #include "shared/source/command_stream/command_stream_receiver.h"
11 #include "shared/source/memory_manager/memory_manager.h"
12 #include "shared/source/memory_manager/migration_sync_data.h"
13
14 #include "opencl/source/command_queue/command_queue.h"
15 #include "opencl/source/context/context.h"
16 #include "opencl/source/mem_obj/image.h"
17 #include "opencl/source/mem_obj/mem_obj.h"
18
19 namespace NEO {
handleMigration(Context & context,CommandStreamReceiver & targetCsr,MemObj * memObj)20 void MigrationController::handleMigration(Context &context, CommandStreamReceiver &targetCsr, MemObj *memObj) {
21 auto memoryManager = targetCsr.getMemoryManager();
22 auto targetRootDeviceIndex = targetCsr.getRootDeviceIndex();
23 auto migrationSyncData = memObj->getMultiGraphicsAllocation().getMigrationSyncData();
24 if (!migrationSyncData->isUsedByTheSameContext(targetCsr.getTagAddress())) {
25 migrationSyncData->waitOnCpu();
26 }
27 if (migrationSyncData->getCurrentLocation() != targetRootDeviceIndex) {
28 migrateMemory(context, *memoryManager, memObj, targetRootDeviceIndex);
29 }
30 migrationSyncData->signalUsage(targetCsr.getTagAddress(), targetCsr.peekTaskCount() + 1);
31 }
32
migrateMemory(Context & context,MemoryManager & memoryManager,MemObj * memObj,uint32_t targetRootDeviceIndex)33 void MigrationController::migrateMemory(Context &context, MemoryManager &memoryManager, MemObj *memObj, uint32_t targetRootDeviceIndex) {
34 auto &multiGraphicsAllocation = memObj->getMultiGraphicsAllocation();
35 auto migrationSyncData = multiGraphicsAllocation.getMigrationSyncData();
36
37 auto sourceRootDeviceIndex = migrationSyncData->getCurrentLocation();
38 if (sourceRootDeviceIndex == std::numeric_limits<uint32_t>::max()) {
39 migrationSyncData->setCurrentLocation(targetRootDeviceIndex);
40 return;
41 }
42
43 migrationSyncData->startMigration();
44
45 auto srcMemory = multiGraphicsAllocation.getGraphicsAllocation(sourceRootDeviceIndex);
46 auto dstMemory = multiGraphicsAllocation.getGraphicsAllocation(targetRootDeviceIndex);
47
48 auto size = srcMemory->getUnderlyingBufferSize();
49 auto hostPtr = migrationSyncData->getHostPtr();
50
51 if (srcMemory->isAllocationLockable()) {
52 auto srcLockPtr = memoryManager.lockResource(srcMemory);
53 memcpy_s(hostPtr, size, srcLockPtr, size);
54 memoryManager.unlockResource(srcMemory);
55 } else {
56
57 auto srcCmdQ = context.getSpecialQueue(sourceRootDeviceIndex);
58 if (srcMemory->getAllocationType() == GraphicsAllocation::AllocationType::IMAGE) {
59 auto pImage = static_cast<Image *>(memObj);
60 size_t origin[3] = {};
61 size_t region[3] = {};
62 pImage->fillImageRegion(region);
63
64 srcCmdQ->enqueueReadImage(pImage, CL_TRUE, origin, region, pImage->getHostPtrRowPitch(), pImage->getHostPtrSlicePitch(), hostPtr, nullptr, 0, nullptr, nullptr);
65 } else {
66 auto pBuffer = static_cast<Buffer *>(memObj);
67 srcCmdQ->enqueueReadBuffer(pBuffer, CL_TRUE, 0u, pBuffer->getSize(), hostPtr, nullptr, 0, nullptr, nullptr);
68 }
69 srcCmdQ->finish();
70 }
71
72 if (dstMemory->isAllocationLockable()) {
73 auto dstLockPtr = memoryManager.lockResource(dstMemory);
74 memcpy_s(dstLockPtr, size, hostPtr, size);
75 memoryManager.unlockResource(dstMemory);
76 } else {
77
78 auto dstCmdQ = context.getSpecialQueue(targetRootDeviceIndex);
79 if (dstMemory->getAllocationType() == GraphicsAllocation::AllocationType::IMAGE) {
80 auto pImage = static_cast<Image *>(memObj);
81 size_t origin[3] = {};
82 size_t region[3] = {};
83 pImage->fillImageRegion(region);
84
85 dstCmdQ->enqueueWriteImage(pImage, CL_TRUE, origin, region, pImage->getHostPtrRowPitch(), pImage->getHostPtrSlicePitch(), hostPtr, nullptr, 0, nullptr, nullptr);
86 } else {
87 auto pBuffer = static_cast<Buffer *>(memObj);
88 dstCmdQ->enqueueWriteBuffer(pBuffer, CL_TRUE, 0u, pBuffer->getSize(), hostPtr, nullptr, 0, nullptr, nullptr);
89 }
90 dstCmdQ->finish();
91 }
92 migrationSyncData->setCurrentLocation(targetRootDeviceIndex);
93 }
94 } // namespace NEO