Coverage Report

Created: 2024-10-16 07:58

/rust/registry/src/index.crates.io-6f17d22bba15001f/wast-64.0.0/src/component/expand.rs
Line
Count
Source (jump to first uncovered line)
1
use crate::component::*;
2
use crate::core;
3
use crate::gensym;
4
use crate::kw;
5
use crate::token::Id;
6
use crate::token::{Index, Span};
7
use std::collections::HashMap;
8
use std::mem;
9
10
/// Performs an AST "expansion" pass over the component fields provided.
11
///
12
/// This expansion is intended to desugar the AST from various parsed constructs
13
/// to bits and bobs amenable for name resolution as well as binary encoding.
14
/// For example `(import "i" (func))` is split into a type definition followed by
15
/// the import referencing that type definition.
16
///
17
/// Most forms of AST expansion happen in this file and afterwards the AST will
18
/// be handed to the name resolution pass which will convert `Index::Id` to
19
/// `Index::Num` wherever it's found.
20
0
pub fn expand(fields: &mut Vec<ComponentField<'_>>) {
21
0
    Expander::default().expand_component_fields(fields)
22
0
}
23
24
enum AnyType<'a> {
25
    Core(CoreType<'a>),
26
    Component(Type<'a>),
27
}
28
29
impl<'a> From<AnyType<'a>> for ComponentTypeDecl<'a> {
30
0
    fn from(t: AnyType<'a>) -> Self {
31
0
        match t {
32
0
            AnyType::Core(t) => Self::CoreType(t),
33
0
            AnyType::Component(t) => Self::Type(t),
34
        }
35
0
    }
36
}
37
38
impl<'a> From<AnyType<'a>> for InstanceTypeDecl<'a> {
39
0
    fn from(t: AnyType<'a>) -> Self {
40
0
        match t {
41
0
            AnyType::Core(t) => Self::CoreType(t),
42
0
            AnyType::Component(t) => Self::Type(t),
43
        }
44
0
    }
45
}
46
47
impl<'a> From<AnyType<'a>> for ComponentField<'a> {
48
0
    fn from(t: AnyType<'a>) -> Self {
49
0
        match t {
50
0
            AnyType::Core(t) => Self::CoreType(t),
51
0
            AnyType::Component(t) => Self::Type(t),
52
        }
53
0
    }
54
}
55
56
#[derive(Default)]
57
struct Expander<'a> {
58
    /// Fields, during processing, which should be prepended to the
59
    /// currently-being-processed field. This should always be empty after
60
    /// processing is complete.
61
    types_to_prepend: Vec<AnyType<'a>>,
62
    component_fields_to_prepend: Vec<ComponentField<'a>>,
63
64
    /// Fields that are appended to the end of the module once everything has
65
    /// finished.
66
    component_fields_to_append: Vec<ComponentField<'a>>,
