mtl_gpu/argument/
argument.rs1use std::ffi::c_void;
4use std::ptr::NonNull;
5
6use mtl_foundation::{Referencing, UInteger};
7use mtl_sys::{msg_send_0, sel};
8
9use crate::enums::{ArgumentType, BindingAccess, DataType, TextureType};
10
11use super::{PointerType, StructType};
12
13#[repr(transparent)]
17pub struct Argument(pub(crate) NonNull<c_void>);
18
19impl Argument {
20 #[inline]
26 pub unsafe fn from_raw(ptr: *mut c_void) -> Option<Self> {
27 NonNull::new(ptr).map(Self)
28 }
29
30 #[inline]
32 pub fn as_raw(&self) -> *mut c_void {
33 self.0.as_ptr()
34 }
35
36 #[inline]
40 pub fn access(&self) -> BindingAccess {
41 unsafe { msg_send_0(self.as_ptr(), sel!(access)) }
42 }
43
44 #[inline]
48 pub fn array_length(&self) -> UInteger {
49 unsafe { msg_send_0(self.as_ptr(), sel!(arrayLength)) }
50 }
51
52 #[inline]
56 pub fn buffer_alignment(&self) -> UInteger {
57 unsafe { msg_send_0(self.as_ptr(), sel!(bufferAlignment)) }
58 }
59
60 #[inline]
64 pub fn buffer_data_size(&self) -> UInteger {
65 unsafe { msg_send_0(self.as_ptr(), sel!(bufferDataSize)) }
66 }
67
68 #[inline]
72 pub fn buffer_data_type(&self) -> DataType {
73 unsafe { msg_send_0(self.as_ptr(), sel!(bufferDataType)) }
74 }
75
76 pub fn buffer_pointer_type(&self) -> Option<PointerType> {
80 unsafe {
81 let ptr: *mut c_void = msg_send_0(self.as_ptr(), sel!(bufferPointerType));
82 PointerType::from_raw(ptr)
83 }
84 }
85
86 pub fn buffer_struct_type(&self) -> Option<StructType> {
90 unsafe {
91 let ptr: *mut c_void = msg_send_0(self.as_ptr(), sel!(bufferStructType));
92 StructType::from_raw(ptr)
93 }
94 }
95
96 #[inline]
100 pub fn index(&self) -> UInteger {
101 unsafe { msg_send_0(self.as_ptr(), sel!(index)) }
102 }
103
104 #[inline]
108 pub fn is_active(&self) -> bool {
109 unsafe { msg_send_0(self.as_ptr(), sel!(isActive)) }
110 }
111
112 #[inline]
116 pub fn is_depth_texture(&self) -> bool {
117 unsafe { msg_send_0(self.as_ptr(), sel!(isDepthTexture)) }
118 }
119
120 pub fn name(&self) -> Option<String> {
124 unsafe {
125 let ptr: *mut c_void = msg_send_0(self.as_ptr(), sel!(name));
126 if ptr.is_null() {
127 return None;
128 }
129 let utf8_ptr: *const std::ffi::c_char =
130 mtl_sys::msg_send_0(ptr as *const c_void, sel!(UTF8String));
131 if utf8_ptr.is_null() {
132 return None;
133 }
134 let c_str = std::ffi::CStr::from_ptr(utf8_ptr);
135 Some(c_str.to_string_lossy().into_owned())
136 }
137 }
138
139 #[inline]
143 pub fn texture_data_type(&self) -> DataType {
144 unsafe { msg_send_0(self.as_ptr(), sel!(textureDataType)) }
145 }
146
147 #[inline]
151 pub fn texture_type(&self) -> TextureType {
152 unsafe { msg_send_0(self.as_ptr(), sel!(textureType)) }
153 }
154
155 #[inline]
159 pub fn threadgroup_memory_alignment(&self) -> UInteger {
160 unsafe { msg_send_0(self.as_ptr(), sel!(threadgroupMemoryAlignment)) }
161 }
162
163 #[inline]
167 pub fn threadgroup_memory_data_size(&self) -> UInteger {
168 unsafe { msg_send_0(self.as_ptr(), sel!(threadgroupMemoryDataSize)) }
169 }
170
171 #[inline]
175 pub fn argument_type(&self) -> ArgumentType {
176 unsafe { msg_send_0(self.as_ptr(), sel!(type)) }
177 }
178
179 #[deprecated(note = "Use is_active instead")]
183 #[inline]
184 pub fn active(&self) -> bool {
185 unsafe { msg_send_0(self.as_ptr(), sel!(active)) }
186 }
187}
188
189impl Clone for Argument {
190 fn clone(&self) -> Self {
191 unsafe {
192 msg_send_0::<*mut c_void>(self.as_ptr(), sel!(retain));
193 }
194 Self(self.0)
195 }
196}
197
198impl Drop for Argument {
199 fn drop(&mut self) {
200 unsafe {
201 msg_send_0::<()>(self.as_ptr(), sel!(release));
202 }
203 }
204}
205
206impl Referencing for Argument {
207 #[inline]
208 fn as_ptr(&self) -> *const c_void {
209 self.0.as_ptr()
210 }
211}
212
213unsafe impl Send for Argument {}
214unsafe impl Sync for Argument {}