xref: /aosp_15_r20/external/angle/src/libANGLE/CLMemory.cpp (revision 8975f5c5ed3d1c378011245431ada316dfb6f244)
1*8975f5c5SAndroid Build Coastguard Worker //
2*8975f5c5SAndroid Build Coastguard Worker // Copyright 2021 The ANGLE Project Authors. All rights reserved.
3*8975f5c5SAndroid Build Coastguard Worker // Use of this source code is governed by a BSD-style license that can be
4*8975f5c5SAndroid Build Coastguard Worker // found in the LICENSE file.
5*8975f5c5SAndroid Build Coastguard Worker //
6*8975f5c5SAndroid Build Coastguard Worker // CLMemory.cpp: Implements the cl::Memory class.
7*8975f5c5SAndroid Build Coastguard Worker 
8*8975f5c5SAndroid Build Coastguard Worker #include "libANGLE/CLMemory.h"
9*8975f5c5SAndroid Build Coastguard Worker 
10*8975f5c5SAndroid Build Coastguard Worker #include "libANGLE/CLBuffer.h"
11*8975f5c5SAndroid Build Coastguard Worker #include "libANGLE/CLContext.h"
12*8975f5c5SAndroid Build Coastguard Worker #include "libANGLE/CLImage.h"
13*8975f5c5SAndroid Build Coastguard Worker #include "libANGLE/cl_utils.h"
14*8975f5c5SAndroid Build Coastguard Worker 
15*8975f5c5SAndroid Build Coastguard Worker #include <cstring>
16*8975f5c5SAndroid Build Coastguard Worker 
17*8975f5c5SAndroid Build Coastguard Worker namespace cl
18*8975f5c5SAndroid Build Coastguard Worker {
19*8975f5c5SAndroid Build Coastguard Worker 
20*8975f5c5SAndroid Build Coastguard Worker namespace
21*8975f5c5SAndroid Build Coastguard Worker {
22*8975f5c5SAndroid Build Coastguard Worker 
InheritMemFlags(MemFlags flags,Memory * parent)23*8975f5c5SAndroid Build Coastguard Worker MemFlags InheritMemFlags(MemFlags flags, Memory *parent)
24*8975f5c5SAndroid Build Coastguard Worker {
25*8975f5c5SAndroid Build Coastguard Worker     if (parent != nullptr)
26*8975f5c5SAndroid Build Coastguard Worker     {
27*8975f5c5SAndroid Build Coastguard Worker         const MemFlags parentFlags = parent->getFlags();
28*8975f5c5SAndroid Build Coastguard Worker         const MemFlags access(CL_MEM_READ_WRITE | CL_MEM_READ_ONLY | CL_MEM_WRITE_ONLY);
29*8975f5c5SAndroid Build Coastguard Worker         const MemFlags hostAccess(CL_MEM_HOST_WRITE_ONLY | CL_MEM_HOST_READ_ONLY |
30*8975f5c5SAndroid Build Coastguard Worker                                   CL_MEM_HOST_NO_ACCESS);
31*8975f5c5SAndroid Build Coastguard Worker         const MemFlags hostPtrFlags(CL_MEM_USE_HOST_PTR | CL_MEM_ALLOC_HOST_PTR |
32*8975f5c5SAndroid Build Coastguard Worker                                     CL_MEM_COPY_HOST_PTR);
33*8975f5c5SAndroid Build Coastguard Worker         if (flags.excludes(access))
34*8975f5c5SAndroid Build Coastguard Worker         {
35*8975f5c5SAndroid Build Coastguard Worker             flags.set(parentFlags.mask(access));
36*8975f5c5SAndroid Build Coastguard Worker         }
37*8975f5c5SAndroid Build Coastguard Worker         if (flags.excludes(hostAccess))
38*8975f5c5SAndroid Build Coastguard Worker         {
39*8975f5c5SAndroid Build Coastguard Worker             flags.set(parentFlags.mask(hostAccess));
40*8975f5c5SAndroid Build Coastguard Worker         }
41*8975f5c5SAndroid Build Coastguard Worker         flags.set(parentFlags.mask(hostPtrFlags));
42*8975f5c5SAndroid Build Coastguard Worker     }
43*8975f5c5SAndroid Build Coastguard Worker     return flags;
44*8975f5c5SAndroid Build Coastguard Worker }
45*8975f5c5SAndroid Build Coastguard Worker 
46*8975f5c5SAndroid Build Coastguard Worker }  // namespace
47*8975f5c5SAndroid Build Coastguard Worker 
setDestructorCallback(MemoryCB pfnNotify,void * userData)48*8975f5c5SAndroid Build Coastguard Worker angle::Result Memory::setDestructorCallback(MemoryCB pfnNotify, void *userData)
49*8975f5c5SAndroid Build Coastguard Worker {
50*8975f5c5SAndroid Build Coastguard Worker     mDestructorCallbacks->emplace(pfnNotify, userData);
51*8975f5c5SAndroid Build Coastguard Worker     return angle::Result::Continue;
52*8975f5c5SAndroid Build Coastguard Worker }
53*8975f5c5SAndroid Build Coastguard Worker 
getInfo(MemInfo name,size_t valueSize,void * value,size_t * valueSizeRet) const54*8975f5c5SAndroid Build Coastguard Worker angle::Result Memory::getInfo(MemInfo name,
55*8975f5c5SAndroid Build Coastguard Worker                               size_t valueSize,
56*8975f5c5SAndroid Build Coastguard Worker                               void *value,
57*8975f5c5SAndroid Build Coastguard Worker                               size_t *valueSizeRet) const
58*8975f5c5SAndroid Build Coastguard Worker {
59*8975f5c5SAndroid Build Coastguard Worker     static_assert(
60*8975f5c5SAndroid Build Coastguard Worker         std::is_same<cl_uint, cl_bool>::value && std::is_same<cl_uint, cl_mem_object_type>::value,
61*8975f5c5SAndroid Build Coastguard Worker         "OpenCL type mismatch");
62*8975f5c5SAndroid Build Coastguard Worker 
63*8975f5c5SAndroid Build Coastguard Worker     cl_uint valUInt       = 0u;
64*8975f5c5SAndroid Build Coastguard Worker     void *valPointer      = nullptr;
65*8975f5c5SAndroid Build Coastguard Worker     const void *copyValue = nullptr;
66*8975f5c5SAndroid Build Coastguard Worker     size_t copySize       = 0u;
67*8975f5c5SAndroid Build Coastguard Worker 
68*8975f5c5SAndroid Build Coastguard Worker     switch (name)
69*8975f5c5SAndroid Build Coastguard Worker     {
70*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::Type:
71*8975f5c5SAndroid Build Coastguard Worker             valUInt   = ToCLenum(getType());
72*8975f5c5SAndroid Build Coastguard Worker             copyValue = &valUInt;
73*8975f5c5SAndroid Build Coastguard Worker             copySize  = sizeof(valUInt);
74*8975f5c5SAndroid Build Coastguard Worker             break;
75*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::Flags:
76*8975f5c5SAndroid Build Coastguard Worker             copyValue = &mFlags;
77*8975f5c5SAndroid Build Coastguard Worker             copySize  = sizeof(mFlags);
78*8975f5c5SAndroid Build Coastguard Worker             break;
79*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::Size:
80*8975f5c5SAndroid Build Coastguard Worker             copyValue = &mSize;
81*8975f5c5SAndroid Build Coastguard Worker             copySize  = sizeof(mSize);
82*8975f5c5SAndroid Build Coastguard Worker             break;
83*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::HostPtr:
84*8975f5c5SAndroid Build Coastguard Worker             copyValue = &mHostPtr;
85*8975f5c5SAndroid Build Coastguard Worker             copySize  = sizeof(mHostPtr);
86*8975f5c5SAndroid Build Coastguard Worker             break;
87*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::MapCount:
88*8975f5c5SAndroid Build Coastguard Worker             valUInt   = mMapCount;
89*8975f5c5SAndroid Build Coastguard Worker             copyValue = &valUInt;
90*8975f5c5SAndroid Build Coastguard Worker             copySize  = sizeof(valUInt);
91*8975f5c5SAndroid Build Coastguard Worker             break;
92*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::ReferenceCount:
93*8975f5c5SAndroid Build Coastguard Worker             valUInt   = getRefCount();
94*8975f5c5SAndroid Build Coastguard Worker             copyValue = &valUInt;
95*8975f5c5SAndroid Build Coastguard Worker             copySize  = sizeof(valUInt);
96*8975f5c5SAndroid Build Coastguard Worker             break;
97*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::Context:
98*8975f5c5SAndroid Build Coastguard Worker             valPointer = mContext->getNative();
99*8975f5c5SAndroid Build Coastguard Worker             copyValue  = &valPointer;
100*8975f5c5SAndroid Build Coastguard Worker             copySize   = sizeof(valPointer);
101*8975f5c5SAndroid Build Coastguard Worker             break;
102*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::AssociatedMemObject:
103*8975f5c5SAndroid Build Coastguard Worker             valPointer = Memory::CastNative(mParent.get());
104*8975f5c5SAndroid Build Coastguard Worker             copyValue  = &valPointer;
105*8975f5c5SAndroid Build Coastguard Worker             copySize   = sizeof(valPointer);
106*8975f5c5SAndroid Build Coastguard Worker             break;
107*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::Offset:
108*8975f5c5SAndroid Build Coastguard Worker             copyValue = &mOffset;
109*8975f5c5SAndroid Build Coastguard Worker             copySize  = sizeof(mOffset);
110*8975f5c5SAndroid Build Coastguard Worker             break;
111*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::UsesSVM_Pointer:
112*8975f5c5SAndroid Build Coastguard Worker             valUInt   = CL_FALSE;  // TODO(jplate) Check for SVM pointer anglebug.com/42264535
113*8975f5c5SAndroid Build Coastguard Worker             copyValue = &valUInt;
114*8975f5c5SAndroid Build Coastguard Worker             copySize  = sizeof(valUInt);
115*8975f5c5SAndroid Build Coastguard Worker             break;
116*8975f5c5SAndroid Build Coastguard Worker         case MemInfo::Properties:
117*8975f5c5SAndroid Build Coastguard Worker             copyValue = mProperties.data();
118*8975f5c5SAndroid Build Coastguard Worker             copySize  = mProperties.size() * sizeof(decltype(mProperties)::value_type);
119*8975f5c5SAndroid Build Coastguard Worker             break;
120*8975f5c5SAndroid Build Coastguard Worker         default:
121*8975f5c5SAndroid Build Coastguard Worker             ANGLE_CL_RETURN_ERROR(CL_INVALID_VALUE);
122*8975f5c5SAndroid Build Coastguard Worker     }
123*8975f5c5SAndroid Build Coastguard Worker 
124*8975f5c5SAndroid Build Coastguard Worker     if (value != nullptr)
125*8975f5c5SAndroid Build Coastguard Worker     {
126*8975f5c5SAndroid Build Coastguard Worker         // CL_INVALID_VALUE if size in bytes specified by param_value_size is < size of return type
127*8975f5c5SAndroid Build Coastguard Worker         // as described in the Memory Object Info table and param_value is not NULL.
128*8975f5c5SAndroid Build Coastguard Worker         if (valueSize < copySize)
129*8975f5c5SAndroid Build Coastguard Worker         {
130*8975f5c5SAndroid Build Coastguard Worker             ANGLE_CL_RETURN_ERROR(CL_INVALID_VALUE);
131*8975f5c5SAndroid Build Coastguard Worker         }
132*8975f5c5SAndroid Build Coastguard Worker         if (copyValue != nullptr)
133*8975f5c5SAndroid Build Coastguard Worker         {
134*8975f5c5SAndroid Build Coastguard Worker             std::memcpy(value, copyValue, copySize);
135*8975f5c5SAndroid Build Coastguard Worker         }
136*8975f5c5SAndroid Build Coastguard Worker     }
137*8975f5c5SAndroid Build Coastguard Worker     if (valueSizeRet != nullptr)
138*8975f5c5SAndroid Build Coastguard Worker     {
139*8975f5c5SAndroid Build Coastguard Worker         *valueSizeRet = copySize;
140*8975f5c5SAndroid Build Coastguard Worker     }
141*8975f5c5SAndroid Build Coastguard Worker     return angle::Result::Continue;
142*8975f5c5SAndroid Build Coastguard Worker }
143*8975f5c5SAndroid Build Coastguard Worker 
~Memory()144*8975f5c5SAndroid Build Coastguard Worker Memory::~Memory()
145*8975f5c5SAndroid Build Coastguard Worker {
146*8975f5c5SAndroid Build Coastguard Worker     std::stack<CallbackData> callbacks;
147*8975f5c5SAndroid Build Coastguard Worker     mDestructorCallbacks->swap(callbacks);
148*8975f5c5SAndroid Build Coastguard Worker     while (!callbacks.empty())
149*8975f5c5SAndroid Build Coastguard Worker     {
150*8975f5c5SAndroid Build Coastguard Worker         const MemoryCB callback = callbacks.top().first;
151*8975f5c5SAndroid Build Coastguard Worker         void *const userData    = callbacks.top().second;
152*8975f5c5SAndroid Build Coastguard Worker         callbacks.pop();
153*8975f5c5SAndroid Build Coastguard Worker         callback(this, userData);
154*8975f5c5SAndroid Build Coastguard Worker     }
155*8975f5c5SAndroid Build Coastguard Worker }
156*8975f5c5SAndroid Build Coastguard Worker 
Memory(const Buffer & buffer,Context & context,PropArray && properties,MemFlags flags,size_t size,void * hostPtr)157*8975f5c5SAndroid Build Coastguard Worker Memory::Memory(const Buffer &buffer,
158*8975f5c5SAndroid Build Coastguard Worker                Context &context,
159*8975f5c5SAndroid Build Coastguard Worker                PropArray &&properties,
160*8975f5c5SAndroid Build Coastguard Worker                MemFlags flags,
161*8975f5c5SAndroid Build Coastguard Worker                size_t size,
162*8975f5c5SAndroid Build Coastguard Worker                void *hostPtr)
163*8975f5c5SAndroid Build Coastguard Worker     : mContext(&context),
164*8975f5c5SAndroid Build Coastguard Worker       mProperties(std::move(properties)),
165*8975f5c5SAndroid Build Coastguard Worker       mFlags(flags.excludes(CL_MEM_READ_WRITE | CL_MEM_READ_ONLY | CL_MEM_WRITE_ONLY)
166*8975f5c5SAndroid Build Coastguard Worker                  ? cl::MemFlags{flags.get() | CL_MEM_READ_WRITE}
167*8975f5c5SAndroid Build Coastguard Worker                  : flags),
168*8975f5c5SAndroid Build Coastguard Worker       mHostPtr(flags.intersects(CL_MEM_USE_HOST_PTR) ? hostPtr : nullptr),
169*8975f5c5SAndroid Build Coastguard Worker       mImpl(nullptr),
170*8975f5c5SAndroid Build Coastguard Worker       mSize(size),
171*8975f5c5SAndroid Build Coastguard Worker       mMapCount(0u)
172*8975f5c5SAndroid Build Coastguard Worker {
173*8975f5c5SAndroid Build Coastguard Worker     ANGLE_CL_IMPL_TRY(context.getImpl().createBuffer(buffer, hostPtr, &mImpl));
174*8975f5c5SAndroid Build Coastguard Worker }
175*8975f5c5SAndroid Build Coastguard Worker 
Memory(const Buffer & buffer,Buffer & parent,MemFlags flags,size_t offset,size_t size)176*8975f5c5SAndroid Build Coastguard Worker Memory::Memory(const Buffer &buffer, Buffer &parent, MemFlags flags, size_t offset, size_t size)
177*8975f5c5SAndroid Build Coastguard Worker     : mContext(parent.mContext),
178*8975f5c5SAndroid Build Coastguard Worker       mFlags(InheritMemFlags(flags, &parent)),
179*8975f5c5SAndroid Build Coastguard Worker       mHostPtr(parent.mHostPtr != nullptr ? static_cast<char *>(parent.mHostPtr) + offset
180*8975f5c5SAndroid Build Coastguard Worker                                           : nullptr),
181*8975f5c5SAndroid Build Coastguard Worker       mParent(&parent),
182*8975f5c5SAndroid Build Coastguard Worker       mOffset(offset),
183*8975f5c5SAndroid Build Coastguard Worker       mImpl(nullptr),
184*8975f5c5SAndroid Build Coastguard Worker       mSize(size),
185*8975f5c5SAndroid Build Coastguard Worker       mMapCount(0u)
186*8975f5c5SAndroid Build Coastguard Worker {
187*8975f5c5SAndroid Build Coastguard Worker     ANGLE_CL_IMPL_TRY(parent.mImpl->createSubBuffer(buffer, flags, size, &mImpl));
188*8975f5c5SAndroid Build Coastguard Worker }
189*8975f5c5SAndroid Build Coastguard Worker 
Memory(Context & context,PropArray && properties,MemFlags flags,Memory * parent,void * hostPtr)190*8975f5c5SAndroid Build Coastguard Worker Memory::Memory(Context &context,
191*8975f5c5SAndroid Build Coastguard Worker                PropArray &&properties,
192*8975f5c5SAndroid Build Coastguard Worker                MemFlags flags,
193*8975f5c5SAndroid Build Coastguard Worker                Memory *parent,
194*8975f5c5SAndroid Build Coastguard Worker                void *hostPtr)
195*8975f5c5SAndroid Build Coastguard Worker     : mContext(&context),
196*8975f5c5SAndroid Build Coastguard Worker       mProperties(std::move(properties)),
197*8975f5c5SAndroid Build Coastguard Worker       mFlags(InheritMemFlags(flags, parent)),
198*8975f5c5SAndroid Build Coastguard Worker       mHostPtr(flags.intersects(CL_MEM_USE_HOST_PTR) ? hostPtr : nullptr),
199*8975f5c5SAndroid Build Coastguard Worker       mParent(parent),
200*8975f5c5SAndroid Build Coastguard Worker       mImpl(nullptr),
201*8975f5c5SAndroid Build Coastguard Worker       mSize(0u),
202*8975f5c5SAndroid Build Coastguard Worker       mMapCount(0u)
203*8975f5c5SAndroid Build Coastguard Worker {}
204*8975f5c5SAndroid Build Coastguard Worker 
205*8975f5c5SAndroid Build Coastguard Worker }  // namespace cl
206