// // Copyright 2017-2023 Valve Corporation. // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. // using System; using UnityEngine; namespace SteamAudio { public class OpenCLDevice { IntPtr mOpenCLDevice = IntPtr.Zero; public OpenCLDevice(Context context, OpenCLDeviceType deviceType, int numCUsToReserve, float fractionCUsForIRUpdate, bool requiresTAN) { var deviceSettings = new OpenCLDeviceSettings { }; deviceSettings.type = deviceType; deviceSettings.numCUsToReserve = numCUsToReserve; deviceSettings.fractionCUsForIRUpdate = fractionCUsForIRUpdate; deviceSettings.requiresTAN = requiresTAN ? Bool.True : Bool.False; var deviceList = IntPtr.Zero; var status = API.iplOpenCLDeviceListCreate(context.Get(), ref deviceSettings, out deviceList); if (status != Error.Success) throw new Exception(string.Format("Unable to enumerate OpenCL devices. [{0}]", status)); var numDevices = API.iplOpenCLDeviceListGetNumDevices(deviceList); if (numDevices <= 0) { API.iplOpenCLDeviceListRelease(ref deviceList); // If we explicitly requested a device that supports TAN, or if we didn't ask for CU // reservation, but still didn't find any devices, stop. if (requiresTAN || numCUsToReserve == 0) throw new Exception(string.Format("No OpenCL devices found.")); Debug.LogWarning("No OpenCL devices found that match the provided parameters, attempting to " + "initialize without CU reservation."); deviceSettings.numCUsToReserve = 0; deviceSettings.fractionCUsForIRUpdate = 0.0f; status = API.iplOpenCLDeviceListCreate(context.Get(), ref deviceSettings, out deviceList); if (status != Error.Success) throw new Exception(string.Format("Unable to enumerate OpenCL devices. [{0}]", status)); numDevices = API.iplOpenCLDeviceListGetNumDevices(deviceList); if (numDevices <= 0) throw new Exception(string.Format("No OpenCL devices found.")); } status = API.iplOpenCLDeviceCreate(context.Get(), deviceList, 0, out mOpenCLDevice); if (status != Error.Success) { API.iplOpenCLDeviceListRelease(ref deviceList); throw new Exception(string.Format("Unable to create OpenCL device. [{0}]", status)); } API.iplOpenCLDeviceListRelease(ref deviceList); } public OpenCLDevice(OpenCLDevice device) { mOpenCLDevice = API.iplOpenCLDeviceRetain(device.mOpenCLDevice); } ~OpenCLDevice() { Release(); } public void Release() { API.iplOpenCLDeviceRelease(ref mOpenCLDevice); } public IntPtr Get() { return mOpenCLDevice; } } }