Edit

kc3-lang/angle/src/libANGLE/CLKernel.cpp

Branch :

  • Show log

    Commit

  • Author : John Plate
    Date : 2021-06-11 19:12:11
    Hash : 69562546
    Message : CL: Refactor info structs and fix conformance bug - Remove variable name prefix from Info structs to be more consistent with other ANGLE structs. - Fix CL object validation check with magics, since the Mesa solution doesn't work without RTTI. - Add support for some extensions required by OpenCL 1.1 and for some optional extensions. - Fix more conformance bugs. Bug: angleproject:6015 Change-Id: I41b1c45d95059a9994f5dc78bf9b74476cc6f2d4 Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/2956349 Commit-Queue: John Plate <jplate@google.com> Reviewed-by: Cody Northrop <cnorthrop@google.com> Reviewed-by: Jamie Madill <jmadill@chromium.org>

  • src/libANGLE/CLKernel.cpp
  • //
    // Copyright 2021 The ANGLE Project Authors. All rights reserved.
    // Use of this source code is governed by a BSD-style license that can be
    // found in the LICENSE file.
    //
    // CLKernel.cpp: Implements the cl::Kernel class.
    
    #include "libANGLE/CLKernel.h"
    
    #include "libANGLE/CLContext.h"
    #include "libANGLE/CLProgram.h"
    
    #include <cstring>
    
    namespace cl
    {
    
    cl_int Kernel::setArg(cl_uint argIndex, size_t argSize, const void *argValue)
    {
        return mImpl->setArg(argIndex, argSize, argValue);
    }
    
    cl_int Kernel::getInfo(KernelInfo name, size_t valueSize, void *value, size_t *valueSizeRet) const
    {
        cl_uint valUInt       = 0u;
        void *valPointer      = nullptr;
        const void *copyValue = nullptr;
        size_t copySize       = 0u;
    
        switch (name)
        {
            case KernelInfo::FunctionName:
                copyValue = mInfo.functionName.c_str();
                copySize  = mInfo.functionName.length() + 1u;
                break;
            case KernelInfo::NumArgs:
                copyValue = &mInfo.numArgs;
                copySize  = sizeof(mInfo.numArgs);
                break;
            case KernelInfo::ReferenceCount:
                valUInt   = getRefCount();
                copyValue = &valUInt;
                copySize  = sizeof(valUInt);
                break;
            case KernelInfo::Context:
                valPointer = mProgram->getContext().getNative();
                copyValue  = &valPointer;
                copySize   = sizeof(valPointer);
                break;
            case KernelInfo::Program:
                valPointer = mProgram->getNative();
                copyValue  = &valPointer;
                copySize   = sizeof(valPointer);
                break;
            case KernelInfo::Attributes:
                copyValue = mInfo.attributes.c_str();
                copySize  = mInfo.attributes.length() + 1u;
                break;
            default:
                return CL_INVALID_VALUE;
        }
    
        if (value != nullptr)
        {
            // CL_INVALID_VALUE if size in bytes specified by param_value_size is < size of return type
            // as described in the Kernel Object Queries table and param_value is not NULL.
            if (valueSize < copySize)
            {
                return CL_INVALID_VALUE;
            }
            if (copyValue != nullptr)
            {
                std::memcpy(value, copyValue, copySize);
            }
        }
        if (valueSizeRet != nullptr)
        {
            *valueSizeRet = copySize;
        }
        return CL_SUCCESS;
    }
    
    cl_int Kernel::getWorkGroupInfo(cl_device_id device,
                                    KernelWorkGroupInfo name,
                                    size_t valueSize,
                                    void *value,
                                    size_t *valueSizeRet) const
    {
        size_t index = 0u;
        if (device != nullptr)
        {
            const DevicePtrs &devices = mProgram->getContext().getDevices();
            while (index < devices.size() && devices[index] != device)
            {
                ++index;
            }
            if (index == devices.size())
            {
                return CL_INVALID_DEVICE;
            }
        }
        const rx::CLKernelImpl::WorkGroupInfo &info = mInfo.workGroups[index];
    
        const void *copyValue = nullptr;
        size_t copySize       = 0u;
    
        switch (name)
        {
            case KernelWorkGroupInfo::GlobalWorkSize:
                copyValue = &info.globalWorkSize;
                copySize  = sizeof(info.globalWorkSize);
                break;
            case KernelWorkGroupInfo::WorkGroupSize:
                copyValue = &info.workGroupSize;
                copySize  = sizeof(info.workGroupSize);
                break;
            case KernelWorkGroupInfo::CompileWorkGroupSize:
                copyValue = &info.compileWorkGroupSize;
                copySize  = sizeof(info.compileWorkGroupSize);
                break;
            case KernelWorkGroupInfo::LocalMemSize:
                copyValue = &info.localMemSize;
                copySize  = sizeof(info.localMemSize);
                break;
            case KernelWorkGroupInfo::PreferredWorkGroupSizeMultiple:
                copyValue = &info.prefWorkGroupSizeMultiple;
                copySize  = sizeof(info.prefWorkGroupSizeMultiple);
                break;
            case KernelWorkGroupInfo::PrivateMemSize:
                copyValue = &info.privateMemSize;
                copySize  = sizeof(info.privateMemSize);
                break;
            default:
                return CL_INVALID_VALUE;
        }
    
        if (value != nullptr)
        {
            // CL_INVALID_VALUE if size in bytes specified by param_value_size is < size of return type
            // as described in the Kernel Object Device Queries table and param_value is not NULL.
            if (valueSize < copySize)
            {
                return CL_INVALID_VALUE;
            }
            if (copyValue != nullptr)
            {
                std::memcpy(value, copyValue, copySize);
            }
        }
        if (valueSizeRet != nullptr)
        {
            *valueSizeRet = copySize;
        }
        return CL_SUCCESS;
    }
    
    cl_int Kernel::getArgInfo(cl_uint argIndex,
                              KernelArgInfo name,
                              size_t valueSize,
                              void *value,
                              size_t *valueSizeRet) const
    {
        const rx::CLKernelImpl::ArgInfo &info = mInfo.args[argIndex];
        const void *copyValue                 = nullptr;
        size_t copySize                       = 0u;
    
        switch (name)
        {
            case KernelArgInfo::AddressQualifier:
                copyValue = &info.addressQualifier;
                copySize  = sizeof(info.addressQualifier);
                break;
            case KernelArgInfo::AccessQualifier:
                copyValue = &info.accessQualifier;
                copySize  = sizeof(info.accessQualifier);
                break;
            case KernelArgInfo::TypeName:
                copyValue = info.typeName.c_str();
                copySize  = info.typeName.length() + 1u;
                break;
            case KernelArgInfo::TypeQualifier:
                copyValue = &info.typeQualifier;
                copySize  = sizeof(info.typeQualifier);
                break;
            case KernelArgInfo::Name:
                copyValue = info.name.c_str();
                copySize  = info.name.length() + 1u;
                break;
            default:
                return CL_INVALID_VALUE;
        }
    
        if (value != nullptr)
        {
            // CL_INVALID_VALUE if size in bytes specified by param_value size is < size of return type
            // as described in the Kernel Argument Queries table and param_value is not NULL.
            if (valueSize < copySize)
            {
                return CL_INVALID_VALUE;
            }
            if (copyValue != nullptr)
            {
                std::memcpy(value, copyValue, copySize);
            }
        }
        if (valueSizeRet != nullptr)
        {
            *valueSizeRet = copySize;
        }
        return CL_SUCCESS;
    }
    
    Kernel::~Kernel()
    {
        --mProgram->mNumAttachedKernels;
    }
    
    Kernel::Kernel(Program &program, const char *name, cl_int &errorCode)
        : mProgram(&program),
          mImpl(program.getImpl().createKernel(*this, name, errorCode)),
          mInfo(mImpl ? mImpl->createInfo(errorCode) : rx::CLKernelImpl::Info{})
    {
        ++mProgram->mNumAttachedKernels;
    }
    
    Kernel::Kernel(Program &program, const rx::CLKernelImpl::CreateFunc &createFunc, cl_int &errorCode)
        : mProgram(&program), mImpl(createFunc(*this)), mInfo(mImpl->createInfo(errorCode))
    {
        ++mProgram->mNumAttachedKernels;
    }
    
    }  // namespace cl