Coverage Report

Created: 2024-10-16 07:58

/rust/registry/src/index.crates.io-6f17d22bba15001f/wast-64.0.0/src/component/instance.rs
Line
Count
Source (jump to first uncovered line)
1
use crate::component::*;
2
use crate::core;
3
use crate::kw;
4
use crate::parser::{Parse, Parser, Result};
5
use crate::token::{Id, LParen, NameAnnotation, Span};
6
7
/// A core instance defined by instantiation or exporting core items.
8
#[derive(Debug)]
9
pub struct CoreInstance<'a> {
10
    /// Where this `core instance` was defined.
11
    pub span: Span,
12
    /// An identifier that this instance is resolved with (optionally) for name
13
    /// resolution.
14
    pub id: Option<Id<'a>>,
15
    /// An optional name for this instance stored in the custom `name` section.
16
    pub name: Option<NameAnnotation<'a>>,
17
    /// What kind of instance this is.
18
    pub kind: CoreInstanceKind<'a>,
19
}
20
21
impl<'a> Parse<'a> for CoreInstance<'a> {
22
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
23
0
        let span = parser.parse::<kw::core>()?.0;
24
0
        parser.parse::<kw::instance>()?;
25
0
        let id = parser.parse()?;
26
0
        let name = parser.parse()?;
27
0
        let kind = parser.parse()?;
28
29
0
        Ok(Self {
30
0
            span,
31
0
            id,
32
0
            name,
33
0
            kind,
34
0
        })
35
0
    }
36
}
37
38
/// The kinds of core instances in the text format.
39
#[derive(Debug)]
40
pub enum CoreInstanceKind<'a> {
41
    /// Instantiate a core module.
42
    Instantiate {
43
        /// The module being instantiated.
44
        module: ItemRef<'a, kw::module>,
45
        /// Arguments used to instantiate the instance.
46
        args: Vec<CoreInstantiationArg<'a>>,
47
    },
48
    /// The instance is defined by exporting local items as an instance.
49
    BundleOfExports(Vec<CoreInstanceExport<'a>>),
50
}
51
52
impl<'a> Parse<'a> for CoreInstanceKind<'a> {
53
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
54
0
        if parser.peek::<LParen>()? && parser.peek2::<kw::instantiate>()? {
55
0
            parser.parens(|parser| {
56
0
                parser.parse::<kw::instantiate>()?;
57
                Ok(Self::Instantiate {
58
0
                    module: parser.parse::<IndexOrRef<'_, _>>()?.0,
59
0
                    args: parser.parse()?,
60
                })
61
0
            })
62
        } else {
63
0
            Ok(Self::BundleOfExports(parser.parse()?))
64
        }
65
0
    }
66
}
67
68
impl Default for kw::module {
69
0
    fn default() -> kw::module {
70
0
        kw::module(Span::from_offset(0))
71
0
    }
72
}
73
74
/// An argument to instantiate a core module.
75
#[derive(Debug)]
76
pub struct CoreInstantiationArg<'a> {
77
    /// The name of the instantiation argument.
78
    pub name: &'a str,
79
    /// The kind of core instantiation argument.
80
    pub kind: CoreInstantiationArgKind<'a>,
81
}
82
83
impl<'a> Parse<'a> for CoreInstantiationArg<'a> {
84
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
85
0
        parser.parse::<kw::with>()?;
86
        Ok(Self {
87
0
            name: parser.parse()?,
88
0
            kind: parser.parse()?,
89
        })
90
0
    }
91
}
92
93
impl<'a> Parse<'a> for Vec<CoreInstantiationArg<'a>> {
94
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
95
0
        let mut args = Vec::new();
96
0
        while !parser.is_empty() {
97
0
            args.push(parser.parens(|parser| parser.parse())?);
98
        }
99
0
        Ok(args)
100
0
    }
101
}
102
103
/// The kind of core instantiation argument.
104
#[derive(Debug)]
105
pub enum CoreInstantiationArgKind<'a> {
106
    /// The argument is a reference to an instance.
107
    Instance(CoreItemRef<'a, kw::instance>),
108
    /// The argument is an instance created from local exported core items.
109
    ///
110
    /// This is syntactic sugar for defining a core instance and also using it
111
    /// as an instantiation argument.
112
    BundleOfExports(Span, Vec<CoreInstanceExport<'a>>),
113
}
114
115
impl<'a> Parse<'a> for CoreInstantiationArgKind<'a> {
116
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
117
0
        parser.parens(|parser| {
118
0
            if let Some(r) = parser.parse()? {
119
0
                Ok(Self::Instance(r))
120
            } else {
121
0
                let span = parser.parse::<kw::instance>()?.0;
122
0
                Ok(Self::BundleOfExports(span, parser.parse()?))
123
            }
124
0
        })
125
0
    }
126
}
127
128
/// An exported item as part of a core instance.
129
#[derive(Debug)]
130
pub struct CoreInstanceExport<'a> {
131
    /// Where this export was defined.
132
    pub span: Span,
133
    /// The name of this export from the instance.
134
    pub name: &'a str,
135
    /// What's being exported from the instance.
136
    pub item: CoreItemRef<'a, core::ExportKind>,
137
}
138
139
impl<'a> Parse<'a> for CoreInstanceExport<'a> {
140
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
141
0
        Ok(Self {
142
0
            span: parser.parse::<kw::export>()?.0,
143
0
            name: parser.parse()?,
144
0
            item: parser.parens(|parser| parser.parse())?,
145
        })
