Line data Source code
1 : use lief_ffi as ffi;
2 : use cxx::memory::UniquePtrTarget;
3 : use std::marker::PhantomData;
4 :
5 : use crate::Range;
6 :
7 : #[doc(hidden)]
8 : pub trait FromFFI<T: UniquePtrTarget> {
9 : fn from_ffi(ptr: cxx::UniquePtr<T>) -> Self;
10 : }
11 :
12 : #[doc(hidden)]
13 : pub trait AsFFI<U> {
14 : fn as_ffi(&self) -> &U;
15 :
16 : #[allow(dead_code)]
17 : fn as_mut_ffi(&mut self) -> std::pin::Pin<&mut U>;
18 : }
19 :
20 : #[doc(hidden)]
21 2567980 : pub fn into_optional<T: FromFFI<U>, U: UniquePtrTarget>(raw_ffi: cxx::UniquePtr<U>) -> Option<T> {
22 2567980 : if raw_ffi.is_null() {
23 1134510 : None
24 : } else {
25 1433470 : Some(T::from_ffi(raw_ffi))
26 : }
27 2567980 : }
28 :
29 :
30 : #[doc(hidden)]
31 0 : pub fn into_ranges(raw_ffi: cxx::UniquePtr<cxx::CxxVector<ffi::Range>>) -> Vec<Range> {
32 0 : let cxx_vec = raw_ffi.as_ref().unwrap();
33 0 : if cxx_vec.is_empty() {
34 0 : return Vec::new();
35 0 : }
36 0 :
37 0 : let mut rust_range: Vec<Range> = Vec::with_capacity(cxx_vec.len());
38 :
39 0 : for ffi_range in cxx_vec {
40 0 : rust_range.push(Range::from_ffi(ffi_range));
41 0 : }
42 :
43 0 : rust_range
44 0 : }
45 :
46 : pub struct Iterator<'a, Parent: UniquePtrTarget, It: UniquePtrTarget> {
47 : #[doc(hidden)]
48 : pub it: cxx::UniquePtr<It>,
49 : _owner: PhantomData<&'a Parent>,
50 : }
51 :
52 : impl<'a, Parent: UniquePtrTarget, It: UniquePtrTarget> Iterator<'a, Parent, It> {
53 : #[doc(hidden)]
54 340210 : pub fn new(it: cxx::UniquePtr<It>) -> Self {
55 340210 : Self {
56 340210 : it,
57 340210 : _owner: PhantomData,
58 340210 : }
59 340210 : }
60 : }
61 :
62 : #[doc(hidden)]
63 : #[macro_export]
64 : macro_rules! declare_iterator_conv {
65 : ($name:ident, $from:ty, $ffi:ty, $parent:ty, $ffi_iterator:ty, $conv: expr) => {
66 : pub type $name<'a> = $crate::common::Iterator<'a, $parent, $ffi_iterator>;
67 : impl<'a> Iterator for $name<'a> {
68 : type Item = $from;
69 5050420 : fn next(&mut self) -> Option<Self::Item> {
70 5050420 : let next = self.it.as_mut().unwrap().next();
71 5050420 : if next.is_null() {
72 340210 : None
73 : } else {
74 4710210 : Some($conv(next))
75 : }
76 5050420 : }
77 : }
78 : impl<'a> ExactSizeIterator for $name<'a> {
79 0 : fn len(&self) -> usize {
80 0 : self.it.as_ref().unwrap().size().try_into().unwrap()
81 0 : }
82 : }
83 : };
84 : }
85 :
86 : #[doc(hidden)]
87 : #[macro_export]
88 : macro_rules! declare_iterator {
89 : ($name:ident, $from:ty, $ffi:ty, $parent:ty, $ffi_iterator:ty) => {
90 : $crate::declare_iterator_conv!($name, $from, $ffi, $parent, $ffi_iterator, |n| {
91 : Self::Item::from_ffi(n)
92 : });
93 : };
94 : }
95 :
96 : pub struct ForwardIterator<'a, Parent: UniquePtrTarget, It: UniquePtrTarget> {
97 : #[doc(hidden)]
98 : pub it: cxx::UniquePtr<It>,
99 : _owner: PhantomData<&'a Parent>,
100 : }
101 :
102 : impl<'a, Parent: UniquePtrTarget, It: UniquePtrTarget> ForwardIterator<'a, Parent, It> {
103 : #[doc(hidden)]
104 490 : pub fn new(it: cxx::UniquePtr<It>) -> Self {
105 490 : Self {
106 490 : it,
107 490 : _owner: PhantomData,
108 490 : }
109 490 : }
110 : }
111 :
112 : #[doc(hidden)]
113 : #[macro_export]
114 : macro_rules! declare_fwd_iterator_conv {
115 : ($name:ident, $from:ty, $ffi:ty, $parent:ty, $ffi_iterator:ty, $conv: expr) => {
116 : pub type $name<'a> = $crate::common::ForwardIterator<'a, $parent, $ffi_iterator>;
117 : impl<'a> Iterator for $name<'a> {
118 : type Item = $from;
119 790130 : fn next(&mut self) -> Option<Self::Item> {
120 790130 : let next = self.it.as_mut().unwrap().next();
121 790130 : if next.is_null() {
122 490 : None
123 : } else {
124 789640 : Some($conv(next))
125 : }
126 790130 : }
127 : }
128 : };
129 : }
130 :
131 : #[doc(hidden)]
132 : #[macro_export]
133 : macro_rules! declare_fwd_iterator {
134 : ($name:ident, $from:ty, $ffi:ty, $parent:ty, $ffi_iterator:ty) => {
135 : $crate::declare_fwd_iterator_conv!($name, $from, $ffi, $parent, $ffi_iterator, |n| {
136 : Self::Item::from_ffi(n)
137 : });
138 : };
139 : }
140 :
141 :
142 : #[doc(hidden)]
143 : #[macro_export]
144 : macro_rules! to_slice {
145 : ($e:expr) => {
146 : let content_ptr = $e;
147 : unsafe {
148 : if content_ptr.size > 0 {
149 : return std::slice::from_raw_parts_mut(content_ptr.ptr, content_ptr.size as usize);
150 : }
151 : return &[];
152 : }
153 : };
154 : }
155 :
156 :
157 : #[doc(hidden)]
158 : #[macro_export]
159 : macro_rules! to_result {
160 : ($func: expr, $self: expr, $($arg:tt)*) => {
161 : let mut err: u32 = 0;
162 :
163 : let value = $func(&$self.ptr, $($arg),*, std::pin::Pin::new(&mut err));
164 : if err > 0 {
165 : return Err($crate::Error::from(err));
166 : }
167 : return Ok(value);
168 : };
169 : ($func: expr, $self: expr) => {
170 : let mut err: u32 = 0;
171 : let value = $func(&$self.ptr, std::pin::Pin::new(&mut err));
172 :
173 : if err > 0 {
174 : return Err($crate::Error::from(err));
175 : }
176 : return Ok(value);
177 : };
178 : }
179 :
180 : #[doc(hidden)]
181 : #[macro_export]
182 : macro_rules! to_conv_result {
183 : ($func: expr, $self: expr, $conv: expr, $($arg:tt)*) => {
184 : let mut err: u32 = 0;
185 : let value = $func(&$self, $($arg),*, std::pin::Pin::new(&mut err));
186 : if err > 0 {
187 : return Err($crate::Error::from(err));
188 : }
189 : return Ok($conv(value));
190 : };
191 : ($func: expr, $self: expr, $conv: expr) => {
192 : let mut err: u32 = 0;
193 : let value = $func(&$self, std::pin::Pin::new(&mut err));
194 : if err > 0 {
195 : return Err($crate::Error::from(err));
196 : }
197 : return Ok($conv(value));
198 : };
199 : }
200 :
201 : #[doc(hidden)]
202 : #[macro_export]
203 : macro_rules! to_opt {
204 : ($func: expr, $self: expr, $($arg:tt)*) => {
205 : let mut _is_set: u32 = 0;
206 :
207 : let value = $func(&$self.ptr, $($arg),*, std::pin::Pin::new(&mut _is_set));
208 : if _is_set == 0 {
209 : return None;
210 : }
211 : return Some(value.into());
212 : };
213 : ($func: expr, $self: expr) => {
214 : let mut _is_set: u32 = 0;
215 : let value = $func(&$self.ptr, std::pin::Pin::new(&mut _is_set));
216 :
217 : if _is_set == 0 {
218 : return None;
219 : }
220 : return Some(value.into());
221 : };
222 : }
223 :
224 :
225 : #[doc(hidden)]
226 : #[macro_export]
227 : macro_rules! to_conv_opt {
228 : ($func: expr, $self: expr, $conv: expr, $($arg:tt)*) => {
229 : let mut _is_set: u32 = 0;
230 :
231 : let value = $func(&$self.ptr, $($arg),*, std::pin::Pin::new(&mut _is_set));
232 : if _is_set == 0 {
233 : return None;
234 : }
235 : return Some($conv(value.into()));
236 : };
237 : ($func: expr, $self: expr, $conv: expr) => {
238 : let mut _is_set: u32 = 0;
239 : let value = $func(&$self.ptr, std::pin::Pin::new(&mut _is_set));
240 :
241 : if _is_set == 0 {
242 : return None;
243 : }
244 : return Some($conv(value.into()));
245 : };
246 : }
247 :
|