1 use {
2     crate::{
3         store::StoreInner,
4         vm::{component::ComponentInstance, VMFuncRef, VMMemoryDefinition},
5         AsContextMut, ValRaw,
6     },
7     anyhow::Result,
8     futures::{stream::FuturesUnordered, FutureExt},
9     std::{boxed::Box, future::Future, mem::MaybeUninit, pin::Pin},
10     wasmtime_environ::component::{
11         RuntimeComponentInstanceIndex, TypeComponentLocalErrorContextTableIndex,
12         TypeFutureTableIndex, TypeStreamTableIndex, TypeTupleIndex,
13     },
14 };
15 
16 pub use futures_and_streams::{ErrorContext, FutureReader, StreamReader};
17 
18 mod futures_and_streams;
19 
20 /// Represents the result of a concurrent operation.
21 ///
22 /// This is similar to a [`std::future::Future`] except that it represents an
23 /// operation which requires exclusive access to a store in order to make
24 /// progress -- without monopolizing that store for the lifetime of the
25 /// operation.
26 pub struct Promise<T>(Pin<Box<dyn Future<Output = T> + Send + Sync + 'static>>);
27 
28 impl<T: 'static> Promise<T> {
29     /// Map the result of this `Promise` from one value to another.
30     pub fn map<U>(self, fun: impl FnOnce(T) -> U + Send + Sync + 'static) -> Promise<U> {
31         Promise(Box::pin(self.0.map(fun)))
32     }
33 
34     /// Convert this `Promise` to a future which may be `await`ed for its
35     /// result.
36     ///
37     /// The returned future will require exclusive use of the store until it
38     /// completes.  If you need to await more than one `Promise` concurrently,
39     /// use [`PromisesUnordered`].
40     pub async fn get<U: Send>(self, store: impl AsContextMut<Data = U>) -> Result<T> {
41         _ = store;
42         todo!()
43     }
44 
45     /// Convert this `Promise` to a future which may be `await`ed for its
46     /// result.
47     ///
48     /// Unlike [`Self::get`], this does _not_ take a store parameter, meaning
49     /// the returned future will not make progress until and unless the event
50     /// loop for the store it came from is polled.  Thus, this method should
51     /// only be used from within host functions and not from top-level embedder
52     /// code.
53     pub fn into_future(self) -> Pin<Box<dyn Future<Output = T> + Send + Sync + 'static>> {
54         self.0
55     }
56 }
57 
58 /// Represents a collection of zero or more concurrent operations.
59 ///
60 /// Similar to [`futures::stream::FuturesUnordered`], this type supports
61 /// `await`ing more than one [`Promise`]s concurrently.
62 pub struct PromisesUnordered<T>(
63     FuturesUnordered<Pin<Box<dyn Future<Output = T> + Send + Sync + 'static>>>,
64 );
65 
66 impl<T: 'static> PromisesUnordered<T> {
67     /// Create a new `PromisesUnordered` with no entries.
68     pub fn new() -> Self {
69         Self(FuturesUnordered::new())
70     }
71 
72     /// Add the specified [`Promise`] to this collection.
73     pub fn push(&mut self, promise: Promise<T>) {
74         self.0.push(promise.0)
75     }
76 
77     /// Get the next result from this collection, if any.
78     pub async fn next<U: Send>(&mut self, store: impl AsContextMut<Data = U>) -> Result<Option<T>> {
79         _ = store;
80         todo!()
81     }
82 }
83 
84 /// Trait representing component model ABI async intrinsics and fused adapter
85 /// helper functions.
86 pub unsafe trait VMComponentAsyncStore {
87     /// The `backpressure.set` intrinsic.
88     fn backpressure_set(
89         &mut self,
90         caller_instance: RuntimeComponentInstanceIndex,
91         enabled: u32,
92     ) -> Result<()>;
93 
94     /// The `task.return` intrinsic.
95     fn task_return(
96         &mut self,
97         instance: &mut ComponentInstance,
98         ty: TypeTupleIndex,
99         storage: *mut ValRaw,
100         storage_len: usize,
101     ) -> Result<()>;
102 
103     /// The `waitable-set.new` intrinsic.
104     fn waitable_set_new(
105         &mut self,
106         instance: &mut ComponentInstance,
107         caller_instance: RuntimeComponentInstanceIndex,
108     ) -> Result<u32>;
109 
110     /// The `waitable-set.wait` intrinsic.
111     fn waitable_set_wait(
112         &mut self,
113         instance: &mut ComponentInstance,
114         caller_instance: RuntimeComponentInstanceIndex,
115         set: u32,
116         async_: bool,
117         memory: *mut VMMemoryDefinition,
118         payload: u32,
119     ) -> Result<u32>;
120 
121     /// The `waitable-set.poll` intrinsic.
122     fn waitable_set_poll(
123         &mut self,
124         instance: &mut ComponentInstance,
125         caller_instance: RuntimeComponentInstanceIndex,
126         set: u32,
127         async_: bool,
128         memory: *mut VMMemoryDefinition,
129         payload: u32,
130     ) -> Result<u32>;
131 
132     /// The `waitable-set.drop` intrinsic.
133     fn waitable_set_drop(
134         &mut self,
135         instance: &mut ComponentInstance,
136         caller_instance: RuntimeComponentInstanceIndex,
137         set: u32,
138     ) -> Result<()>;
139 
140     /// The `waitable.join` intrinsic.
141     fn waitable_join(
142         &mut self,
143         instance: &mut ComponentInstance,
144         caller_instance: RuntimeComponentInstanceIndex,
145         set: u32,
146         waitable: u32,
147     ) -> Result<()>;
148 
149     /// The `yield` intrinsic.
150     fn yield_(&mut self, instance: &mut ComponentInstance, async_: bool) -> Result<()>;
151 
152     /// The `subtask.drop` intrinsic.
153     fn subtask_drop(
154         &mut self,
155         instance: &mut ComponentInstance,
156         caller_instance: RuntimeComponentInstanceIndex,
157         task_id: u32,
158     ) -> Result<()>;
159 
160     /// A helper function for fused adapter modules involving calls where the
161     /// caller is sync-lowered but the callee is async-lifted.
162     fn sync_enter(
163         &mut self,
164         start: *mut VMFuncRef,
165         return_: *mut VMFuncRef,
166         caller_instance: RuntimeComponentInstanceIndex,
167         task_return_type: TypeTupleIndex,
168         result_count: u32,
169         storage: *mut ValRaw,
170         storage_len: usize,
171     ) -> Result<()>;
172 
173     /// A helper function for fused adapter modules involving calls where the
174     /// caller is sync-lowered but the callee is async-lifted.
175     fn sync_exit(
176         &mut self,
177         instance: &mut ComponentInstance,
178         callback: *mut VMFuncRef,
179         caller_instance: RuntimeComponentInstanceIndex,
180         callee: *mut VMFuncRef,
181         callee_instance: RuntimeComponentInstanceIndex,
182         param_count: u32,
183         storage: *mut MaybeUninit<ValRaw>,
184         storage_len: usize,
185     ) -> Result<()>;
186 
187     /// A helper function for fused adapter modules involving calls where the
188     /// caller is async-lowered.
189     fn async_enter(
190         &mut self,
191         start: *mut VMFuncRef,
192         return_: *mut VMFuncRef,
193         caller_instance: RuntimeComponentInstanceIndex,
194         task_return_type: TypeTupleIndex,
195         params: u32,
196         results: u32,
197     ) -> Result<()>;
198 
199     /// A helper function for fused adapter modules involving calls where the
200     /// caller is async-lowered.
201     fn async_exit(
202         &mut self,
203         instance: &mut ComponentInstance,
204         callback: *mut VMFuncRef,
205         post_return: *mut VMFuncRef,
206         caller_instance: RuntimeComponentInstanceIndex,
207         callee: *mut VMFuncRef,
208         callee_instance: RuntimeComponentInstanceIndex,
209         param_count: u32,
210         result_count: u32,
211         flags: u32,
212     ) -> Result<u32>;
213 
214     /// The `future.new` intrinsic.
215     fn future_new(
216         &mut self,
217         instance: &mut ComponentInstance,
218         ty: TypeFutureTableIndex,
219     ) -> Result<u32>;
220 
221     /// The `future.write` intrinsic.
222     fn future_write(
223         &mut self,
224         instance: &mut ComponentInstance,
225         memory: *mut VMMemoryDefinition,
226         realloc: *mut VMFuncRef,
227         string_encoding: u8,
228         ty: TypeFutureTableIndex,
229         future: u32,
230         address: u32,
231     ) -> Result<u32>;
232 
233     /// The `future.read` intrinsic.
234     fn future_read(
235         &mut self,
236         instance: &mut ComponentInstance,
237         memory: *mut VMMemoryDefinition,
238         realloc: *mut VMFuncRef,
239         string_encoding: u8,
240         ty: TypeFutureTableIndex,
241         future: u32,
242         address: u32,
243     ) -> Result<u32>;
244 
245     /// The `future.cancel-write` intrinsic.
246     fn future_cancel_write(
247         &mut self,
248         instance: &mut ComponentInstance,
249         ty: TypeFutureTableIndex,
250         async_: bool,
251         writer: u32,
252     ) -> Result<u32>;
253 
254     /// The `future.cancel-read` intrinsic.
255     fn future_cancel_read(
256         &mut self,
257         instance: &mut ComponentInstance,
258         ty: TypeFutureTableIndex,
259         async_: bool,
260         reader: u32,
261     ) -> Result<u32>;
262 
263     /// The `future.close-writable` intrinsic.
264     fn future_close_writable(
265         &mut self,
266         instance: &mut ComponentInstance,
267         ty: TypeFutureTableIndex,
268         writer: u32,
269     ) -> Result<()>;
270 
271     /// The `future.close-readable` intrinsic.
272     fn future_close_readable(
273         &mut self,
274         instance: &mut ComponentInstance,
275         ty: TypeFutureTableIndex,
276         reader: u32,
277     ) -> Result<()>;
278 
279     /// The `stream.new` intrinsic.
280     fn stream_new(
281         &mut self,
282         instance: &mut ComponentInstance,
283         ty: TypeStreamTableIndex,
284     ) -> Result<u32>;
285 
286     /// The `stream.write` intrinsic.
287     fn stream_write(
288         &mut self,
289         instance: &mut ComponentInstance,
290         memory: *mut VMMemoryDefinition,
291         realloc: *mut VMFuncRef,
292         string_encoding: u8,
293         ty: TypeStreamTableIndex,
294         stream: u32,
295         address: u32,
296         count: u32,
297     ) -> Result<u32>;
298 
299     /// The `stream.read` intrinsic.
300     fn stream_read(
301         &mut self,
302         instance: &mut ComponentInstance,
303         memory: *mut VMMemoryDefinition,
304         realloc: *mut VMFuncRef,
305         string_encoding: u8,
306         ty: TypeStreamTableIndex,
307         stream: u32,
308         address: u32,
309         count: u32,
310     ) -> Result<u32>;
311 
312     /// The `stream.cancel-write` intrinsic.
313     fn stream_cancel_write(
314         &mut self,
315         instance: &mut ComponentInstance,
316         ty: TypeStreamTableIndex,
317         async_: bool,
318         writer: u32,
319     ) -> Result<u32>;
320 
321     /// The `stream.cancel-read` intrinsic.
322     fn stream_cancel_read(
323         &mut self,
324         instance: &mut ComponentInstance,
325         ty: TypeStreamTableIndex,
326         async_: bool,
327         reader: u32,
328     ) -> Result<u32>;
329 
330     /// The `stream.close-writable` intrinsic.
331     fn stream_close_writable(
332         &mut self,
333         instance: &mut ComponentInstance,
334         ty: TypeStreamTableIndex,
335         writer: u32,
336     ) -> Result<()>;
337 
338     /// The `stream.close-readable` intrinsic.
339     fn stream_close_readable(
340         &mut self,
341         instance: &mut ComponentInstance,
342         ty: TypeStreamTableIndex,
343         reader: u32,
344     ) -> Result<()>;
345 
346     /// The "fast-path" implementation of the `stream.write` intrinsic for
347     /// "flat" (i.e. memcpy-able) payloads.
348     fn flat_stream_write(
349         &mut self,
350         instance: &mut ComponentInstance,
351         memory: *mut VMMemoryDefinition,
352         realloc: *mut VMFuncRef,
353         ty: TypeStreamTableIndex,
354         payload_size: u32,
355         payload_align: u32,
356         stream: u32,
357         address: u32,
358         count: u32,
359     ) -> Result<u32>;
360 
361     /// The "fast-path" implementation of the `stream.read` intrinsic for "flat"
362     /// (i.e. memcpy-able) payloads.
363     fn flat_stream_read(
364         &mut self,
365         instance: &mut ComponentInstance,
366         memory: *mut VMMemoryDefinition,
367         realloc: *mut VMFuncRef,
368         ty: TypeStreamTableIndex,
369         payload_size: u32,
370         payload_align: u32,
371         stream: u32,
372         address: u32,
373         count: u32,
374     ) -> Result<u32>;
375 
376     /// The `error-context.new` intrinsic.
377     fn error_context_new(
378         &mut self,
379         instance: &mut ComponentInstance,
380         memory: *mut VMMemoryDefinition,
381         realloc: *mut VMFuncRef,
382         string_encoding: u8,
383         ty: TypeComponentLocalErrorContextTableIndex,
384         debug_msg_address: u32,
385         debug_msg_len: u32,
386     ) -> Result<u32>;
387 
388     /// The `error-context.debug-message` intrinsic.
389     fn error_context_debug_message(
390         &mut self,
391         instance: &mut ComponentInstance,
392         memory: *mut VMMemoryDefinition,
393         realloc: *mut VMFuncRef,
394         string_encoding: u8,
395         ty: TypeComponentLocalErrorContextTableIndex,
396         err_ctx_handle: u32,
397         debug_msg_address: u32,
398     ) -> Result<()>;
399 
400     /// The `error-context.drop` intrinsic.
401     fn error_context_drop(
402         &mut self,
403         instance: &mut ComponentInstance,
404         ty: TypeComponentLocalErrorContextTableIndex,
405         err_ctx_handle: u32,
406     ) -> Result<()>;
407 }
408 
409 unsafe impl<T> VMComponentAsyncStore for StoreInner<T> {
410     fn backpressure_set(
411         &mut self,
412         caller_instance: RuntimeComponentInstanceIndex,
413         enabled: u32,
414     ) -> Result<()> {
415         _ = (caller_instance, enabled);
416         todo!()
417     }
418 
419     fn task_return(
420         &mut self,
421         instance: &mut ComponentInstance,
422         ty: TypeTupleIndex,
423         storage: *mut ValRaw,
424         storage_len: usize,
425     ) -> Result<()> {
426         _ = (instance, ty, storage, storage_len);
427         todo!()
428     }
429 
430     fn waitable_set_new(
431         &mut self,
432         instance: &mut ComponentInstance,
433         caller_instance: RuntimeComponentInstanceIndex,
434     ) -> Result<u32> {
435         _ = (instance, caller_instance);
436         todo!();
437     }
438 
439     fn waitable_set_wait(
440         &mut self,
441         instance: &mut ComponentInstance,
442         caller_instance: RuntimeComponentInstanceIndex,
443         set: u32,
444         async_: bool,
445         memory: *mut VMMemoryDefinition,
446         payload: u32,
447     ) -> Result<u32> {
448         _ = (instance, caller_instance, set, async_, memory, payload);
449         todo!();
450     }
451 
452     fn waitable_set_poll(
453         &mut self,
454         instance: &mut ComponentInstance,
455         caller_instance: RuntimeComponentInstanceIndex,
456         set: u32,
457         async_: bool,
458         memory: *mut VMMemoryDefinition,
459         payload: u32,
460     ) -> Result<u32> {
461         _ = (instance, caller_instance, set, async_, memory, payload);
462         todo!();
463     }
464 
465     fn waitable_set_drop(
466         &mut self,
467         instance: &mut ComponentInstance,
468         caller_instance: RuntimeComponentInstanceIndex,
469         set: u32,
470     ) -> Result<()> {
471         _ = (instance, caller_instance, set);
472         todo!();
473     }
474 
475     fn waitable_join(
476         &mut self,
477         instance: &mut ComponentInstance,
478         caller_instance: RuntimeComponentInstanceIndex,
479         set: u32,
480         waitable: u32,
481     ) -> Result<()> {
482         _ = (instance, caller_instance, set, waitable);
483         todo!();
484     }
485 
486     fn yield_(&mut self, instance: &mut ComponentInstance, async_: bool) -> Result<()> {
487         _ = (instance, async_);
488         todo!()
489     }
490 
491     fn subtask_drop(
492         &mut self,
493         instance: &mut ComponentInstance,
494         caller_instance: RuntimeComponentInstanceIndex,
495         task_id: u32,
496     ) -> Result<()> {
497         _ = (instance, caller_instance, task_id);
498         todo!()
499     }
500 
501     fn sync_enter(
502         &mut self,
503         start: *mut VMFuncRef,
504         return_: *mut VMFuncRef,
505         caller_instance: RuntimeComponentInstanceIndex,
506         task_return_type: TypeTupleIndex,
507         result_count: u32,
508         storage: *mut ValRaw,
509         storage_len: usize,
510     ) -> Result<()> {
511         _ = (
512             start,
513             return_,
514             caller_instance,
515             task_return_type,
516             result_count,
517             storage,
518             storage_len,
519         );
520         todo!()
521     }
522 
523     fn sync_exit(
524         &mut self,
525         instance: &mut ComponentInstance,
526         callback: *mut VMFuncRef,
527         caller_instance: RuntimeComponentInstanceIndex,
528         callee: *mut VMFuncRef,
529         callee_instance: RuntimeComponentInstanceIndex,
530         param_count: u32,
531         storage: *mut MaybeUninit<ValRaw>,
532         storage_len: usize,
533     ) -> Result<()> {
534         _ = (
535             instance,
536             callback,
537             caller_instance,
538             callee,
539             callee_instance,
540             param_count,
541             storage,
542             storage_len,
543         );
544         todo!()
545     }
546 
547     fn async_enter(
548         &mut self,
549         start: *mut VMFuncRef,
550         return_: *mut VMFuncRef,
551         caller_instance: RuntimeComponentInstanceIndex,
552         task_return_type: TypeTupleIndex,
553         params: u32,
554         results: u32,
555     ) -> Result<()> {
556         _ = (
557             start,
558             return_,
559             caller_instance,
560             task_return_type,
561             params,
562             results,
563         );
564         todo!()
565     }
566 
567     fn async_exit(
568         &mut self,
569         instance: &mut ComponentInstance,
570         callback: *mut VMFuncRef,
571         post_return: *mut VMFuncRef,
572         caller_instance: RuntimeComponentInstanceIndex,
573         callee: *mut VMFuncRef,
574         callee_instance: RuntimeComponentInstanceIndex,
575         param_count: u32,
576         result_count: u32,
577         flags: u32,
578     ) -> Result<u32> {
579         _ = (
580             instance,
581             callback,
582             post_return,
583             caller_instance,
584             callee,
585             callee_instance,
586             param_count,
587             result_count,
588             flags,
589         );
590         todo!()
591     }
592 
593     fn future_new(
594         &mut self,
595         instance: &mut ComponentInstance,
596         ty: TypeFutureTableIndex,
597     ) -> Result<u32> {
598         _ = (instance, ty);
599         todo!()
600     }
601 
602     fn future_write(
603         &mut self,
604         instance: &mut ComponentInstance,
605         memory: *mut VMMemoryDefinition,
606         realloc: *mut VMFuncRef,
607         string_encoding: u8,
608         ty: TypeFutureTableIndex,
609         future: u32,
610         address: u32,
611     ) -> Result<u32> {
612         _ = (
613             instance,
614             memory,
615             realloc,
616             string_encoding,
617             ty,
618             future,
619             address,
620         );
621         todo!()
622     }
623 
624     fn future_read(
625         &mut self,
626         instance: &mut ComponentInstance,
627         memory: *mut VMMemoryDefinition,
628         realloc: *mut VMFuncRef,
629         string_encoding: u8,
630         ty: TypeFutureTableIndex,
631         future: u32,
632         address: u32,
633     ) -> Result<u32> {
634         _ = (
635             instance,
636             memory,
637             realloc,
638             string_encoding,
639             ty,
640             future,
641             address,
642         );
643         todo!()
644     }
645 
646     fn future_cancel_write(
647         &mut self,
648         instance: &mut ComponentInstance,
649         ty: TypeFutureTableIndex,
650         async_: bool,
651         writer: u32,
652     ) -> Result<u32> {
653         _ = (instance, ty, async_, writer);
654         todo!()
655     }
656 
657     fn future_cancel_read(
658         &mut self,
659         instance: &mut ComponentInstance,
660         ty: TypeFutureTableIndex,
661         async_: bool,
662         reader: u32,
663     ) -> Result<u32> {
664         _ = (instance, ty, async_, reader);
665         todo!()
666     }
667 
668     fn future_close_writable(
669         &mut self,
670         instance: &mut ComponentInstance,
671         ty: TypeFutureTableIndex,
672         writer: u32,
673     ) -> Result<()> {
674         _ = (instance, ty, writer);
675         todo!()
676     }
677 
678     fn future_close_readable(
679         &mut self,
680         instance: &mut ComponentInstance,
681         ty: TypeFutureTableIndex,
682         reader: u32,
683     ) -> Result<()> {
684         _ = (instance, ty, reader);
685         todo!()
686     }
687 
688     fn stream_new(
689         &mut self,
690         instance: &mut ComponentInstance,
691         ty: TypeStreamTableIndex,
692     ) -> Result<u32> {
693         _ = (instance, ty);
694         todo!()
695     }
696 
697     fn stream_write(
698         &mut self,
699         instance: &mut ComponentInstance,
700         memory: *mut VMMemoryDefinition,
701         realloc: *mut VMFuncRef,
702         string_encoding: u8,
703         ty: TypeStreamTableIndex,
704         stream: u32,
705         address: u32,
706         count: u32,
707     ) -> Result<u32> {
708         _ = (
709             instance,
710             memory,
711             realloc,
712             string_encoding,
713             ty,
714             stream,
715             address,
716             count,
717         );
718         todo!()
719     }
720 
721     fn stream_read(
722         &mut self,
723         instance: &mut ComponentInstance,
724         memory: *mut VMMemoryDefinition,
725         realloc: *mut VMFuncRef,
726         string_encoding: u8,
727         ty: TypeStreamTableIndex,
728         stream: u32,
729         address: u32,
730         count: u32,
731     ) -> Result<u32> {
732         _ = (
733             instance,
734             memory,
735             realloc,
736             string_encoding,
737             ty,
738             stream,
739             address,
740             count,
741         );
742         todo!()
743     }
744 
745     fn stream_cancel_write(
746         &mut self,
747         instance: &mut ComponentInstance,
748         ty: TypeStreamTableIndex,
749         async_: bool,
750         writer: u32,
751     ) -> Result<u32> {
752         _ = (instance, ty, async_, writer);
753         todo!()
754     }
755 
756     fn stream_cancel_read(
757         &mut self,
758         instance: &mut ComponentInstance,
759         ty: TypeStreamTableIndex,
760         async_: bool,
761         reader: u32,
762     ) -> Result<u32> {
763         _ = (instance, ty, async_, reader);
764         todo!()
765     }
766 
767     fn stream_close_writable(
768         &mut self,
769         instance: &mut ComponentInstance,
770         ty: TypeStreamTableIndex,
771         writer: u32,
772     ) -> Result<()> {
773         _ = (instance, ty, writer);
774         todo!()
775     }
776 
777     fn stream_close_readable(
778         &mut self,
779         instance: &mut ComponentInstance,
780         ty: TypeStreamTableIndex,
781         reader: u32,
782     ) -> Result<()> {
783         _ = (instance, ty, reader);
784         todo!()
785     }
786 
787     fn flat_stream_write(
788         &mut self,
789         instance: &mut ComponentInstance,
790         memory: *mut VMMemoryDefinition,
791         realloc: *mut VMFuncRef,
792         ty: TypeStreamTableIndex,
793         payload_size: u32,
794         payload_align: u32,
795         stream: u32,
796         address: u32,
797         count: u32,
798     ) -> Result<u32> {
799         _ = (
800             instance,
801             memory,
802             realloc,
803             ty,
804             payload_size,
805             payload_align,
806             stream,
807             address,
808             count,
809         );
810         todo!()
811     }
812 
813     fn flat_stream_read(
814         &mut self,
815         instance: &mut ComponentInstance,
816         memory: *mut VMMemoryDefinition,
817         realloc: *mut VMFuncRef,
818         ty: TypeStreamTableIndex,
819         payload_size: u32,
820         payload_align: u32,
821         stream: u32,
822         address: u32,
823         count: u32,
824     ) -> Result<u32> {
825         _ = (
826             instance,
827             memory,
828             realloc,
829             ty,
830             payload_size,
831             payload_align,
832             stream,
833             address,
834             count,
835         );
836         todo!()
837     }
838 
839     fn error_context_new(
840         &mut self,
841         instance: &mut ComponentInstance,
842         memory: *mut VMMemoryDefinition,
843         realloc: *mut VMFuncRef,
844         string_encoding: u8,
845         ty: TypeComponentLocalErrorContextTableIndex,
846         debug_msg_address: u32,
847         debug_msg_len: u32,
848     ) -> Result<u32> {
849         _ = (
850             instance,
851             memory,
852             realloc,
853             string_encoding,
854             ty,
855             debug_msg_address,
856             debug_msg_len,
857         );
858         todo!()
859     }
860 
861     fn error_context_debug_message(
862         &mut self,
863         instance: &mut ComponentInstance,
864         memory: *mut VMMemoryDefinition,
865         realloc: *mut VMFuncRef,
866         string_encoding: u8,
867         ty: TypeComponentLocalErrorContextTableIndex,
868         err_ctx_handle: u32,
869         debug_msg_address: u32,
870     ) -> Result<()> {
871         _ = (
872             instance,
873             memory,
874             realloc,
875             string_encoding,
876             ty,
877             err_ctx_handle,
878             debug_msg_address,
879         );
880         todo!()
881     }
882 
883     fn error_context_drop(
884         &mut self,
885         instance: &mut ComponentInstance,
886         ty: TypeComponentLocalErrorContextTableIndex,
887         err_ctx_handle: u32,
888     ) -> Result<()> {
889         _ = (instance, ty, err_ctx_handle);
890         todo!()
891     }
892 }
893