146
0
    }
147
}
148
149
impl<'a> Parse<'a> for Vec<CoreInstanceExport<'a>> {
150
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
151
0
        let mut exports = Vec::new();
152
0
        while !parser.is_empty() {
153
0
            exports.push(parser.parens(|parser| parser.parse())?);
154
        }
155
0
        Ok(exports)
156
0
    }
157
}
158
159
/// A component instance defined by instantiation or exporting items.
160
#[derive(Debug)]
161
pub struct Instance<'a> {
162
    /// Where this `instance` was defined.
163
    pub span: Span,
164
    /// An identifier that this instance is resolved with (optionally) for name
165
    /// resolution.
166
    pub id: Option<Id<'a>>,
167
    /// An optional name for this instance stored in the custom `name` section.
168
    pub name: Option<NameAnnotation<'a>>,
169
    /// If present, inline export annotations which indicate names this
170
    /// definition should be exported under.
171
    pub exports: InlineExport<'a>,
172
    /// What kind of instance this is.
173
    pub kind: InstanceKind<'a>,
174
}
175
176
impl<'a> Parse<'a> for Instance<'a> {
177
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
178
0
        let span = parser.parse::<kw::instance>()?.0;
179
0
        let id = parser.parse()?;
180
0
        let name = parser.parse()?;
181
0
        let exports = parser.parse()?;
182
0
        let kind = parser.parse()?;
183
184
0
        Ok(Self {
185
0
            span,
186
0
            id,
187
0
            name,
188
0
            exports,
189
0
            kind,
190
0
        })
191
0
    }
192
}
193
194
/// The kinds of instances in the text format.
195
#[derive(Debug)]
196
pub enum InstanceKind<'a> {
197
    /// The `(instance (import "x"))` sugar syntax
198
    Import {
199
        /// The name of the import
200
        import: InlineImport<'a>,
201
        /// The type of the instance being imported
202
        ty: ComponentTypeUse<'a, InstanceType<'a>>,
203
    },
204
    /// Instantiate a component.
205
    Instantiate {
206
        /// The component being instantiated.
207
        component: ItemRef<'a, kw::component>,
208
        /// Arguments used to instantiate the instance.
209
        args: Vec<InstantiationArg<'a>>,
210
    },
211
    /// The instance is defined by exporting local items as an instance.
212
    BundleOfExports(Vec<ComponentExport<'a>>),
213
}
214
215
impl<'a> Parse<'a> for InstanceKind<'a> {
216
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
217
0
        if let Some(import) = parser.parse()? {
218
            return Ok(Self::Import {
219
0
                import,
220
0
                ty: parser.parse()?,
221
            });
222
0
        }
223
0
224
0
        if parser.peek::<LParen>()? && parser.peek2::<kw::instantiate>()? {
225
0
            parser.parens(|parser| {
226
0
                parser.parse::<kw::instantiate>()?;
227
                Ok(Self::Instantiate {
228
0
                    component: parser.parse::<IndexOrRef<'_, _>>()?.0,
229
0
                    args: parser.parse()?,
230
                })
231
0
            })
232
        } else {
233
0
            Ok(Self::BundleOfExports(parser.parse()?))
234
        }
235
0
    }
236
}
237
238
impl Default for kw::component {
239
0
    fn default() -> kw::component {
240
0
        kw::component(Span::from_offset(0))
241
0
    }
242
}
243
244
/// An argument to instantiate a component.
245
#[derive(Debug)]
246
pub struct InstantiationArg<'a> {
247
    /// The name of the instantiation argument.
248
    pub name: &'a str,
249
    /// The kind of instantiation argument.
250
    pub kind: InstantiationArgKind<'a>,
251
}
252
253
impl<'a> Parse<'a> for InstantiationArg<'a> {
254
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
255
0
        parser.parse::<kw::with>()?;
256
        Ok(Self {
257
0
            name: parser.parse()?,
258
0
            kind: parser.parse()?,
259
        })
260
0
    }
261
}
262
263
impl<'a> Parse<'a> for Vec<InstantiationArg<'a>> {
264
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
265
0
        let mut args = Vec::new();
266
0
        while !parser.is_empty() {
267
0
            args.push(parser.parens(|parser| parser.parse())?);
268
        }
269
0
        Ok(args)
270
0
    }
271
}
272
273
/// The kind of instantiation argument.
274
#[derive(Debug)]
275
pub enum InstantiationArgKind<'a> {
276
    /// The argument is a reference to a component item.
277
    Item(ComponentExportKind<'a>),
278
    /// The argument is an instance created from local exported items.
279
    ///
280
    /// This is syntactic sugar for defining an instance and also using it
281
    /// as an instantiation argument.
282
    BundleOfExports(Span, Vec<ComponentExport<'a>>),
283
}
284
285
impl<'a> Parse<'a> for InstantiationArgKind<'a> {
286
0
    fn parse(parser: Parser<'a>) -> Result<Self> {
287
0
        if let Some(item) = parser.parse()? {
288
0
            Ok(Self::Item(item))
289
        } else {
290
0
            parser.parens(|parser| {
291
0
                let span = parser.parse::<kw::instance>()?.0;
292
0
                Ok(Self::BundleOfExports(span, parser.parse()?))
293
0
            })
294
        }
295
0
    }
296
}