1// Take a look at the license at the top of the repository in the LICENSE file.
2
3// rustdoc-stripper-ignore-next
4//! `IMPL` Shared (reference counted) wrapper implementation.
5
6use std::{
7 cmp, fmt,
8 hash::{Hash, Hasher},
9 marker::PhantomData,
10 ptr,
11};
12
13use crate::translate::*;
14
15// rustdoc-stripper-ignore-next
16/// Wrapper implementations for shared types. See `wrapper!`.
17#[macro_export]
18macro_rules! glib_shared_wrapper {
19 ([$($attr:meta)*] $visibility:vis $name:ident $(<$($generic:ident $(: $bound:tt $(+ $bound2:tt)*)?),+>)?, $ffi_name:ty,
20 @ref $ref_arg:ident $ref_expr:expr, @unref $unref_arg:ident $unref_expr:expr
21 $(, @type_ $get_type_expr:expr)?) => {
22 $crate::glib_shared_wrapper!(
23 @generic_impl [$($attr)*] $visibility $name $(<$($generic $(: $bound $(+ $bound2)*)?),+>)?, $ffi_name,
24 @ref $ref_arg $ref_expr, @unref $unref_arg $unref_expr
25 );
26
27 $crate::glib_shared_wrapper!(@value_impl $name $(<$($generic $(: $bound $(+ $bound2)*)?),+>)?, $ffi_name $(, @type_ $get_type_expr)?);
28 };
29
30 (@generic_impl [$($attr:meta)*] $visibility:vis $name:ident $(<$($generic:ident $(: $bound:tt $(+ $bound2:tt)*)?),+>)?, $ffi_name:ty,
31 @ref $ref_arg:ident $ref_expr:expr, @unref $unref_arg:ident $unref_expr:expr) => {
32 $(#[$attr])*
33 #[repr(transparent)]
34 $visibility struct $name $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? {
35 inner: $crate::shared::Shared<$ffi_name, Self>,
36 }
37
38 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $name $(<$($generic),+>)? {
39 #[doc = "Return the inner pointer to the underlying C value."]
40 #[inline]
41 pub fn as_ptr(&self) -> *mut $ffi_name {
42 unsafe { *(self as *const Self as *const *const $ffi_name) as *mut $ffi_name }
43 }
44
45 #[doc = "Borrows the underlying C value."]
46 #[inline]
47 pub unsafe fn from_glib_ptr_borrow<'a>(ptr: *const *const $ffi_name) -> &'a Self {
48 &*(ptr as *const Self)
49 }
50 }
51
52 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? std::clone::Clone for $name $(<$($generic),+>)? {
53 #[inline]
54 fn clone(&self) -> Self {
55 Self {
56 inner: std::clone::Clone::clone(&self.inner),
57 }
58 }
59 }
60
61 #[doc(hidden)]
62 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::shared::SharedMemoryManager<$ffi_name> for $name $(<$($generic),+>)? {
63 #[inline]
64 unsafe fn ref_($ref_arg: *mut $ffi_name) {
65 $ref_expr;
66 }
67
68 #[inline]
69 #[allow(clippy::no_effect)]
70 unsafe fn unref($unref_arg: *mut $ffi_name) {
71 $unref_expr;
72 }
73 }
74
75 #[doc(hidden)]
76 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::GlibPtrDefault for $name $(<$($generic),+>)? {
77 type GlibType = *mut $ffi_name;
78 }
79
80 #[doc(hidden)]
81 unsafe impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::TransparentPtrType for $name $(<$($generic),+>)? {}
82
83 #[doc(hidden)]
84 impl<'a $(, $($generic $(: $bound $(+ $bound2)*)?),+)?> $crate::translate::ToGlibPtr<'a, *mut $ffi_name> for $name $(<$($generic),+>)? {
85 type Storage = std::marker::PhantomData<&'a $crate::shared::Shared<$ffi_name, Self>>;
86
87 #[inline]
88 fn to_glib_none(&'a self) -> $crate::translate::Stash<'a, *mut $ffi_name, Self> {
89 let stash = $crate::translate::ToGlibPtr::to_glib_none(&self.inner);
90 $crate::translate::Stash(stash.0, stash.1)
91 }
92
93 #[inline]
94 fn to_glib_full(&self) -> *mut $ffi_name {
95 $crate::translate::ToGlibPtr::to_glib_full(&self.inner)
96 }
97 }
98
99 #[doc(hidden)]
100 impl<'a $(, $($generic $(: $bound $(+ $bound2)*)?),+)?> $crate::translate::ToGlibPtr<'a, *const $ffi_name> for $name $(<$($generic),+>)? {
101 type Storage = std::marker::PhantomData<&'a $crate::shared::Shared<$ffi_name, Self>>;
102
103 #[inline]
104 fn to_glib_none(&'a self) -> $crate::translate::Stash<'a, *const $ffi_name, Self> {
105 let stash = $crate::translate::ToGlibPtr::to_glib_none(&self.inner);
106 $crate::translate::Stash(stash.0 as *const _, stash.1)
107 }
108
109 #[inline]
110 fn to_glib_full(&self) -> *const $ffi_name {
111 $crate::translate::ToGlibPtr::to_glib_full(&self.inner) as *const _
112 }
113 }
114
115 #[doc(hidden)]
116 impl<'a $(, $($generic $(: $bound $(+ $bound2)*)?),+)?> $crate::translate::ToGlibContainerFromSlice<'a, *mut *mut $ffi_name> for $name $(<$($generic),+>)? {
117 type Storage = (std::marker::PhantomData<&'a [Self]>, Option<Vec<*mut $ffi_name>>);
118
119 fn to_glib_none_from_slice(t: &'a [Self]) -> (*mut *mut $ffi_name, Self::Storage) {
120 let mut v_ptr = Vec::with_capacity(t.len() + 1);
121 unsafe {
122 let ptr = v_ptr.as_mut_ptr();
123 std::ptr::copy_nonoverlapping(t.as_ptr() as *mut *mut $ffi_name, ptr, t.len());
124 std::ptr::write(ptr.add(t.len()), std::ptr::null_mut());
125 v_ptr.set_len(t.len() + 1);
126 }
127
128 (v_ptr.as_ptr() as *mut *mut $ffi_name, (std::marker::PhantomData, Some(v_ptr)))
129 }
130
131 fn to_glib_container_from_slice(t: &'a [Self]) -> (*mut *mut $ffi_name, Self::Storage) {
132 let v_ptr = unsafe {
133 let v_ptr = $crate::ffi::g_malloc(std::mem::size_of::<*mut $ffi_name>() * (t.len() + 1)) as *mut *mut $ffi_name;
134
135 std::ptr::copy_nonoverlapping(t.as_ptr() as *mut *mut $ffi_name, v_ptr, t.len());
136 std::ptr::write(v_ptr.add(t.len()), std::ptr::null_mut());
137
138 v_ptr
139 };
140
141 (v_ptr, (std::marker::PhantomData, None))
142 }
143
144 fn to_glib_full_from_slice(t: &[Self]) -> *mut *mut $ffi_name {
145 unsafe {
146 let v_ptr = $crate::ffi::g_malloc(std::mem::size_of::<*mut $ffi_name>() * (t.len() + 1)) as *mut *mut $ffi_name;
147
148 for (i, s) in t.iter().enumerate() {
149 std::ptr::write(v_ptr.add(i), $crate::translate::ToGlibPtr::to_glib_full(s));
150 }
151 std::ptr::write(v_ptr.add(t.len()), std::ptr::null_mut());
152
153 v_ptr
154 }
155 }
156 }
157
158 #[doc(hidden)]
159 impl<'a $(, $($generic $(: $bound $(+ $bound2)*)?),+)?> $crate::translate::ToGlibContainerFromSlice<'a, *const *mut $ffi_name> for $name $(<$($generic),+>)? {
160 type Storage = (std::marker::PhantomData<&'a [Self]>, Option<Vec<*mut $ffi_name>>);
161
162 fn to_glib_none_from_slice(t: &'a [Self]) -> (*const *mut $ffi_name, Self::Storage) {
163 let (ptr, stash) = $crate::translate::ToGlibContainerFromSlice::<'a, *mut *mut $ffi_name>::to_glib_none_from_slice(t);
164 (ptr as *const *mut $ffi_name, stash)
165 }
166
167 fn to_glib_container_from_slice(_: &'a [Self]) -> (*const *mut $ffi_name, Self::Storage) {
168 // Can't have consumer free a *const pointer
169 unimplemented!()
170 }
171
172 fn to_glib_full_from_slice(_: &[Self]) -> *const *mut $ffi_name {
173 // Can't have consumer free a *const pointer
174 unimplemented!()
175 }
176 }
177
178 #[doc(hidden)]
179 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::FromGlibPtrNone<*mut $ffi_name> for $name $(<$($generic),+>)? {
180 #[inline]
181 unsafe fn from_glib_none(ptr: *mut $ffi_name) -> Self {
182 Self {
183 inner: $crate::translate::from_glib_none(ptr),
184 }
185 }
186 }
187
188 #[doc(hidden)]
189 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::FromGlibPtrNone<*const $ffi_name> for $name $(<$($generic),+>)? {
190 #[inline]
191 unsafe fn from_glib_none(ptr: *const $ffi_name) -> Self {
192 Self {
193 inner: $crate::translate::from_glib_none(ptr),
194 }
195 }
196 }
197
198 #[doc(hidden)]
199 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::FromGlibPtrFull<*mut $ffi_name> for $name $(<$($generic),+>)? {
200 #[inline]
201 unsafe fn from_glib_full(ptr: *mut $ffi_name) -> Self {
202 Self {
203 inner: $crate::translate::from_glib_full(ptr),
204 }
205 }
206 }
207
208 #[doc(hidden)]
209 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::FromGlibPtrBorrow<*mut $ffi_name> for $name $(<$($generic),+>)? {
210 #[inline]
211 unsafe fn from_glib_borrow(ptr: *mut $ffi_name) -> $crate::translate::Borrowed<Self> {
212 $crate::translate::Borrowed::new(
213 Self {
214 inner: $crate::translate::from_glib_borrow::<_, $crate::shared::Shared<_, _>>(ptr).into_inner(),
215 }
216 )
217 }
218 }
219
220 #[doc(hidden)]
221 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::FromGlibPtrBorrow<*const $ffi_name> for $name $(<$($generic),+>)? {
222 #[inline]
223 unsafe fn from_glib_borrow(ptr: *const $ffi_name) -> $crate::translate::Borrowed<Self> {
224 $crate::translate::from_glib_borrow::<_, Self>(ptr as *mut $ffi_name)
225 }
226 }
227
228 #[doc(hidden)]
229 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::FromGlibContainerAsVec<*mut $ffi_name, *mut *mut $ffi_name> for $name $(<$($generic),+>)? {
230 unsafe fn from_glib_none_num_as_vec(ptr: *mut *mut $ffi_name, num: usize) -> Vec<Self> {
231 if num == 0 || ptr.is_null() {
232 return Vec::new();
233 }
234
235 let mut res = Vec::<Self>::with_capacity(num);
236 let res_ptr = res.as_mut_ptr();
237 for i in 0..num {
238 ::std::ptr::write(res_ptr.add(i), $crate::translate::from_glib_none(std::ptr::read(ptr.add(i))));
239 }
240 res.set_len(num);
241 res
242 }
243
244 unsafe fn from_glib_container_num_as_vec(ptr: *mut *mut $ffi_name, num: usize) -> Vec<Self> {
245 let res = $crate::translate::FromGlibContainerAsVec::from_glib_none_num_as_vec(ptr, num);
246 $crate::ffi::g_free(ptr as *mut _);
247 res
248 }
249
250 unsafe fn from_glib_full_num_as_vec(ptr: *mut *mut $ffi_name, num: usize) -> Vec<Self> {
251 if num == 0 || ptr.is_null() {
252 $crate::ffi::g_free(ptr as *mut _);
253 return Vec::new();
254 }
255
256 let mut res = Vec::with_capacity(num);
257 let res_ptr = res.as_mut_ptr();
258 ::std::ptr::copy_nonoverlapping(ptr as *mut Self, res_ptr, num);
259 res.set_len(num);
260 $crate::ffi::g_free(ptr as *mut _);
261 res
262 }
263 }
264
265 #[doc(hidden)]
266 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::FromGlibPtrArrayContainerAsVec<*mut $ffi_name, *mut *mut $ffi_name> for $name $(<$($generic),+>)? {
267 unsafe fn from_glib_none_as_vec(ptr: *mut *mut $ffi_name) -> Vec<Self> {
268 $crate::translate::FromGlibContainerAsVec::from_glib_none_num_as_vec(ptr, $crate::translate::c_ptr_array_len(ptr))
269 }
270
271 unsafe fn from_glib_container_as_vec(ptr: *mut *mut $ffi_name) -> Vec<Self> {
272 $crate::translate::FromGlibContainerAsVec::from_glib_container_num_as_vec(ptr, $crate::translate::c_ptr_array_len(ptr))
273 }
274
275 unsafe fn from_glib_full_as_vec(ptr: *mut *mut $ffi_name) -> Vec<Self> {
276 $crate::translate::FromGlibContainerAsVec::from_glib_full_num_as_vec(ptr, $crate::translate::c_ptr_array_len(ptr))
277 }
278 }
279
280 #[doc(hidden)]
281 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::FromGlibContainerAsVec<*mut $ffi_name, *const *mut $ffi_name> for $name $(<$($generic),+>)? {
282 unsafe fn from_glib_none_num_as_vec(ptr: *const *mut $ffi_name, num: usize) -> Vec<Self> {
283 $crate::translate::FromGlibContainerAsVec::from_glib_none_num_as_vec(ptr as *mut *mut _, num)
284 }
285
286 unsafe fn from_glib_container_num_as_vec(_: *const *mut $ffi_name, _: usize) -> Vec<Self> {
287 // Can't free a *const
288 unimplemented!()
289 }
290
291 unsafe fn from_glib_full_num_as_vec(_: *const *mut $ffi_name, _: usize) -> Vec<Self> {
292 // Can't free a *const
293 unimplemented!()
294 }
295 }
296
297 #[doc(hidden)]
298 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::FromGlibPtrArrayContainerAsVec<*mut $ffi_name, *const *mut $ffi_name> for $name $(<$($generic),+>)? {
299 unsafe fn from_glib_none_as_vec(ptr: *const *mut $ffi_name) -> Vec<Self> {
300 $crate::translate::FromGlibPtrArrayContainerAsVec::from_glib_none_as_vec(ptr as *mut *mut _)
301 }
302
303 unsafe fn from_glib_container_as_vec(_: *const *mut $ffi_name) -> Vec<Self> {
304 // Can't free a *const
305 unimplemented!()
306 }
307
308 unsafe fn from_glib_full_as_vec(_: *const *mut $ffi_name) -> Vec<Self> {
309 // Can't free a *const
310 unimplemented!()
311 }
312 }
313
314 #[doc(hidden)]
315 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::IntoGlibPtr<*mut $ffi_name> for $name $(<$($generic),+>)? {
316 #[inline]
317 unsafe fn into_glib_ptr(self) -> *mut $ffi_name {
318 let s = std::mem::ManuallyDrop::new(self);
319 $crate::translate::ToGlibPtr::<*const $ffi_name>::to_glib_none(&*s).0 as *mut _
320 }
321 }
322
323 #[doc(hidden)]
324 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::translate::IntoGlibPtr<*const $ffi_name> for $name $(<$($generic),+>)? {
325 #[inline]
326 unsafe fn into_glib_ptr(self) -> *const $ffi_name {
327 let s = std::mem::ManuallyDrop::new(self);
328 $crate::translate::ToGlibPtr::<*const $ffi_name>::to_glib_none(&*s).0 as *const _
329 }
330 }
331 };
332
333 (@value_impl $name:ident $(<$($generic:ident $(: $bound:tt $(+ $bound2:tt)*)?),+>)?, $ffi_name:ty) => { };
334
335 (@value_impl $name:ident $(<$($generic:ident $(: $bound:tt $(+ $bound2:tt)*)?),+>)?, $ffi_name:ty, @type_ $get_type_expr:expr) => {
336 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::types::StaticType for $name $(<$($generic),+>)? {
337 #[inline]
338 fn static_type() -> $crate::types::Type {
339 #[allow(unused_unsafe)]
340 unsafe { $crate::translate::from_glib($get_type_expr) }
341 }
342 }
343
344 #[doc(hidden)]
345 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::value::ValueType for $name $(<$($generic),+>)? {
346 type Type = Self;
347 }
348
349 #[doc(hidden)]
350 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::value::ValueTypeOptional for $name $(<$($generic),+>)? { }
351
352 #[doc(hidden)]
353 unsafe impl<'a $(, $($generic $(: $bound $(+ $bound2)*)?),+)?> $crate::value::FromValue<'a> for $name $(<$($generic),+>)? {
354 type Checker = $crate::value::GenericValueTypeOrNoneChecker<Self>;
355
356 #[inline]
357 unsafe fn from_value(value: &'a $crate::Value) -> Self {
358 let ptr = $crate::gobject_ffi::g_value_dup_boxed($crate::translate::ToGlibPtr::to_glib_none(value).0);
359 debug_assert!(!ptr.is_null());
360 <Self as $crate::translate::FromGlibPtrFull<*mut $ffi_name>>::from_glib_full(ptr as *mut $ffi_name)
361 }
362 }
363
364 #[doc(hidden)]
365 unsafe impl<'a $(, $($generic $(: $bound $(+ $bound2)*)?),+)?> $crate::value::FromValue<'a> for &'a $name $(<$($generic),+>)? {
366 type Checker = $crate::value::GenericValueTypeOrNoneChecker<Self>;
367
368 #[inline]
369 unsafe fn from_value(value: &'a $crate::Value) -> Self {
370 debug_assert_eq!(std::mem::size_of::<Self>(), std::mem::size_of::<$crate::ffi::gpointer>());
371 let value = &*(value as *const $crate::Value as *const $crate::gobject_ffi::GValue);
372 debug_assert!(!value.data[0].v_pointer.is_null());
373 <$name $(<$($generic),+>)?>::from_glib_ptr_borrow(&value.data[0].v_pointer as *const $crate::ffi::gpointer as *const *const $ffi_name)
374 }
375 }
376
377 #[doc(hidden)]
378 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::value::ToValue for $name $(<$($generic),+>)? {
379 #[inline]
380 fn to_value(&self) -> $crate::Value {
381 unsafe {
382 let mut value = $crate::Value::from_type_unchecked(<Self as $crate::StaticType>::static_type());
383 $crate::gobject_ffi::g_value_take_boxed(
384 $crate::translate::ToGlibPtrMut::to_glib_none_mut(&mut value).0,
385 $crate::translate::ToGlibPtr::<*mut $ffi_name>::to_glib_full(self) as *mut _,
386 );
387 value
388 }
389 }
390
391 #[inline]
392 fn value_type(&self) -> $crate::Type {
393 <Self as $crate::StaticType>::static_type()
394 }
395 }
396
397 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? std::convert::From<$name $(<$($generic),+>)?> for $crate::Value {
398 #[inline]
399 fn from(s: $name $(<$($generic),+>)?) -> Self {
400 unsafe {
401 let mut value = $crate::Value::from_type_unchecked(<$name $(<$($generic),+>)? as $crate::StaticType>::static_type());
402 $crate::gobject_ffi::g_value_take_boxed(
403 $crate::translate::ToGlibPtrMut::to_glib_none_mut(&mut value).0,
404 $crate::translate::IntoGlibPtr::<*mut $ffi_name>::into_glib_ptr(s) as *mut _,
405 );
406 value
407 }
408 }
409 }
410
411 #[doc(hidden)]
412 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::value::ToValueOptional for $name $(<$($generic),+>)? {
413 #[inline]
414 fn to_value_optional(s: Option<&Self>) -> $crate::Value {
415 let mut value = $crate::Value::for_value_type::<Self>();
416 unsafe {
417 $crate::gobject_ffi::g_value_take_boxed(
418 $crate::translate::ToGlibPtrMut::to_glib_none_mut(&mut value).0,
419 $crate::translate::ToGlibPtr::<*mut $ffi_name>::to_glib_full(&s) as *mut _,
420 );
421 }
422
423 value
424 }
425 }
426
427 impl $(<$($generic $(: $bound $(+ $bound2)*)?),+>)? $crate::HasParamSpec for $name $(<$($generic),+>)? {
428 type ParamSpec = $crate::ParamSpecBoxed;
429 type SetValue = Self;
430 type BuilderFn = fn(&str) -> $crate::ParamSpecBoxedBuilder<Self>;
431
432 fn param_spec_builder() -> Self::BuilderFn {
433 |name| Self::ParamSpec::builder(name)
434 }
435 }
436 };
437}
438
439pub trait SharedMemoryManager<T> {
440 /// # Safety
441 ///
442 /// Callers are responsible for ensuring that a matching call to `unref`
443 /// is made at an appropriate time.
444 unsafe fn ref_(ptr: *mut T);
445
446 /// # Safety
447 ///
448 /// Callers are responsible for ensuring that a matching call to `ref` was
449 /// made before this is called, and that the pointer is not used after the
450 /// `unref` call.
451 unsafe fn unref(ptr: *mut T);
452}
453
454/// Encapsulates memory management logic for shared types.
455#[repr(transparent)]
456pub struct Shared<T, MM: SharedMemoryManager<T>> {
457 inner: ptr::NonNull<T>,
458 mm: PhantomData<*const MM>,
459}
460
461impl<T, MM: SharedMemoryManager<T>> Drop for Shared<T, MM> {
462 #[inline]
463 fn drop(&mut self) {
464 unsafe {
465 MM::unref(self.inner.as_ptr());
466 }
467 }
468}
469
470impl<T, MM: SharedMemoryManager<T>> Clone for Shared<T, MM> {
471 #[inline]
472 fn clone(&self) -> Self {
473 unsafe {
474 MM::ref_(self.inner.as_ptr());
475 }
476 Self {
477 inner: self.inner,
478 mm: PhantomData,
479 }
480 }
481}
482
483impl<T, MM: SharedMemoryManager<T>> fmt::Debug for Shared<T, MM> {
484 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
485 f&mut DebugStruct<'_, '_>.debug_struct("Shared")
486 .field(name:"inner", &self.inner)
487 .finish()
488 }
489}
490
491impl<T, MM: SharedMemoryManager<T>> PartialOrd for Shared<T, MM> {
492 #[inline]
493 fn partial_cmp(&self, other: &Self) -> Option<cmp::Ordering> {
494 Some(self.cmp(other))
495 }
496}
497
498impl<T, MM: SharedMemoryManager<T>> Ord for Shared<T, MM> {
499 #[inline]
500 fn cmp(&self, other: &Self) -> cmp::Ordering {
501 self.inner.cmp(&other.inner)
502 }
503}
504
505impl<T, MM: SharedMemoryManager<T>> PartialEq for Shared<T, MM> {
506 #[inline]
507 fn eq(&self, other: &Self) -> bool {
508 self.inner == other.inner
509 }
510}
511
512impl<T, MM: SharedMemoryManager<T>> Eq for Shared<T, MM> {}
513
514impl<T, MM: SharedMemoryManager<T>> Hash for Shared<T, MM> {
515 #[inline]
516 fn hash<H>(&self, state: &mut H)
517 where
518 H: Hasher,
519 {
520 self.inner.hash(state)
521 }
522}
523
524impl<'a, T: 'static, MM> ToGlibPtr<'a, *mut T> for Shared<T, MM>
525where
526 MM: SharedMemoryManager<T> + 'static,
527{
528 type Storage = PhantomData<&'a Self>;
529
530 #[inline]
531 fn to_glib_none(&'a self) -> Stash<'a, *mut T, Self> {
532 Stash(self.inner.as_ptr(), PhantomData)
533 }
534
535 #[inline]
536 fn to_glib_full(&self) -> *mut T {
537 unsafe {
538 MM::ref_(self.inner.as_ptr());
539 }
540 self.inner.as_ptr()
541 }
542}
543
544impl<T: 'static, MM: SharedMemoryManager<T>> FromGlibPtrNone<*mut T> for Shared<T, MM> {
545 #[inline]
546 unsafe fn from_glib_none(ptr: *mut T) -> Self {
547 debug_assert!(!ptr.is_null());
548 MM::ref_(ptr);
549 Self {
550 inner: ptr::NonNull::new_unchecked(ptr),
551 mm: PhantomData,
552 }
553 }
554}
555
556impl<T: 'static, MM: SharedMemoryManager<T>> FromGlibPtrNone<*const T> for Shared<T, MM> {
557 #[inline]
558 unsafe fn from_glib_none(ptr: *const T) -> Self {
559 debug_assert!(!ptr.is_null());
560 MM::ref_(ptr as *mut _);
561 Self {
562 inner: ptr::NonNull::new_unchecked(ptr as *mut _),
563 mm: PhantomData,
564 }
565 }
566}
567
568impl<T: 'static, MM: SharedMemoryManager<T>> FromGlibPtrFull<*mut T> for Shared<T, MM> {
569 #[inline]
570 unsafe fn from_glib_full(ptr: *mut T) -> Self {
571 debug_assert!(!ptr.is_null());
572 Self {
573 inner: ptr::NonNull::new_unchecked(ptr),
574 mm: PhantomData,
575 }
576 }
577}
578
579impl<T: 'static, MM: SharedMemoryManager<T>> FromGlibPtrBorrow<*mut T> for Shared<T, MM> {
580 #[inline]
581 unsafe fn from_glib_borrow(ptr: *mut T) -> Borrowed<Self> {
582 debug_assert!(!ptr.is_null());
583 Borrowed::new(Self {
584 inner: ptr::NonNull::new_unchecked(ptr),
585 mm: PhantomData,
586 })
587 }
588}
589