在 64 位視窗中為 AMD 系統實現 OpenCL 1.2 平臺的數量

OpenCL 是低階 API,因此必須首先在“C 空間”中實現。為此,需要從 Khronos 的網站下載標頭檔案。我的硬體是 AMD,能夠支援 1.2 版,下載

opencl.h 
cl_platform.h 
cl.h 
cl_ext.h 
cl_egl.h 
cl_dx9_media_sharing.h 
cl_d3d10.h 
cl_d3d11.h 
cl_gl.h 
cl_gl_ext.h 
cl.hpp

這個頁面

應該足夠 C++繫結所以在將這些檔案新增到專案並設定適當的二進位制(和庫)檔案位置後(

用於 64 位 amd 庫的$(AMDAPPSDKROOT)\ lib \ x86_64(首選 amd app sdk 的庫)

用於 64 位 opencl.dll 的 C:\ Windows \ SysWOW64(如果 ICD 是 Linux 系統,則為 .so 檔案)

例如,但對於 Intel-Nvidia 不同,你可以在安裝適當的驅動程式(例如 amd 的 crimson)後開始查詢平臺列表(amd, intel, xilinx, nvidia)。驅動程式用於執行 opencl 應用程式(使用 ICD),庫和標頭檔案用於簡化開發。

要查詢平臺:

#define __CL_ENABLE_EXCEPTIONS
#include "stdafx.h"
#include <vector>
#include <CL/cl.hpp>

extern "C"
    {
       // when this class is created, it contains a list of platforms in "platforms" field.
       class OpenClPlatformList
       {
           public:
               std::vector<cl::Platform> platforms;
               int platformNum;
               OpenClPlatformList()
               {
                   platforms= std::vector< cl::Platform>();
                   cl::Platform::get(&platforms);
                   platformNum= platforms.size();
               }
        };

        // this is seen from C# when imported. Creates an object in memory.
        __declspec(dllexport)
            OpenClPlatformList * createPlatformList()
        {
            return new OpenClPlatformList();
        }

        __declspec(dllexport)
            int platformNumber(OpenClPlatformList * hList)
        {
            return hList->platformNum;
        }

        __declspec(dllexport)
            void deletePlatformList(OpenClPlatformList * p)
        {
            if (p != NULL)
                delete p;
            p = NULL;
        }

    }

可以內建到一個 DLL(如 OCLImplementation.dll)

並從 C#側使用它,

using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;

namespace WrapperCSharp
{
    public class WrapperCSharp
    {
        [DllImport("OCLImplementation", CallingConvention = CallingConvention.Cdecl)]
        private static extern IntPtr createPlatformList();

        [DllImport("OCLImplementation", CallingConvention = CallingConvention.Cdecl)]
        private static extern int platformNumber(IntPtr hList);

        [DllImport("OCLImplementation", CallingConvention = CallingConvention.Cdecl)]
        private static extern void deletePlatformList(IntPtr hList);
    }
}

當然,必須通過 C#專案看到 dll,只需將它放在專案的可執行檔案附近即可。

現在,如果示例計算機至少有一個支援 opencl 的平臺,

IntPtr platformList = createPlatformList(); // just an address in C-space
int totalPlatforms = platformNumber(platformList); // AMD+NVIDIA systems should have "2"
deletePlatformList(platformList); //

totalPlatforms 變數必須至少具有 1 值。然後,你可以使用 C 空間中的平臺變數,使用其他函式迭代所有平臺,以查詢所有裝置,如 CPU,GPU 和特殊用途加速器,如 phi 或某些 fpga。

人們不會簡單地將所有這些 C++寫入 C#包裝器以用於時間關鍵型專案。有許多為 C#,Java 和其他語言編寫的包裝器。對於 java,有一個 Aparapi 是“java 位元組碼到 opencl-c”轉換器 api,它將你在 java 中純粹編寫的內容轉換為動態的 gpu-parallel 版本,因此它具有一定的可移植性。