1use xmlserde::xml_serde_enum;
2use xmlserde_derives::XmlDeserialize;
3
4use crate::{
5 array::Array,
6 attribute::Attribute,
7 documentation::{DocDeprecated, DocStability, DocVersion, Documentation, SourcePosition},
8 prelude::*,
9 r#type::Type,
10 FunctionScope, TransferOwnership,
11};
12
13xml_serde_enum! {
14 #[derive(Debug, Copy, Clone, PartialEq, Eq, PartialOrd, Ord)]
15 Direction {
16 In => "in",
17 Out => "out",
18 InOut => "inout",
19 }
20}
21
22#[derive(Clone, Debug, PartialEq, Eq, XmlDeserialize)]
23pub enum ParameterType {
24 #[xmlserde(name = b"type")]
25 Type(Type),
26 #[xmlserde(name = b"array")]
27 Array(Array),
28 #[xmlserde(name = b"varargs")]
29 VarArgs,
30}
31
32impl From<crate::r#type::Type> for ParameterType {
33 fn from(value: crate::r#type::Type) -> Self {
34 Self::Type(value)
35 }
36}
37
38impl From<crate::r#type::AnyType> for ParameterType {
39 fn from(value: crate::r#type::AnyType) -> Self {
40 match value {
41 crate::r#type::AnyType::Array(arr) => Self::Array(arr),
42 crate::r#type::AnyType::Type(ty) => Self::Type(ty),
43 }
44 }
45}
46
47#[derive(Debug, Clone, Copy, PartialEq, Eq)]
49pub enum AnyParameter<'a> {
50 Instance(&'a InstanceParameter),
51 Regular(&'a Parameter),
52}
53
54impl<'a> AnyParameter<'a> {
55 pub fn name(&self) -> &str {
56 match self {
57 Self::Instance(p) => p.name(),
58 Self::Regular(p) => p.name(),
59 }
60 }
61
62 pub fn is_instance(&self) -> bool {
63 matches!(self, Self::Instance(_))
64 }
65
66 pub fn is_regular(&self) -> bool {
67 matches!(self, Self::Regular(_))
68 }
69
70 pub fn as_instance(&self) -> &'a InstanceParameter {
71 match self {
72 Self::Instance(p) => p,
73 _ => unreachable!(),
74 }
75 }
76
77 pub fn as_regular(&self) -> &'a Parameter {
78 match self {
79 Self::Regular(p) => p,
80 _ => unreachable!(),
81 }
82 }
83
84 pub fn is_nullable(&self) -> Option<bool> {
85 match self {
86 Self::Instance(p) => p.is_nullable(),
87 Self::Regular(p) => p.is_nullable(),
88 }
89 }
90
91 pub fn is_allow_none(&self) -> Option<bool> {
92 match self {
93 Self::Instance(p) => p.is_allow_none(),
94 Self::Regular(p) => p.is_allow_none(),
95 }
96 }
97
98 pub fn direction(&self) -> Option<Direction> {
99 match self {
100 Self::Instance(p) => p.direction(),
101 Self::Regular(p) => p.direction(),
102 }
103 }
104
105 pub fn is_caller_allocates(&self) -> Option<bool> {
106 match self {
107 Self::Instance(p) => p.is_caller_allocates(),
108 Self::Regular(p) => p.is_caller_allocates(),
109 }
110 }
111
112 pub fn transfer_ownership(&self) -> Option<TransferOwnership> {
113 match self {
114 Self::Instance(p) => p.transfer_ownership(),
115 Self::Regular(p) => p.transfer_ownership(),
116 }
117 }
118}
119
120#[derive(Clone, Debug, Default, PartialEq, Eq, XmlDeserialize)]
121#[xmlserde(root = b"parameters")]
122#[xmlserde(deny_unknown_fields)]
123pub struct Parameters {
124 #[xmlserde(name = b"instance-parameter", ty = "child")]
125 instance_parameter: Option<InstanceParameter>,
126 #[xmlserde(name = b"parameter", ty = "child")]
127 parameter: Vec<Parameter>,
128}
129
130impl Parameters {
131 pub fn is_empty(&self) -> bool {
132 self.instance_parameter.is_none() && self.parameter.is_empty()
133 }
134
135 pub fn instance(&self) -> Option<&InstanceParameter> {
136 self.instance_parameter.as_ref()
137 }
138
139 pub fn inner(&self) -> &[Parameter] {
140 &self.parameter
141 }
142
143 pub fn all(&self) -> impl Iterator<Item = AnyParameter<'_>> {
145 self.instance_parameter
146 .iter()
147 .map(AnyParameter::Instance)
148 .chain(self.parameter.iter().map(AnyParameter::Regular))
149 }
150}
151
152impl IntoIterator for Parameters {
153 type Item = Parameter;
154 type IntoIter = std::vec::IntoIter<Self::Item>;
155
156 fn into_iter(self) -> Self::IntoIter {
157 self.parameter.into_iter()
158 }
159}
160
161impl<'a> IntoIterator for &'a Parameters {
162 type Item = &'a Parameter;
163 type IntoIter = std::slice::Iter<'a, Parameter>;
164
165 fn into_iter(self) -> Self::IntoIter {
166 self.parameter.iter()
167 }
168}
169
170impl AsRef<[Parameter]> for Parameters {
171 fn as_ref(&self) -> &[Parameter] {
172 &self.parameter
173 }
174}
175
176impl std::ops::Deref for Parameters {
177 type Target = [Parameter];
178
179 fn deref(&self) -> &Self::Target {
180 &self.parameter
181 }
182}
183
184impl std::ops::Index<usize> for Parameters {
185 type Output = Parameter;
186
187 fn index(&self, index: usize) -> &Self::Output {
188 &self.parameter[index]
189 }
190}
191
192#[derive(Clone, Debug, PartialEq, Eq, XmlDeserialize)]
193#[xmlserde(root = b"parameter")]
194#[xmlserde(deny_unknown_fields)]
195pub struct Parameter {
196 #[xmlserde(name = b"name", ty = "attr")]
197 name: String,
198 #[xmlserde(name = b"transfer-ownership", ty = "attr")]
199 transfer: Option<TransferOwnership>,
200 #[xmlserde(name = b"nullable", ty = "attr")]
201 nullable: Option<bool>,
202 #[xmlserde(name = b"allow-none", ty = "attr")]
203 allow_none: Option<bool>,
204 #[xmlserde(name = b"introspectable", ty = "attr")]
205 introspectable: Option<bool>,
206 #[xmlserde(name = b"scope", ty = "attr")]
207 scope: Option<FunctionScope>,
208 #[xmlserde(name = b"closure", ty = "attr")]
209 closure: Option<usize>,
210 #[xmlserde(name = b"destroy", ty = "attr")]
211 destroy: Option<usize>,
212 #[xmlserde(name = b"direction", ty = "attr")]
213 direction: Option<Direction>,
214 #[xmlserde(name = b"caller-allocates", ty = "attr")]
215 caller_allocates: Option<bool>,
216 #[xmlserde(name = b"optional", ty = "attr")]
217 optional: Option<bool>,
218 #[xmlserde(name = b"skip", ty = "attr")]
219 skip: Option<bool>,
220 #[xmlserde(name = b"doc", ty = "child")]
222 doc: Option<Documentation>,
223 #[xmlserde(name = b"doc-deprecated", ty = "child")]
224 doc_deprecated: Option<DocDeprecated>,
225 #[xmlserde(name = b"doc-stability", ty = "child")]
226 doc_stability: Option<DocStability>,
227 #[xmlserde(name = b"doc-version", ty = "child")]
228 doc_version: Option<DocVersion>,
229 #[xmlserde(name = b"source-position", ty = "child")]
230 source_position: Option<SourcePosition>,
231 #[xmlserde(name = b"attribute", ty = "child")]
233 attributes: Vec<Attribute>,
234 #[xmlserde(ty = "untag")]
235 type_: Option<ParameterType>,
236}
237
238impl Parameter {
239 pub fn name(&self) -> &str {
240 &self.name
241 }
242
243 pub fn is_nullable(&self) -> Option<bool> {
244 self.nullable
245 }
246
247 pub fn is_allow_none(&self) -> Option<bool> {
248 self.allow_none
249 }
250
251 pub fn is_introspectable(&self) -> bool {
252 self.introspectable.unwrap_or(true)
253 }
254
255 pub fn scope(&self) -> Option<FunctionScope> {
256 self.scope
257 }
258
259 pub fn closure(&self) -> Option<usize> {
260 self.closure
261 }
262
263 pub fn destroy(&self) -> Option<usize> {
264 self.destroy
265 }
266
267 pub fn direction(&self) -> Option<Direction> {
268 self.direction
269 }
270
271 pub fn is_caller_allocates(&self) -> Option<bool> {
272 self.caller_allocates
273 }
274
275 pub fn is_optional(&self) -> Option<bool> {
276 self.optional
277 }
278
279 pub fn is_skip(&self) -> Option<bool> {
280 self.skip
281 }
282
283 pub fn transfer_ownership(&self) -> Option<TransferOwnership> {
284 self.transfer
285 }
286
287 pub fn ty(&self) -> Option<&ParameterType> {
288 self.type_.as_ref()
289 }
290}
291
292impl_attributable!(Parameter);
293impl_documentable!(Parameter);
294
295#[derive(Clone, Debug, PartialEq, Eq, XmlDeserialize)]
296#[xmlserde(root = b"instance-parameter")]
297#[xmlserde(deny_unknown_fields)]
298pub struct InstanceParameter {
299 #[xmlserde(name = b"name", ty = "attr")]
300 name: String,
301 #[xmlserde(name = b"transfer-ownership", ty = "attr")]
302 transfer: Option<TransferOwnership>,
303 #[xmlserde(name = b"nullable", ty = "attr")]
304 nullable: Option<bool>,
305 #[xmlserde(name = b"allow-none", ty = "attr")]
306 allow_none: Option<bool>,
307 #[xmlserde(name = b"direction", ty = "attr")]
308 direction: Option<Direction>,
309 #[xmlserde(name = b"caller-allocates", ty = "attr")]
310 caller_allocates: Option<bool>,
311 #[xmlserde(name = b"doc", ty = "child")]
313 doc: Option<Documentation>,
314 #[xmlserde(name = b"doc-deprecated", ty = "child")]
315 doc_deprecated: Option<DocDeprecated>,
316 #[xmlserde(name = b"doc-stability", ty = "child")]
317 doc_stability: Option<DocStability>,
318 #[xmlserde(name = b"doc-version", ty = "child")]
319 doc_version: Option<DocVersion>,
320 #[xmlserde(name = b"source-position", ty = "child")]
321 source_position: Option<SourcePosition>,
322 #[xmlserde(name = b"type", ty = "child")]
323 type_: Option<Type>,
324}
325
326impl InstanceParameter {
327 pub fn name(&self) -> &str {
328 &self.name
329 }
330
331 pub fn is_nullable(&self) -> Option<bool> {
332 self.nullable
333 }
334
335 pub fn is_allow_none(&self) -> Option<bool> {
336 self.allow_none
337 }
338
339 pub fn direction(&self) -> Option<Direction> {
340 self.direction
341 }
342
343 pub fn is_caller_allocates(&self) -> Option<bool> {
344 self.caller_allocates
345 }
346
347 pub fn transfer_ownership(&self) -> Option<TransferOwnership> {
348 self.transfer
349 }
350
351 pub fn ty(&self) -> Option<&Type> {
352 self.type_.as_ref()
353 }
354}
355
356impl_documentable!(InstanceParameter);