Skip to main content

oidn_wgpu/
sys.rs

1//! Raw FFI bindings to Intel Open Image Denoise (OIDN) C API.
2//! Targets OIDN 2.4.x. Full API coverage. See <https://www.openimagedenoise.org>.
3
4#![allow(non_camel_case_types, non_upper_case_globals, dead_code)]
5
6use std::os::raw::{c_char, c_int, c_void};
7
8// ---------------------------------------------------------------------------
9// Constants (from oidn.h)
10// ---------------------------------------------------------------------------
11
12pub const OIDN_UUID_SIZE: usize = 16;
13pub const OIDN_LUID_SIZE: usize = 8;
14
15// ---------------------------------------------------------------------------
16// Opaque handles
17// ---------------------------------------------------------------------------
18
19#[repr(C)]
20pub struct OIDNDeviceImpl {
21    _private: [u8; 0],
22}
23#[repr(C)]
24pub struct OIDNBufferImpl {
25    _private: [u8; 0],
26}
27#[repr(C)]
28pub struct OIDNFilterImpl {
29    _private: [u8; 0],
30}
31
32pub type OIDNDevice = *mut OIDNDeviceImpl;
33pub type OIDNBuffer = *mut OIDNBufferImpl;
34pub type OIDNFilter = *mut OIDNFilterImpl;
35
36// ---------------------------------------------------------------------------
37// Enums
38// ---------------------------------------------------------------------------
39
40#[repr(u32)]
41#[derive(Copy, Clone, Debug, PartialEq, Eq)]
42pub enum OIDNDeviceType {
43    Default = 0,
44    CPU = 1,
45    SYCL = 2,
46    CUDA = 3,
47    HIP = 4,
48    Metal = 5,
49}
50
51#[repr(u32)]
52#[derive(Copy, Clone, Debug, PartialEq, Eq)]
53pub enum OIDNError {
54    None = 0,
55    Unknown = 1,
56    InvalidArgument = 2,
57    InvalidOperation = 3,
58    OutOfMemory = 4,
59    UnsupportedHardware = 5,
60    Cancelled = 6,
61}
62
63#[repr(u32)]
64#[derive(Copy, Clone, Debug, PartialEq, Eq)]
65pub enum OIDNFormat {
66    Undefined = 0,
67    Float = 1,
68    Float2,
69    Float3,
70    Float4,
71    Half = 257,
72    Half2,
73    Half3,
74    Half4,
75}
76
77#[repr(u32)]
78#[derive(Copy, Clone, Debug, PartialEq, Eq)]
79pub enum OIDNStorage {
80    Undefined = 0,
81    Host = 1,
82    Device = 2,
83    Managed = 3,
84}
85
86#[repr(u32)]
87#[derive(Copy, Clone, Debug, PartialEq, Eq)]
88pub enum OIDNExternalMemoryTypeFlag {
89    None = 0,
90    OpaqueFD = 1 << 0,
91    DmaBuf = 1 << 1,
92    OpaqueWin32 = 1 << 2,
93    OpaqueWin32KMT = 1 << 3,
94    D3D11Texture = 1 << 4,
95    D3D11TextureKMT = 1 << 5,
96    D3D11Resource = 1 << 6,
97    D3D11ResourceKMT = 1 << 7,
98    D3D12Heap = 1 << 8,
99    D3D12Resource = 1 << 9,
100}
101
102#[repr(u32)]
103#[derive(Copy, Clone, Debug, PartialEq, Eq)]
104pub enum OIDNQuality {
105    Default = 0,
106    Fast = 4,
107    Balanced = 5,
108    High = 6,
109}
110
111// Callbacks
112pub type OIDNErrorFunction =
113    Option<unsafe extern "C" fn(user_ptr: *mut c_void, code: OIDNError, message: *const c_char)>;
114pub type OIDNProgressMonitorFunction = Option<unsafe extern "C" fn(user_ptr: *mut c_void, n: f64) -> bool>;
115
116// ---------------------------------------------------------------------------
117// Physical device
118// ---------------------------------------------------------------------------
119
120extern "C" {
121    pub fn oidnGetNumPhysicalDevices() -> c_int;
122    pub fn oidnGetPhysicalDeviceBool(physicalDeviceID: c_int, name: *const c_char) -> bool;
123    pub fn oidnGetPhysicalDeviceInt(physicalDeviceID: c_int, name: *const c_char) -> c_int;
124    pub fn oidnGetPhysicalDeviceString(physicalDeviceID: c_int, name: *const c_char) -> *const c_char;
125    pub fn oidnGetPhysicalDeviceData(
126        physicalDeviceID: c_int,
127        name: *const c_char,
128        byteSize: *mut usize,
129    ) -> *const c_void;
130}
131
132// ---------------------------------------------------------------------------
133// Device creation and support
134// ---------------------------------------------------------------------------
135
136extern "C" {
137    pub fn oidnIsCPUDeviceSupported() -> bool;
138    pub fn oidnIsCUDADeviceSupported(deviceID: c_int) -> bool;
139    pub fn oidnIsHIPDeviceSupported(deviceID: c_int) -> bool;
140    pub fn oidnIsMetalDeviceSupported(device: *mut c_void) -> bool;
141
142    pub fn oidnNewDevice(type_: OIDNDeviceType) -> OIDNDevice;
143    pub fn oidnNewDeviceByID(physicalDeviceID: c_int) -> OIDNDevice;
144    pub fn oidnNewDeviceByUUID(uuid: *const c_void) -> OIDNDevice;
145    pub fn oidnNewDeviceByLUID(luid: *const c_void) -> OIDNDevice;
146    pub fn oidnNewDeviceByPCIAddress(
147        pciDomain: c_int,
148        pciBus: c_int,
149        pciDevice: c_int,
150        pciFunction: c_int,
151    ) -> OIDNDevice;
152    /// deviceIDs and streams: arrays of length numPairs. stream null = default stream.
153    pub fn oidnNewCUDADevice(
154        deviceIDs: *const c_int,
155        streams: *const *mut c_void,
156        numPairs: c_int,
157    ) -> OIDNDevice;
158    pub fn oidnNewHIPDevice(
159        deviceIDs: *const c_int,
160        streams: *const *mut c_void,
161        numPairs: c_int,
162    ) -> OIDNDevice;
163    /// commandQueues: array of Metal MTLCommandQueue (void* when not ObjC).
164    pub fn oidnNewMetalDevice(commandQueues: *const *mut c_void, numQueues: c_int) -> OIDNDevice;
165
166    pub fn oidnRetainDevice(device: OIDNDevice);
167    pub fn oidnReleaseDevice(device: OIDNDevice);
168    pub fn oidnSetDeviceBool(device: OIDNDevice, name: *const c_char, value: bool);
169    pub fn oidnSetDeviceInt(device: OIDNDevice, name: *const c_char, value: c_int);
170    pub fn oidnGetDeviceBool(device: OIDNDevice, name: *const c_char) -> bool;
171    pub fn oidnGetDeviceInt(device: OIDNDevice, name: *const c_char) -> c_int;
172    pub fn oidnSetDeviceErrorFunction(
173        device: OIDNDevice,
174        func: OIDNErrorFunction,
175        user_ptr: *mut c_void,
176    );
177    pub fn oidnGetDeviceError(device: OIDNDevice, out_message: *mut *const c_char) -> OIDNError;
178    pub fn oidnCommitDevice(device: OIDNDevice);
179    pub fn oidnSyncDevice(device: OIDNDevice);
180}
181
182// SYCL device/queue APIs (oidnIsSYCLDeviceSupported, oidnNewSYCLDevice, oidnExecuteSYCLFilterAsync)
183// are C++-only in OIDN (sycl::device*, sycl::queue*, sycl::event*). Not exposed from Rust;
184// use the type-based oidnNewDevice(OIDN_DEVICE_TYPE_SYCL) instead, or a C++ shim for interop.
185
186// ---------------------------------------------------------------------------
187// Buffer
188// ---------------------------------------------------------------------------
189
190extern "C" {
191    pub fn oidnNewBuffer(device: OIDNDevice, byte_size: usize) -> OIDNBuffer;
192    pub fn oidnNewBufferWithStorage(
193        device: OIDNDevice,
194        byte_size: usize,
195        storage: OIDNStorage,
196    ) -> OIDNBuffer;
197    pub fn oidnNewSharedBuffer(device: OIDNDevice, dev_ptr: *mut c_void, byte_size: usize) -> OIDNBuffer;
198    pub fn oidnNewSharedBufferFromFD(
199        device: OIDNDevice,
200        fd_type: OIDNExternalMemoryTypeFlag,
201        fd: c_int,
202        byte_size: usize,
203    ) -> OIDNBuffer;
204    pub fn oidnNewSharedBufferFromWin32Handle(
205        device: OIDNDevice,
206        handle_type: OIDNExternalMemoryTypeFlag,
207        handle: *mut c_void,
208        name: *const c_void,
209        byte_size: usize,
210    ) -> OIDNBuffer;
211    pub fn oidnNewSharedBufferFromMetal(device: OIDNDevice, buffer: *mut c_void) -> OIDNBuffer;
212
213    pub fn oidnGetBufferSize(buffer: OIDNBuffer) -> usize;
214    pub fn oidnGetBufferStorage(buffer: OIDNBuffer) -> OIDNStorage;
215    pub fn oidnGetBufferData(buffer: OIDNBuffer) -> *mut c_void;
216    pub fn oidnReadBuffer(
217        buffer: OIDNBuffer,
218        byte_offset: usize,
219        byte_size: usize,
220        dst_host_ptr: *mut c_void,
221    );
222    pub fn oidnReadBufferAsync(
223        buffer: OIDNBuffer,
224        byte_offset: usize,
225        byte_size: usize,
226        dst_host_ptr: *mut c_void,
227    );
228    pub fn oidnWriteBuffer(
229        buffer: OIDNBuffer,
230        byte_offset: usize,
231        byte_size: usize,
232        src_host_ptr: *const c_void,
233    );
234    pub fn oidnWriteBufferAsync(
235        buffer: OIDNBuffer,
236        byte_offset: usize,
237        byte_size: usize,
238        src_host_ptr: *const c_void,
239    );
240    pub fn oidnRetainBuffer(buffer: OIDNBuffer);
241    pub fn oidnReleaseBuffer(buffer: OIDNBuffer);
242}
243
244// ---------------------------------------------------------------------------
245// Filter
246// ---------------------------------------------------------------------------
247
248extern "C" {
249    pub fn oidnNewFilter(device: OIDNDevice, type_name: *const c_char) -> OIDNFilter;
250    pub fn oidnRetainFilter(filter: OIDNFilter);
251    pub fn oidnReleaseFilter(filter: OIDNFilter);
252    pub fn oidnSetFilterImage(
253        filter: OIDNFilter,
254        name: *const c_char,
255        buffer: OIDNBuffer,
256        format: OIDNFormat,
257        width: usize,
258        height: usize,
259        byte_offset: usize,
260        pixel_byte_stride: usize,
261        row_byte_stride: usize,
262    );
263    pub fn oidnSetSharedFilterImage(
264        filter: OIDNFilter,
265        name: *const c_char,
266        dev_ptr: *mut c_void,
267        format: OIDNFormat,
268        width: usize,
269        height: usize,
270        byte_offset: usize,
271        pixel_byte_stride: usize,
272        row_byte_stride: usize,
273    );
274    pub fn oidnUnsetFilterImage(filter: OIDNFilter, name: *const c_char);
275    pub fn oidnSetSharedFilterData(
276        filter: OIDNFilter,
277        name: *const c_char,
278        host_ptr: *mut c_void,
279        byte_size: usize,
280    );
281    pub fn oidnUpdateFilterData(filter: OIDNFilter, name: *const c_char);
282    pub fn oidnUnsetFilterData(filter: OIDNFilter, name: *const c_char);
283    pub fn oidnSetFilterBool(filter: OIDNFilter, name: *const c_char, value: bool);
284    pub fn oidnGetFilterBool(filter: OIDNFilter, name: *const c_char) -> bool;
285    pub fn oidnSetFilterInt(filter: OIDNFilter, name: *const c_char, value: c_int);
286    pub fn oidnGetFilterInt(filter: OIDNFilter, name: *const c_char) -> c_int;
287    pub fn oidnSetFilterFloat(filter: OIDNFilter, name: *const c_char, value: f32);
288    pub fn oidnGetFilterFloat(filter: OIDNFilter, name: *const c_char) -> f32;
289    pub fn oidnSetFilterProgressMonitorFunction(
290        filter: OIDNFilter,
291        func: OIDNProgressMonitorFunction,
292        user_ptr: *mut c_void,
293    );
294    pub fn oidnCommitFilter(filter: OIDNFilter);
295    pub fn oidnExecuteFilter(filter: OIDNFilter);
296    pub fn oidnExecuteFilterAsync(filter: OIDNFilter);
297}