1 use {Generics, Lifetime, MutTy, Mutability, Path, QSelf, Ty, TyParamBound};
2 use aster::ident::ToIdent;
3 use aster::invoke::{Invoke, Identity};
4 use aster::lifetime::IntoLifetime;
5 use aster::path::PathBuilder;
6 use aster::qpath::QPathBuilder;
7 use aster::ty_param::TyParamBoundBuilder;
8 
9 // ////////////////////////////////////////////////////////////////////////////
10 
11 pub struct TyBuilder<F = Identity> {
12     callback: F,
13 }
14 
15 impl TyBuilder {
new() -> Self16     pub fn new() -> Self {
17         TyBuilder::with_callback(Identity)
18     }
19 }
20 
21 impl<F> TyBuilder<F>
22     where F: Invoke<Ty>
23 {
with_callback(callback: F) -> Self24     pub fn with_callback(callback: F) -> Self {
25         TyBuilder { callback: callback }
26     }
27 
build(self, ty: Ty) -> F::Result28     pub fn build(self, ty: Ty) -> F::Result {
29         self.callback.invoke(ty)
30     }
31 
id<I>(self, id: I) -> F::Result where I: ToIdent32     pub fn id<I>(self, id: I) -> F::Result
33         where I: ToIdent
34     {
35         self.path().id(id).build()
36     }
37 
build_path(self, path: Path) -> F::Result38     pub fn build_path(self, path: Path) -> F::Result {
39         self.build(Ty::Path(None, path))
40     }
41 
build_qpath(self, qself: QSelf, path: Path) -> F::Result42     pub fn build_qpath(self, qself: QSelf, path: Path) -> F::Result {
43         self.build(Ty::Path(Some(qself), path))
44     }
45 
path(self) -> PathBuilder<TyPathBuilder<F>>46     pub fn path(self) -> PathBuilder<TyPathBuilder<F>> {
47         PathBuilder::with_callback(TyPathBuilder(self))
48     }
49 
qpath(self) -> QPathBuilder<TyQPathBuilder<F>>50     pub fn qpath(self) -> QPathBuilder<TyQPathBuilder<F>> {
51         QPathBuilder::with_callback(TyQPathBuilder(self))
52     }
53 
isize(self) -> F::Result54     pub fn isize(self) -> F::Result {
55         self.id("isize")
56     }
57 
i8(self) -> F::Result58     pub fn i8(self) -> F::Result {
59         self.id("i8")
60     }
61 
i16(self) -> F::Result62     pub fn i16(self) -> F::Result {
63         self.id("i16")
64     }
65 
i32(self) -> F::Result66     pub fn i32(self) -> F::Result {
67         self.id("i32")
68     }
69 
i64(self) -> F::Result70     pub fn i64(self) -> F::Result {
71         self.id("i64")
72     }
73 
usize(self) -> F::Result74     pub fn usize(self) -> F::Result {
75         self.id("usize")
76     }
77 
u8(self) -> F::Result78     pub fn u8(self) -> F::Result {
79         self.id("u8")
80     }
81 
u16(self) -> F::Result82     pub fn u16(self) -> F::Result {
83         self.id("u16")
84     }
85 
u32(self) -> F::Result86     pub fn u32(self) -> F::Result {
87         self.id("u32")
88     }
89 
u64(self) -> F::Result90     pub fn u64(self) -> F::Result {
91         self.id("u64")
92     }
93 
f32(self) -> F::Result94     pub fn f32(self) -> F::Result {
95         self.id("f32")
96     }
97 
f64(self) -> F::Result98     pub fn f64(self) -> F::Result {
99         self.id("f64")
100     }
101 
bool(self) -> F::Result102     pub fn bool(self) -> F::Result {
103         self.id("bool")
104     }
105 
unit(self) -> F::Result106     pub fn unit(self) -> F::Result {
107         self.tuple().build()
108     }
109 
tuple(self) -> TyTupleBuilder<F>110     pub fn tuple(self) -> TyTupleBuilder<F> {
111         TyTupleBuilder {
112             builder: self,
113             tys: vec![],
114         }
115     }
116 
build_slice(self, ty: Ty) -> F::Result117     pub fn build_slice(self, ty: Ty) -> F::Result {
118         self.build(Ty::Slice(Box::new(ty)))
119     }
120 
slice(self) -> TyBuilder<TySliceBuilder<F>>121     pub fn slice(self) -> TyBuilder<TySliceBuilder<F>> {
122         TyBuilder::with_callback(TySliceBuilder(self))
123     }
124 
ref_(self) -> TyRefBuilder<F>125     pub fn ref_(self) -> TyRefBuilder<F> {
126         TyRefBuilder {
127             builder: self,
128             lifetime: None,
129             mutability: Mutability::Immutable,
130         }
131     }
132 
never(self) -> F::Result133     pub fn never(self) -> F::Result {
134         self.build(Ty::Never)
135     }
136 
infer(self) -> F::Result137     pub fn infer(self) -> F::Result {
138         self.build(Ty::Infer)
139     }
140 
option(self) -> TyBuilder<TyOptionBuilder<F>>141     pub fn option(self) -> TyBuilder<TyOptionBuilder<F>> {
142         TyBuilder::with_callback(TyOptionBuilder(self))
143     }
144 
result(self) -> TyBuilder<TyResultOkBuilder<F>>145     pub fn result(self) -> TyBuilder<TyResultOkBuilder<F>> {
146         TyBuilder::with_callback(TyResultOkBuilder(self))
147     }
148 
phantom_data(self) -> TyBuilder<TyPhantomDataBuilder<F>>149     pub fn phantom_data(self) -> TyBuilder<TyPhantomDataBuilder<F>> {
150         TyBuilder::with_callback(TyPhantomDataBuilder(self))
151     }
152 
box_(self) -> TyBuilder<TyBoxBuilder<F>>153     pub fn box_(self) -> TyBuilder<TyBoxBuilder<F>> {
154         TyBuilder::with_callback(TyBoxBuilder(self))
155     }
156 
iterator(self) -> TyBuilder<TyIteratorBuilder<F>>157     pub fn iterator(self) -> TyBuilder<TyIteratorBuilder<F>> {
158         TyBuilder::with_callback(TyIteratorBuilder(self))
159     }
160 
impl_trait(self) -> TyImplTraitTyBuilder<F>161     pub fn impl_trait(self) -> TyImplTraitTyBuilder<F> {
162         TyImplTraitTyBuilder {
163             builder: self,
164             bounds: Vec::new(),
165         }
166     }
167 }
168 
169 // ////////////////////////////////////////////////////////////////////////////
170 
171 pub struct TyPathBuilder<F>(TyBuilder<F>);
172 
173 impl<F> Invoke<Path> for TyPathBuilder<F>
174     where F: Invoke<Ty>
175 {
176     type Result = F::Result;
177 
invoke(self, path: Path) -> F::Result178     fn invoke(self, path: Path) -> F::Result {
179         self.0.build_path(path)
180     }
181 }
182 
183 // ////////////////////////////////////////////////////////////////////////////
184 
185 pub struct TyQPathBuilder<F>(TyBuilder<F>);
186 
187 impl<F> Invoke<(QSelf, Path)> for TyQPathBuilder<F>
188     where F: Invoke<Ty>
189 {
190     type Result = F::Result;
191 
invoke(self, (qself, path): (QSelf, Path)) -> F::Result192     fn invoke(self, (qself, path): (QSelf, Path)) -> F::Result {
193         self.0.build_qpath(qself, path)
194     }
195 }
196 
197 // ////////////////////////////////////////////////////////////////////////////
198 
199 pub struct TySliceBuilder<F>(TyBuilder<F>);
200 
201 impl<F> Invoke<Ty> for TySliceBuilder<F>
202     where F: Invoke<Ty>
203 {
204     type Result = F::Result;
205 
invoke(self, ty: Ty) -> F::Result206     fn invoke(self, ty: Ty) -> F::Result {
207         self.0.build_slice(ty)
208     }
209 }
210 
211 // ////////////////////////////////////////////////////////////////////////////
212 
213 pub struct TyRefBuilder<F> {
214     builder: TyBuilder<F>,
215     lifetime: Option<Lifetime>,
216     mutability: Mutability,
217 }
218 
219 impl<F> TyRefBuilder<F>
220     where F: Invoke<Ty>
221 {
mut_(mut self) -> Self222     pub fn mut_(mut self) -> Self {
223         self.mutability = Mutability::Mutable;
224         self
225     }
226 
lifetime<N>(mut self, name: N) -> Self where N: ToIdent227     pub fn lifetime<N>(mut self, name: N) -> Self
228         where N: ToIdent
229     {
230         self.lifetime = Some(Lifetime { ident: name.to_ident() });
231         self
232     }
233 
build_ty(self, ty: Ty) -> F::Result234     pub fn build_ty(self, ty: Ty) -> F::Result {
235         let ty = MutTy {
236             ty: ty,
237             mutability: self.mutability,
238         };
239         self.builder.build(Ty::Rptr(self.lifetime, Box::new(ty)))
240     }
241 
ty(self) -> TyBuilder<Self>242     pub fn ty(self) -> TyBuilder<Self> {
243         TyBuilder::with_callback(self)
244     }
245 }
246 
247 impl<F> Invoke<Ty> for TyRefBuilder<F>
248     where F: Invoke<Ty>
249 {
250     type Result = F::Result;
251 
invoke(self, ty: Ty) -> F::Result252     fn invoke(self, ty: Ty) -> F::Result {
253         self.build_ty(ty)
254     }
255 }
256 
257 // ////////////////////////////////////////////////////////////////////////////
258 
259 pub struct TyOptionBuilder<F>(TyBuilder<F>);
260 
261 impl<F> Invoke<Ty> for TyOptionBuilder<F>
262     where F: Invoke<Ty>
263 {
264     type Result = F::Result;
265 
invoke(self, ty: Ty) -> F::Result266     fn invoke(self, ty: Ty) -> F::Result {
267         let path = PathBuilder::new()
268             .global()
269             .id("std")
270             .id("option")
271             .segment("Option")
272             .with_ty(ty)
273             .build()
274             .build();
275 
276         self.0.build_path(path)
277     }
278 }
279 
280 // ////////////////////////////////////////////////////////////////////////////
281 
282 pub struct TyResultOkBuilder<F>(TyBuilder<F>);
283 
284 impl<F> Invoke<Ty> for TyResultOkBuilder<F>
285     where F: Invoke<Ty>
286 {
287     type Result = TyBuilder<TyResultErrBuilder<F>>;
288 
invoke(self, ty: Ty) -> TyBuilder<TyResultErrBuilder<F>>289     fn invoke(self, ty: Ty) -> TyBuilder<TyResultErrBuilder<F>> {
290         TyBuilder::with_callback(TyResultErrBuilder(self.0, ty))
291     }
292 }
293 
294 pub struct TyResultErrBuilder<F>(TyBuilder<F>, Ty);
295 
296 impl<F> Invoke<Ty> for TyResultErrBuilder<F>
297     where F: Invoke<Ty>
298 {
299     type Result = F::Result;
300 
invoke(self, ty: Ty) -> F::Result301     fn invoke(self, ty: Ty) -> F::Result {
302         let path = PathBuilder::new()
303             .global()
304             .id("std")
305             .id("result")
306             .segment("Result")
307             .with_ty(self.1)
308             .with_ty(ty)
309             .build()
310             .build();
311 
312         self.0.build_path(path)
313     }
314 }
315 
316 // ////////////////////////////////////////////////////////////////////////////
317 
318 pub struct TyPhantomDataBuilder<F>(TyBuilder<F>);
319 
320 impl<F> Invoke<Ty> for TyPhantomDataBuilder<F>
321     where F: Invoke<Ty>
322 {
323     type Result = F::Result;
324 
invoke(self, ty: Ty) -> F::Result325     fn invoke(self, ty: Ty) -> F::Result {
326         let path = PathBuilder::new()
327             .global()
328             .id("std")
329             .id("marker")
330             .segment("PhantomData")
331             .with_ty(ty)
332             .build()
333             .build();
334 
335         self.0.build_path(path)
336     }
337 }
338 
339 // ////////////////////////////////////////////////////////////////////////////
340 
341 pub struct TyBoxBuilder<F>(TyBuilder<F>);
342 
343 impl<F> Invoke<Ty> for TyBoxBuilder<F>
344     where F: Invoke<Ty>
345 {
346     type Result = F::Result;
347 
invoke(self, ty: Ty) -> F::Result348     fn invoke(self, ty: Ty) -> F::Result {
349         let path = PathBuilder::new()
350             .global()
351             .id("std")
352             .id("boxed")
353             .segment("Box")
354             .with_ty(ty)
355             .build()
356             .build();
357 
358         self.0.build_path(path)
359     }
360 }
361 
362 // ////////////////////////////////////////////////////////////////////////////
363 
364 pub struct TyIteratorBuilder<F>(TyBuilder<F>);
365 
366 impl<F> Invoke<Ty> for TyIteratorBuilder<F>
367     where F: Invoke<Ty>
368 {
369     type Result = F::Result;
370 
invoke(self, ty: Ty) -> F::Result371     fn invoke(self, ty: Ty) -> F::Result {
372         let path = PathBuilder::new()
373             .global()
374             .id("std")
375             .id("iter")
376             .segment("Iterator")
377             .binding("Item")
378             .build(ty.clone())
379             .build()
380             .build();
381 
382         self.0.build_path(path)
383     }
384 }
385 
386 // ////////////////////////////////////////////////////////////////////////////
387 
388 pub struct TyImplTraitTyBuilder<F> {
389     builder: TyBuilder<F>,
390     bounds: Vec<TyParamBound>,
391 }
392 
393 impl<F> TyImplTraitTyBuilder<F>
394     where F: Invoke<Ty>
395 {
with_bounds<I>(mut self, iter: I) -> Self where I: Iterator<Item = TyParamBound>396     pub fn with_bounds<I>(mut self, iter: I) -> Self
397         where I: Iterator<Item = TyParamBound>
398     {
399         self.bounds.extend(iter);
400         self
401     }
402 
with_bound(mut self, bound: TyParamBound) -> Self403     pub fn with_bound(mut self, bound: TyParamBound) -> Self {
404         self.bounds.push(bound);
405         self
406     }
407 
bound(self) -> TyParamBoundBuilder<Self>408     pub fn bound(self) -> TyParamBoundBuilder<Self> {
409         TyParamBoundBuilder::with_callback(self)
410     }
411 
with_generics(self, generics: Generics) -> Self412     pub fn with_generics(self, generics: Generics) -> Self {
413         self.with_lifetimes(generics.lifetimes.into_iter().map(|def| def.lifetime))
414     }
415 
with_lifetimes<I, L>(mut self, lifetimes: I) -> Self where I: Iterator<Item = L>, L: IntoLifetime416     pub fn with_lifetimes<I, L>(mut self, lifetimes: I) -> Self
417         where I: Iterator<Item = L>,
418               L: IntoLifetime
419     {
420         for lifetime in lifetimes {
421             self = self.lifetime(lifetime);
422         }
423 
424         self
425     }
426 
lifetime<L>(self, lifetime: L) -> Self where L: IntoLifetime427     pub fn lifetime<L>(self, lifetime: L) -> Self
428         where L: IntoLifetime
429     {
430         self.bound().lifetime(lifetime)
431     }
432 
build(self) -> F::Result433     pub fn build(self) -> F::Result {
434         let bounds = self.bounds;
435         self.builder.build(Ty::ImplTrait(bounds))
436     }
437 }
438 
439 impl<F> Invoke<TyParamBound> for TyImplTraitTyBuilder<F>
440     where F: Invoke<Ty>
441 {
442     type Result = Self;
443 
invoke(self, bound: TyParamBound) -> Self444     fn invoke(self, bound: TyParamBound) -> Self {
445         self.with_bound(bound)
446     }
447 }
448 
449 // ////////////////////////////////////////////////////////////////////////////
450 
451 pub struct TyTupleBuilder<F> {
452     builder: TyBuilder<F>,
453     tys: Vec<Ty>,
454 }
455 
456 impl<F> TyTupleBuilder<F>
457     where F: Invoke<Ty>
458 {
with_tys<I>(mut self, iter: I) -> Self where I: IntoIterator<Item = Ty>459     pub fn with_tys<I>(mut self, iter: I) -> Self
460         where I: IntoIterator<Item = Ty>
461     {
462         self.tys.extend(iter);
463         self
464     }
465 
with_ty(mut self, ty: Ty) -> Self466     pub fn with_ty(mut self, ty: Ty) -> Self {
467         self.tys.push(ty);
468         self
469     }
470 
ty(self) -> TyBuilder<Self>471     pub fn ty(self) -> TyBuilder<Self> {
472         TyBuilder::with_callback(self)
473     }
474 
build(self) -> F::Result475     pub fn build(self) -> F::Result {
476         self.builder.build(Ty::Tup(self.tys))
477     }
478 }
479 
480 impl<F> Invoke<Ty> for TyTupleBuilder<F>
481     where F: Invoke<Ty>
482 {
483     type Result = Self;
484 
invoke(self, ty: Ty) -> Self485     fn invoke(self, ty: Ty) -> Self {
486         self.with_ty(ty)
487     }
488 }
489