67
}
68
69
impl<'a> Expander<'a> {
70
0
    fn expand_component_fields(&mut self, fields: &mut Vec<ComponentField<'a>>) {
71
0
        let mut cur = 0;
72
0
        while cur < fields.len() {
73
0
            self.expand_field(&mut fields[cur]);
74
0
            let amt = self.types_to_prepend.len() + self.component_fields_to_prepend.len();
75
0
            fields.splice(cur..cur, self.component_fields_to_prepend.drain(..));
76
0
            fields.splice(cur..cur, self.types_to_prepend.drain(..).map(Into::into));
77
0
            cur += 1 + amt;
78
0
        }
79
0
        fields.append(&mut self.component_fields_to_append);
80
0
    }
81
82
0
    fn expand_decls<T>(&mut self, decls: &mut Vec<T>, expand: fn(&mut Self, &mut T))
83
0
    where
84
0
        T: From<AnyType<'a>>,
85
0
    {
86
0
        let mut cur = 0;
87
0
        while cur < decls.len() {
88
0
            expand(self, &mut decls[cur]);
89
0
            assert!(self.component_fields_to_prepend.is_empty());
90
0
            assert!(self.component_fields_to_append.is_empty());
91
0
            let amt = self.types_to_prepend.len();
92
0
            decls.splice(cur..cur, self.types_to_prepend.drain(..).map(From::from));
93
0
            cur += 1 + amt;
94
        }
95
0
    }
Unexecuted instantiation: <wast::component::expand::Expander>::expand_decls::<wast::component::types::InstanceTypeDecl>
Unexecuted instantiation: <wast::component::expand::Expander>::expand_decls::<wast::component::types::ComponentTypeDecl>
96
97
0
    fn expand_field(&mut self, item: &mut ComponentField<'a>) {
98
0
        let expanded = match item {
99
0
            ComponentField::CoreModule(m) => self.expand_core_module(m),
100
0
            ComponentField::CoreInstance(i) => {
101
0
                self.expand_core_instance(i);
102
0
                None
103
            }
104
0
            ComponentField::CoreType(t) => {
105
0
                self.expand_core_type(t);
106
0
                None
107
            }
108
0
            ComponentField::Component(c) => self.expand_nested_component(c),
109
0
            ComponentField::Instance(i) => self.expand_instance(i),
110
0
            ComponentField::Type(t) => {
111
0
                self.expand_type(t);
112
0
                None
113
            }
114
0
            ComponentField::CanonicalFunc(f) => {
115
0
                self.expand_canonical_func(f);
116
0
                None
117
            }
118
0
            ComponentField::CoreFunc(f) => self.expand_core_func(f),
119
0
            ComponentField::Func(f) => self.expand_func(f),
120
0
            ComponentField::Import(i) => {
121
0
                self.expand_item_sig(&mut i.item);
122
0
                None
123
            }
124
0
            ComponentField::Export(e) => {
125
0
                if let Some(sig) = &mut e.ty {
126
0
                    self.expand_item_sig(&mut sig.0);
127
0
                }
128
0
                None
129
            }
130
            ComponentField::Start(_)
131
            | ComponentField::Alias(_)
132
            | ComponentField::Custom(_)
133
0
            | ComponentField::Producers(_) => None,
134
        };
135
136
0
        if let Some(expanded) = expanded {
137
0
            *item = expanded;
138
0
        }
139
0
    }
140
141
0
    fn expand_core_module(&mut self, module: &mut CoreModule<'a>) -> Option<ComponentField<'a>> {
142
0
        for name in module.exports.names.drain(..) {
143
0
            let id = gensym::fill(module.span, &mut module.id);
144
0
            self.component_fields_to_append
145
0
                .push(ComponentField::Export(ComponentExport {
146
0
                    span: module.span,
147
0
                    id: None,
148
0
                    debug_name: None,
149
0
                    name,
150
0
                    kind: ComponentExportKind::module(module.span, id),
151
0
                    ty: None,
152
0
                }));
153
0
        }
154
0
        match &mut module.kind {
155
            // inline modules are expanded later during resolution
156
0
            CoreModuleKind::Inline { .. } => None,
157
0
            CoreModuleKind::Import { import, ty } => {
158
0
                let idx = self.expand_core_type_use(ty);
159
0
                Some(ComponentField::Import(ComponentImport {
160
0
                    span: module.span,
161
0
                    name: import.name,
162
0
                    item: ItemSig {
163
0
                        span: module.span,
164
0
                        id: module.id,
165
0
                        name: None,
166
0
                        kind: ItemSigKind::CoreModule(CoreTypeUse::Ref(idx)),
167
0
                    },
168
0
                }))
169
            }
170
        }
171
0
    }
172
173
0
    fn expand_core_instance(&mut self, instance: &mut CoreInstance<'a>) {
174
0
        match &mut instance.kind {
175
0
            CoreInstanceKind::Instantiate { args, .. } => {
176
0
                for arg in args {
177
0
                    self.expand_core_instantiation_arg(&mut arg.kind);
178
0
                }
179
            }
180
0
            CoreInstanceKind::BundleOfExports { .. } => {}
181
        }
182
0
    }
183
184
0
    fn expand_nested_component(
185
0
        &mut self,
186
0
        component: &mut NestedComponent<'a>,
187
0
    ) -> Option<ComponentField<'a>> {
188
0
        for name in component.exports.names.drain(..) {
189
0
            let id = gensym::fill(component.span, &mut component.id);
190
0
            self.component_fields_to_append
191
0
                .push(ComponentField::Export(ComponentExport {
192
0
                    span: component.span,
193
0
                    id: None,
194
0
                    debug_name: None,
195
0
                    name,
196
0
                    kind: ComponentExportKind::component(component.span, id),
197
0
                    ty: None,
198
0
                }));
199
0
        }
200
0
        match &mut component.kind {
201
0
            NestedComponentKind::Inline(fields) => {
202
0
                expand(fields);
203
0
                None
204
            }
205
0
            NestedComponentKind::Import { import, ty } => {
206
0
                let idx = self.expand_component_type_use(ty);
207
0
                Some(ComponentField::Import(ComponentImport {
208
0
                    span: component.span,
209
0
                    name: import.name,
210
0
                    item: ItemSig {
211
0
                        span: component.span,
212
0
                        id: component.id,
213
0
                        name: None,
214
0
                        kind: ItemSigKind::Component(ComponentTypeUse::Ref(idx)),
215
0
                    },
216
0
                }))
217
            }
218
        }
219
0
    }
220
221
0
    fn expand_instance(&mut self, instance: &mut Instance<'a>) -> Option<ComponentField<'a>> {
222
0
        for name in instance.exports.names.drain(..) {
223
0
            let id = gensym::fill(instance.span, &mut instance.id);
224
0
            self.component_fields_to_append
225
0
                .push(ComponentField::Export(ComponentExport {
226
0
                    span: instance.span,
227
0
                    id: None,
228
0
                    debug_name: None,
229
0
                    name,
230
0
                    kind: ComponentExportKind::instance(instance.span, id),
231
0
                    ty: None,
232
0
                }));
233
0
        }
234
0
        match &mut instance.kind {
235
0
            InstanceKind::Import { import, ty } => {
236
0
                let idx = self.expand_component_type_use(ty);
237
0
                Some(ComponentField::Import(ComponentImport {
238
0
                    span: instance.span,
239
0
                    name: import.name,
240
0
                    item: ItemSig {
241
0
                        span: instance.span,
242
0
                        id: instance.id,
243
0
                        name: None,
244
0
                        kind: ItemSigKind::Instance(ComponentTypeUse::Ref(idx)),
245
0
                    },
246
0
                }))
247
            }
248
0
            InstanceKind::Instantiate { args, .. } => {
249
0
                for arg in args {
250
0
                    self.expand_instantiation_arg(&mut arg.kind);
251
0
                }
252
0
                None
253
            }
254
0
            InstanceKind::BundleOfExports { .. } => None,
255
        }
256
0
    }
257
258
0
    fn expand_canonical_func(&mut self, func: &mut CanonicalFunc<'a>) {
259
0
        match &mut func.kind {
260
0
            CanonicalFuncKind::Lift { ty, .. } => {
261
0
                self.expand_component_type_use(ty);
262
0
            }
263
            CanonicalFuncKind::Lower(_)
264
            | CanonicalFuncKind::ResourceNew(_)
265
            | CanonicalFuncKind::ResourceRep(_)
266
0
            | CanonicalFuncKind::ResourceDrop(_) => {}
267
        }
268
0
    }
269
270
0
    fn expand_core_func(&mut self, func: &mut CoreFunc<'a>) -> Option<ComponentField<'a>> {
271
0
        match &mut func.kind {
272
0
            CoreFuncKind::Alias(a) => Some(ComponentField::Alias(Alias {
273
0
                span: func.span,
274
0
                id: func.id,
275
0
                name: func.name,
276
0
                target: AliasTarget::CoreExport {
277
0
                    instance: a.instance,
278
0
                    name: a.name,
279
0
                    kind: core::ExportKind::Func,
280
0
                },
281
0
            })),
282
0
            CoreFuncKind::Lower(info) => Some(ComponentField::CanonicalFunc(CanonicalFunc {
283
0
                span: func.span,
284
0
                id: func.id,
285
0
                name: func.name,
286
0
                kind: CanonicalFuncKind::Lower(mem::take(info)),
287
0
            })),
288
0
            CoreFuncKind::ResourceNew(info) => Some(ComponentField::CanonicalFunc(CanonicalFunc {
289
0
                span: func.span,
290
0
                id: func.id,
291
0
                name: func.name,
292
0
                kind: CanonicalFuncKind::ResourceNew(mem::take(info)),
293
0
            })),
294
0
            CoreFuncKind::ResourceDrop(info) => {
295
0
                Some(ComponentField::CanonicalFunc(CanonicalFunc {
296
0
                    span: func.span,
297
0
                    id: func.id,
298
0
                    name: func.name,
299
0
                    kind: CanonicalFuncKind::ResourceDrop(mem::take(info)),
300
0
                }))
301
            }
302
0
            CoreFuncKind::ResourceRep(info) => Some(ComponentField::CanonicalFunc(CanonicalFunc {
303
0
                span: func.span,
304
0
                id: func.id,
305
0
                name: func.name,
306
0
                kind: CanonicalFuncKind::ResourceRep(mem::take(info)),
307
0
            })),
308
        }
309
0
    }
310
311
0
    fn expand_func(&mut self, func: &mut Func<'a>) -> Option<ComponentField<'a>> {
312
0
        for name in func.exports.names.drain(..) {
313
0
            let id = gensym::fill(func.span, &mut func.id);
314
0
            self.component_fields_to_append
315
0
                .push(ComponentField::Export(ComponentExport {
316
0
                    span: func.span,
317
0
                    id: None,
318
0
                    debug_name: None,
319
0
                    name,
320
0
                    kind: ComponentExportKind::func(func.span, id),
321
0
                    ty: None,
322
0
                }));
323
0
        }
324
0
        match &mut func.kind {
325
0
            FuncKind::Import { import, ty } => {
326
0
                let idx = self.expand_component_type_use(ty);
327
0
                Some(ComponentField::Import(ComponentImport {
328
0
                    span: func.span,
329
0
                    name: import.name,
330
0
                    item: ItemSig {
331
0
                        span: func.span,
332
0
                        id: func.id,
333
0
                        name: None,
334
0
                        kind: ItemSigKind::Func(ComponentTypeUse::Ref(idx)),
335
0
                    },
336
0
                }))
337
            }
338
0
            FuncKind::Lift { ty, info } => {
339
0
                let idx = self.expand_component_type_use(ty);
340
0
                Some(ComponentField::CanonicalFunc(CanonicalFunc {
341
0
                    span: func.span,
342
0
                    id: func.id,
343
0
                    name: func.name,
344
0
                    kind: CanonicalFuncKind::Lift {
345
0
                        ty: ComponentTypeUse::Ref(idx),
346
0
                        info: mem::take(info),
347
0
                    },
348
0
                }))
349
            }
350
0
            FuncKind::Alias(a) => Some(ComponentField::Alias(Alias {
351
0
                span: func.span,
352
0
                id: func.id,
353
0
                name: func.name,
354
0
                target: AliasTarget::Export {
355
0
                    instance: a.instance,
356
0
                    name: a.name,
357
0
                    kind: ComponentExportAliasKind::Func,
358
0
                },
359
0
            })),
360
        }
361
0
    }
362
363
0
    fn expand_core_type(&mut self, field: &mut CoreType<'a>) {
364
0
        match &mut field.def {
365
0
            CoreTypeDef::Def(_) => {}
366
0
            CoreTypeDef::Module(m) => self.expand_module_ty(m),
367
        }
368
369
0
        let id = gensym::fill(field.span, &mut field.id);
370
0
        let index = Index::Id(id);
371
0
        match &field.def {
372
0
            CoreTypeDef::Def(_) => {}
373
0
            CoreTypeDef::Module(t) => t.key().insert(self, index),
374
        }
375
0
    }
376
377
0
    fn expand_type(&mut self, field: &mut Type<'a>) {
378
0
        match &mut field.def {
379
0
            TypeDef::Defined(d) => self.expand_defined_ty(d),
380
0
            TypeDef::Func(f) => self.expand_func_ty(f),
381
0
            TypeDef::Component(c) => self.expand_component_ty(c),
382
0
            TypeDef::Instance(i) => self.expand_instance_ty(i),
383
0
            TypeDef::Resource(_) => {}
384
        }
385
386
0
        let id = gensym::fill(field.span, &mut field.id);
387
0
        let index = Index::Id(id);
388
0
        match &field.def {
389
0
            TypeDef::Defined(t) => t.key().insert(self, index),
390
0
            TypeDef::Func(t) => t.key().insert(self, index),
391
0
            TypeDef::Component(t) => t.key().insert(self, index),
392
0
            TypeDef::Instance(t) => t.key().insert(self, index),
393
0
            TypeDef::Resource(_) => {}
394
        }
395
0
        for name in field.exports.names.drain(..) {
396
0
            self.component_fields_to_append
397
0
                .push(ComponentField::Export(ComponentExport {
398
0
                    span: field.span,
399
0
                    id: None,
400
0
                    debug_name: None,
401
0
                    name,
402
0
                    kind: ComponentExportKind::ty(field.span, id),
403
0
                    ty: None,
404
0
                }));
405
0
        }
406
0
    }
407
408
0
    fn expand_func_ty(&mut self, ty: &mut ComponentFunctionType<'a>) {
409
0
        for param in ty.params.iter_mut() {
410
0
            self.expand_component_val_ty(&mut param.ty);
411
0
        }
412
413
0
        for result in ty.results.iter_mut() {
414
0
            self.expand_component_val_ty(&mut result.ty);
415
0
        }
416
0
    }
417
418
0
    fn expand_module_ty(&mut self, ty: &mut ModuleType<'a>) {
419
0
        use crate::core::resolve::types::{FuncKey, TypeKey, TypeReference};
420
0
421
0
        // Note that this is a custom implementation from everything else in
422
0
        // this file since this is using core wasm types instead of component
423
0
        // types, so a small part of the core wasm expansion process is
424
0
        // inlined here to handle the `TypeUse` from core wasm.
425
0
426
0
        let mut func_type_to_idx = HashMap::new();
427
0
        let mut to_prepend = Vec::new();
428
0
        let mut i = 0;
429
0
        while i < ty.decls.len() {
430
0
            match &mut ty.decls[i] {
431
0
                ModuleTypeDecl::Type(ty) => match &ty.def {
432
0
                    core::TypeDef::Func(f) => {
433
0
                        let id = gensym::fill(ty.span, &mut ty.id);
434
0
                        func_type_to_idx.insert(f.key(), Index::Id(id));
435
0
                    }
436
0
                    core::TypeDef::Struct(_) => {}
437
0
                    core::TypeDef::Array(_) => {}
438
                },
439
0
                ModuleTypeDecl::Alias(_) => {}
440
0
                ModuleTypeDecl::Import(ty) => {
441
0
                    expand_sig(&mut ty.item, &mut to_prepend, &mut func_type_to_idx);
442
0
                }
443
0
                ModuleTypeDecl::Export(_, item) => {
444
0
                    expand_sig(item, &mut to_prepend, &mut func_type_to_idx);
445
0
                }
446
            }
447
0
            ty.decls.splice(i..i, to_prepend.drain(..));
448
0
            i += 1;
449
        }
450
451
0
        fn expand_sig<'a>(
452
0
            item: &mut core::ItemSig<'a>,
453
0
            to_prepend: &mut Vec<ModuleTypeDecl<'a>>,
454
0
            func_type_to_idx: &mut HashMap<FuncKey<'a>, Index<'a>>,
455
0
        ) {
456
0
            match &mut item.kind {
457
0
                core::ItemKind::Func(t) | core::ItemKind::Tag(core::TagType::Exception(t)) => {
458
                    // If the index is already filled in then this is skipped
459
0
                    if t.index.is_some() {
460
0
                        return;
461
0
                    }
462
0
463
0
                    // Otherwise the inline type information is used to
464
0
                    // generate a type into this module if necessary. If the
465
0
                    // function type already exists we reuse the same key,
466
0
                    // otherwise a fresh type definition is created and we use
467
0
                    // that one instead.
468
0
                    let ty = t.inline.take().unwrap_or_default();
469
0
                    let key = ty.key();
470
0
                    if let Some(idx) = func_type_to_idx.get(&key) {
471
0
                        t.index = Some(*idx);
472
0
                        return;
473
0
                    }
474
0
                    let id = gensym::gen(item.span);
475
0
                    to_prepend.push(ModuleTypeDecl::Type(core::Type {
476
0
                        span: item.span,
477
0
                        id: Some(id),
478
0
                        name: None,
479
0
                        def: key.to_def(item.span),
480
0
                        parent: None,
481
0
                        final_type: None,
482
0
                    }));
483
0
                    let idx = Index::Id(id);
484
0
                    t.index = Some(idx);
485
                }
486
                core::ItemKind::Global(_)
487
                | core::ItemKind::Table(_)
488
0
                | core::ItemKind::Memory(_) => {}
489
            }
490
0
        }
491
0
    }
492
493
0
    fn expand_component_ty(&mut self, ty: &mut ComponentType<'a>) {
494
0
        Expander::default().expand_decls(&mut ty.decls, |e, decl| match decl {
495
0
            ComponentTypeDecl::CoreType(t) => e.expand_core_type(t),
496
0
            ComponentTypeDecl::Type(t) => e.expand_type(t),
497
0
            ComponentTypeDecl::Alias(_) => {}
498
0
            ComponentTypeDecl::Export(t) => e.expand_item_sig(&mut t.item),
499
0
            ComponentTypeDecl::Import(t) => e.expand_item_sig(&mut t.item),
500
0
        })
501
0
    }
502
503
0
    fn expand_instance_ty(&mut self, ty: &mut InstanceType<'a>) {
504
0
        Expander::default().expand_decls(&mut ty.decls, |e, decl| match decl {
505
0
            InstanceTypeDecl::CoreType(t) => e.expand_core_type(t),
506
0
            InstanceTypeDecl::Type(t) => e.expand_type(t),
507
0
            InstanceTypeDecl::Alias(_) => {}
508
0
            InstanceTypeDecl::Export(t) => e.expand_item_sig(&mut t.item),
509
0
        })
510
0
    }
511
512
0
    fn expand_item_sig(&mut self, ext: &mut ItemSig<'a>) {
513
0
        match &mut ext.kind {
514
0
            ItemSigKind::CoreModule(t) => {
515
0
                self.expand_core_type_use(t);
516
0
            }
517
0
            ItemSigKind::Func(t) => {
518
0
                self.expand_component_type_use(t);
519
0
            }
520
0
            ItemSigKind::Component(t) => {
521
0
                self.expand_component_type_use(t);
522
0
            }
523
0
            ItemSigKind::Instance(t) => {
524
0
                self.expand_component_type_use(t);
525
0
            }
526
0
            ItemSigKind::Value(t) => {
527
0
                self.expand_component_val_ty(&mut t.0);
528
0
            }
529
0
            ItemSigKind::Type(_) => {}
530
        }
531
0
    }
532
533
0
    fn expand_defined_ty(&mut self, ty: &mut ComponentDefinedType<'a>) {
534
0
        match ty {
535
            ComponentDefinedType::Primitive(_)
536
            | ComponentDefinedType::Flags(_)
537
0
            | ComponentDefinedType::Enum(_) => {}
538
0
            ComponentDefinedType::Record(r) => {
539
0
                for field in r.fields.iter_mut() {
540
0
                    self.expand_component_val_ty(&mut field.ty);
541
0
                }
542
            }
543
0
            ComponentDefinedType::Variant(v) => {
544
0
                for case in v.cases.iter_mut() {
545
0
                    if let Some(ty) = &mut case.ty {
546
0
                        self.expand_component_val_ty(ty);
547
0
                    }
548
                }
549
            }
550
0
            ComponentDefinedType::List(t) => {
551
0
                self.expand_component_val_ty(&mut t.element);
552
0
            }
553
0
            ComponentDefinedType::Tuple(t) => {
554
0
                for field in t.fields.iter_mut() {
555
0
                    self.expand_component_val_ty(field);
556
0
                }
557
            }
558
0
            ComponentDefinedType::Option(t) => {
559
0
                self.expand_component_val_ty(&mut t.element);
560
0
            }
561
0
            ComponentDefinedType::Result(r) => {
562
0
                if let Some(ty) = &mut r.ok {
563
0
                    self.expand_component_val_ty(ty);
564
0
                }
565
566
0
                if let Some(ty) = &mut r.err {
567
0
                    self.expand_component_val_ty(ty);
568
0
                }
569
            }
570
0
            ComponentDefinedType::Own(_) | ComponentDefinedType::Borrow(_) => {}
571
        }
572
0
    }
573
574
0
    fn expand_component_val_ty(&mut self, ty: &mut ComponentValType<'a>) {
575
0
        let inline = match ty {
576
            ComponentValType::Inline(ComponentDefinedType::Primitive(_))
577
0
            | ComponentValType::Ref(_) => return,
578
0
            ComponentValType::Inline(inline) => {
579
0
                self.expand_defined_ty(inline);
580
0
                mem::take(inline)
581
            }
582
        };
583
        // If this inline type has already been defined within this context
584
        // then reuse the previously defined type to avoid injecting too many
585
        // types into the type index space.
586
0
        if let Some(idx) = inline.key().lookup(self) {
587
0
            *ty = ComponentValType::Ref(idx);
588
0
            return;
589
0
        }
590
0
591
0
        // And if this type isn't already defined we append it to the index
592
0
        // space with a fresh and unique name.
593
0
        let span = Span::from_offset(0); // FIXME(#613): don't manufacture
594
0
        let id = gensym::gen(span);
595
0
596
0
        self.types_to_prepend.push(inline.into_any_type(span, id));
597
0
598
0
        let idx = Index::Id(id);
599
0
        *ty = ComponentValType::Ref(idx);
600
0
    }
601
602
0
    fn expand_core_type_use<T>(
603
0
        &mut self,
604
0
        item: &mut CoreTypeUse<'a, T>,
605
0
    ) -> CoreItemRef<'a, kw::r#type>
606
0
    where
607
0
        T: TypeReference<'a>,
608
0
    {
609
0
        let span = Span::from_offset(0); // FIXME(#613): don't manufacture
610
0
        let mut inline = match mem::take(item) {
611
            // If this type-use was already a reference to an existing type
612
            // then we put it back the way it was and return the corresponding
613
            // index.
614
0
            CoreTypeUse::Ref(idx) => {
615
0
                *item = CoreTypeUse::Ref(idx.clone());
616
0
                return idx;
617
            }
618
619
            // ... otherwise with an inline type definition we go into
620
            // processing below.
621
0
            CoreTypeUse::Inline(inline) => inline,
622
0
        };
623
0
        inline.expand(self);
624
625
        // If this inline type has already been defined within this context
626
        // then reuse the previously defined type to avoid injecting too many
627
        // types into the type index space.
628
0
        if let Some(idx) = inline.key().lookup(self) {
629
0
            let ret = CoreItemRef {
630
0
                idx,
631
0
                kind: kw::r#type(span),
632
0
                export_name: None,
633
0
            };
634
0
            *item = CoreTypeUse::Ref(ret.clone());
635
0
            return ret;
636
0
        }
637
0
638
0
        // And if this type isn't already defined we append it to the index
639
0
        // space with a fresh and unique name.
640
0
        let id = gensym::gen(span);
641
0
642
0
        self.types_to_prepend.push(inline.into_any_type(span, id));
643
0
644
0
        let idx = Index::Id(id);
645
0
        let ret = CoreItemRef {
646
0
            idx,
647
0
            kind: kw::r#type(span),
648
0
            export_name: None,
649
0
        };
650
0
651
0
        *item = CoreTypeUse::Ref(ret.clone());
652
0
        ret
653
0
    }
654
655
0
    fn expand_component_type_use<T>(
656
0
        &mut self,
657
0
        item: &mut ComponentTypeUse<'a, T>,
658
0
    ) -> ItemRef<'a, kw::r#type>
659
0
    where
660
0
        T: TypeReference<'a>,
661
0
    {
662
0
        let span = Span::from_offset(0); // FIXME(#613): don't manufacture
663
0
        let mut inline = match mem::take(item) {
664
            // If this type-use was already a reference to an existing type
665
            // then we put it back the way it was and return the corresponding
666
            // index.
667
0
            ComponentTypeUse::Ref(idx) => {
668
0
                *item = ComponentTypeUse::Ref(idx.clone());
669
0
                return idx;
670
            }
671
672
            // ... otherwise with an inline type definition we go into
673
            // processing below.
674
0
            ComponentTypeUse::Inline(inline) => inline,
675
0
        };
676
0
        inline.expand(self);
677
678
        // If this inline type has already been defined within this context
679
        // then reuse the previously defined type to avoid injecting too many
680
        // types into the type index space.
681
0
        if let Some(idx) = inline.key().lookup(self) {
682
0
            let ret = ItemRef {
683
0
                idx,
684
0
                kind: kw::r#type(span),
685
0
                export_names: Vec::new(),
686
0
            };
687
0
            *item = ComponentTypeUse::Ref(ret.clone());
688
0
            return ret;
689
0
        }
690
0
691
0
        // And if this type isn't already defined we append it to the index
692
0
        // space with a fresh and unique name.
693
0
        let id = gensym::gen(span);
694
0
695
0
        self.types_to_prepend.push(inline.into_any_type(span, id));
696
0
697
0
        let idx = Index::Id(id);
698
0
        let ret = ItemRef {
699
0
            idx,
700
0
            kind: kw::r#type(span),
701
0
            export_names: Vec::new(),
702
0
        };
703
0
704
0
        *item = ComponentTypeUse::Ref(ret.clone());
705
0
        ret
706
0
    }
Unexecuted instantiation: <wast::component::expand::Expander>::expand_component_type_use::<wast::component::types::InstanceType>
Unexecuted instantiation: <wast::component::expand::Expander>::expand_component_type_use::<wast::component::types::ComponentType>
Unexecuted instantiation: <wast::component::expand::Expander>::expand_component_type_use::<wast::component::types::ComponentFunctionType>
707
708
0
    fn expand_core_instantiation_arg(&mut self, arg: &mut CoreInstantiationArgKind<'a>) {
709
0
        let (span, exports) = match arg {
710
0
            CoreInstantiationArgKind::Instance(_) => return,
711
0
            CoreInstantiationArgKind::BundleOfExports(span, exports) => (*span, mem::take(exports)),
712
0
        };
713
0
        let id = gensym::gen(span);
714
0
        self.component_fields_to_prepend
715
0
            .push(ComponentField::CoreInstance(CoreInstance {
716
0
                span,
717
0
                id: Some(id),
718
0
                name: None,
719
0
                kind: CoreInstanceKind::BundleOfExports(exports),
720
0
            }));
721
0
        *arg = CoreInstantiationArgKind::Instance(CoreItemRef {
722
0
            kind: kw::instance(span),
723
0
            idx: Index::Id(id),
724
0
            export_name: None,
725
0
        });
726
0
    }
727
728
0
    fn expand_instantiation_arg(&mut self, arg: &mut InstantiationArgKind<'a>) {
729
0
        let (span, exports) = match arg {
730
0
            InstantiationArgKind::Item(_) => return,
731
0
            InstantiationArgKind::BundleOfExports(span, exports) => (*span, mem::take(exports)),
732
0
        };
733
0
        let id = gensym::gen(span);
734
0
        self.component_fields_to_prepend
735
0
            .push(ComponentField::Instance(Instance {
736
0
                span,
737
0
                id: Some(id),
738
0
                name: None,
739
0
                exports: Default::default(),
740
0
                kind: InstanceKind::BundleOfExports(exports),
741
0
            }));
742
0
        *arg = InstantiationArgKind::Item(ComponentExportKind::instance(span, id));
743
0
    }
744
}
745
746
trait TypeReference<'a> {
747
    type Key: TypeKey<'a>;
748
    fn key(&self) -> Self::Key;
749
    fn expand(&mut self, cx: &mut Expander<'a>);
750
    fn into_any_type(self, span: Span, id: Id<'a>) -> AnyType<'a>;
751
}
752
753
impl<'a> TypeReference<'a> for ComponentDefinedType<'a> {
754
    type Key = Todo; // FIXME(#598): should implement this
755
756
0
    fn key(&self) -> Self::Key {
757
0
        Todo
758
0
    }
759
760
0
    fn expand(&mut self, cx: &mut Expander<'a>) {
761
0
        cx.expand_defined_ty(self)
762
0
    }
763
764
0
    fn into_any_type(self, span: Span, id: Id<'a>) -> AnyType<'a> {
765
0
        AnyType::Component(Type {
766
0
            span,
767
0
            id: Some(id),
768
0
            name: None,
769
0
            exports: Default::default(),
770
0
            def: TypeDef::Defined(self),
771
0
        })
772
0
    }
773
}
774
775
impl<'a> TypeReference<'a> for ComponentType<'a> {
776
    type Key = Todo; // FIXME(#598): should implement this
777
778
0
    fn key(&self) -> Self::Key {
779
0
        Todo
780
0
    }
781
782
0
    fn expand(&mut self, cx: &mut Expander<'a>) {
783
0
        cx.expand_component_ty(self)
784
0
    }
785
786
0
    fn into_any_type(self, span: Span, id: Id<'a>) -> AnyType<'a> {
787
0
        AnyType::Component(Type {
788
0
            span,
789
0
            id: Some(id),
790
0
            name: None,
791
0
            exports: Default::default(),
792
0
            def: TypeDef::Component(self),
793
0
        })
794
0
    }
795
}
796
797
impl<'a> TypeReference<'a> for ModuleType<'a> {
798
    type Key = Todo; // FIXME(#598): should implement this
799
800
0
    fn key(&self) -> Self::Key {
801
0
        Todo
802
0
    }
803
804
0
    fn expand(&mut self, cx: &mut Expander<'a>) {
805
0
        cx.expand_module_ty(self)
806
0
    }
807
808
0
    fn into_any_type(self, span: Span, id: Id<'a>) -> AnyType<'a> {
809
0
        AnyType::Core(CoreType {
810
0
            span,
811
0
            id: Some(id),
812
0
            name: None,
813
0
            def: CoreTypeDef::Module(self),
814
0
        })
815
0
    }
816
}
817
818
impl<'a> TypeReference<'a> for InstanceType<'a> {
819
    type Key = Todo; // FIXME(#598): should implement this
820
821
0
    fn key(&self) -> Self::Key {
822
0
        Todo
823
0
    }
824
825
0
    fn expand(&mut self, cx: &mut Expander<'a>) {
826
0
        cx.expand_instance_ty(self)
827
0
    }
828
829
0
    fn into_any_type(self, span: Span, id: Id<'a>) -> AnyType<'a> {
830
0
        AnyType::Component(Type {
831
0
            span,
832
0
            id: Some(id),
833
0
            name: None,
834
0
            exports: Default::default(),
835
0
            def: TypeDef::Instance(self),
836
0
        })
837
0
    }
838
}
839
840
impl<'a> TypeReference<'a> for ComponentFunctionType<'a> {
841
    type Key = Todo; // FIXME(#598): should implement this
842
843
0
    fn key(&self) -> Self::Key {
844
0
        Todo
845
0
    }
846
847
0
    fn expand(&mut self, cx: &mut Expander<'a>) {
848
0
        cx.expand_func_ty(self)
849
0
    }
850
851
0
    fn into_any_type(self, span: Span, id: Id<'a>) -> AnyType<'a> {
852
0
        AnyType::Component(Type {
853
0
            span,
854
0
            id: Some(id),
855
0
            name: None,
856
0
            exports: Default::default(),
857
0
            def: TypeDef::Func(self),
858
0
        })
859
0
    }
860
}
861
862
trait TypeKey<'a> {
863
    fn lookup(&self, cx: &Expander<'a>) -> Option<Index<'a>>;
864
    fn insert(&self, cx: &mut Expander<'a>, index: Index<'a>);
865
}
866
867
struct Todo;
868
869
impl<'a> TypeKey<'a> for Todo {
870
0
    fn lookup(&self, _cx: &Expander<'a>) -> Option<Index<'a>> {
871
0
        None
872
0
    }
873
874
0
    fn insert(&self, _cx: &mut Expander<'a>, _index: Index<'a>) {}
875
}