maplibre_native_ffi/
call.rs1use std::ffi::c_void;
5
6use maplibre_native_ffi_sys::{self as sys, NativeHandle};
7
8use crate::Result;
9use crate::completion::{self, CommandCompletion, NativeFuture};
10use crate::convert::{self, InputArena, ToNative};
11
12pub(crate) struct Call<'a, H: NativeHandle> {
13 native: H,
14 _owner: std::marker::PhantomData<&'a H>,
16 arena: InputArena,
17}
18
19impl Call<'static, ()> {
20 pub(crate) fn global() -> Self {
21 Self::new(())
22 }
23}
24
25impl<'a, H: NativeHandle> Call<'a, H> {
26 pub(crate) fn new(native: H) -> Self {
27 Self {
28 native,
29 _owner: std::marker::PhantomData,
30 arena: InputArena::default(),
31 }
32 }
33
34 pub(crate) fn input<N, T: ToNative<N> + ?Sized>(&mut self, value: &T) -> Result<N> {
35 value.to_native(&mut self.arena)
36 }
37
38 pub(crate) fn array<N: 'static, T: ToNative<N>>(&mut self, values: &[T]) -> Result<*const N> {
39 convert::array(values, &mut self.arena)
40 }
41
42 pub(crate) fn reference<N: 'static, T: ToNative<N> + ?Sized>(
43 &mut self,
44 value: &T,
45 ) -> Result<*const N> {
46 convert::reference(value, &mut self.arena)
47 }
48
49 pub(crate) fn optional_reference<N: 'static, T: ToNative<N> + ?Sized>(
50 &mut self,
51 value: Option<&T>,
52 ) -> Result<*const N> {
53 convert::optional_reference(value, &mut self.arena)
54 }
55
56 pub(crate) fn status(
60 &mut self,
61 call: impl FnOnce(H, *mut sys::mln_diagnostic) -> sys::mln_status,
62 ) -> Result<()> {
63 crate::error::check(|diagnostic| call(self.native, diagnostic))?;
64 self.arena.accept_registrations();
65 Ok(())
66 }
67
68 pub(crate) fn status_registered(
70 &mut self,
71 call: impl FnOnce(H, *mut sys::mln_diagnostic) -> (sys::mln_status, bool),
72 ) -> Result<()> {
73 let mut accepted = false;
74 crate::error::check(|diagnostic| {
75 let (status, retained) = call(self.native, diagnostic);
76 accepted = retained;
77 status
78 })?;
79 if accepted {
80 self.arena.accept_registrations();
81 }
82 Ok(())
83 }
84
85 pub(crate) fn run<R>(&mut self, call: impl FnOnce(H) -> R) -> R {
86 let result = call(self.native);
87 self.arena.accept_registrations();
88 result
89 }
90
91 pub(crate) fn command(
92 self,
93 submit: impl FnOnce(H, *const sys::mln_completion, *mut sys::mln_diagnostic) -> sys::mln_status,
94 ) -> Result<NativeFuture<CommandCompletion>> {
95 self.complete(submit, completion::command)
96 }
97
98 pub(crate) fn discard(
99 mut self,
100 submit: impl FnOnce(H, *const sys::mln_completion, *mut sys::mln_diagnostic) -> sys::mln_status,
101 ) -> Result<()> {
102 crate::error::check(|diagnostic| submit(self.native, std::ptr::null(), diagnostic))?;
103 self.arena.accept_registrations();
104 Ok(())
105 }
106
107 pub(crate) fn complete<T: Send + 'static>(
108 mut self,
109 submit: impl FnOnce(H, *const sys::mln_completion, *mut sys::mln_diagnostic) -> sys::mln_status,
110 convert: impl FnOnce(&sys::mln_completion_result) -> Result<T> + Send + 'static,
111 ) -> Result<NativeFuture<T>> {
112 let native = self.native;
113 let future = completion::submit(
114 |completion, diagnostic| submit(native, completion, diagnostic),
115 convert,
116 )?;
117 self.arena.accept_registrations();
118 Ok(future)
119 }
120}
121
122pub(crate) struct ViewScope {
125 token: *mut c_void,
126 end: unsafe extern "C" fn(*mut c_void),
127}
128
129unsafe impl Send for ViewScope {}
132unsafe impl Sync for ViewScope {}
134
135impl ViewScope {
136 pub(crate) unsafe fn begin<H: NativeHandle>(
142 native: H,
143 begin: unsafe extern "C" fn(
144 H,
145 *mut *mut c_void,
146 *mut sys::mln_diagnostic,
147 ) -> sys::mln_status,
148 end: unsafe extern "C" fn(*mut c_void),
149 ) -> Result<Self> {
150 let mut token = std::ptr::null_mut();
151 crate::error::check(|diagnostic| unsafe { begin(native, &mut token, diagnostic) })?;
153 Ok(Self { token, end })
154 }
155}
156
157impl Drop for ViewScope {
158 fn drop(&mut self) {
159 unsafe { (self.end)(self.token) };
161 }
162}
163
164pub struct Lent<'v, T> {
172 value: T,
173 _view: std::marker::PhantomData<&'v ()>,
174}
175
176impl<T> Lent<'_, T> {
177 pub(crate) fn new(value: T) -> Self {
178 Self {
179 value,
180 _view: std::marker::PhantomData,
181 }
182 }
183}
184
185impl<T> std::ops::Deref for Lent<'_, T> {
186 type Target = T;
187
188 fn deref(&self) -> &T {
189 &self.value
190 }
191}
192
193impl<T: std::fmt::Debug> std::fmt::Debug for Lent<'_, T> {
194 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
195 self.value.fmt(f)
196 }
197}