@@ -145,42 +145,7 @@ impl WorldGenerator for CSharp {
145
145
gen. import ( & resolve. name_world_key ( key) , func) ;
146
146
}
147
147
148
- let mut ret_struct_type = String :: new ( ) ;
149
- if gen. gen . return_area_size > 0 {
150
- uwrite ! (
151
- ret_struct_type,
152
- r#"
153
- private unsafe struct ReturnArea
154
- {{
155
- private int GetS32(IntPtr ptr, int offset)
156
- {{
157
- var span = new Span<byte>((void*)ptr, {});
158
-
159
- return BitConverter.ToInt32(span.Slice(offset, 4));
160
- }}
161
-
162
- public string GetUTF8String(IntPtr ptr)
163
- {{
164
- return Encoding.UTF8.GetString((byte*)GetS32(ptr, 0), GetS32(ptr, 4));
165
- }}
166
-
167
- }}
168
-
169
- [ThreadStatic]
170
- [FixedAddressValueType]
171
- private static ReturnArea returnArea;
172
- "# ,
173
- gen . gen . return_area_size
174
- ) ;
175
- }
176
-
177
- uwrite ! (
178
- gen . csharp_interop_src,
179
- r#"
180
- {ret_struct_type}
181
- "#
182
- ) ;
183
-
148
+ gen. add_import_return_area ( ) ;
184
149
gen. add_interface_fragment ( false ) ;
185
150
}
186
151
@@ -217,59 +182,7 @@ impl WorldGenerator for CSharp {
217
182
gen. export ( func, Some ( key) ) ;
218
183
}
219
184
220
- // Declare a statically-allocated return area, if needed. We only do
221
- // this for export bindings, because import bindings allocate their
222
- // return-area on the stack.
223
- if gen. gen . return_area_size > 0 {
224
- let mut ret_area_str = String :: new ( ) ;
225
-
226
- uwrite ! (
227
- ret_area_str,
228
- "
229
- [InlineArray({})]
230
- [StructLayout(LayoutKind.Sequential, Pack = {})]
231
- private struct ReturnArea
232
- {{
233
- private byte buffer;
234
-
235
- private int GetS32(int offset)
236
- {{
237
- ReadOnlySpan<byte> span = this;
238
-
239
- return BitConverter.ToInt32(span.Slice(offset, 4));
240
- }}
241
-
242
- public void SetS32(int offset, int value)
243
- {{
244
- Span<byte> span = this;
245
-
246
- BitConverter.TryWriteBytes(span.Slice(offset), value);
247
- }}
248
-
249
- internal unsafe int AddrOfBuffer()
250
- {{
251
- fixed(byte* ptr = &buffer)
252
- {{
253
- return (int)ptr;
254
- }}
255
- }}
256
-
257
- public unsafe string GetUTF8String(int p0, int p1)
258
- {{
259
- return Encoding.UTF8.GetString((byte*)p0, p1);
260
- }}
261
- }}
262
-
263
- [ThreadStatic]
264
- private static ReturnArea returnArea = default;
265
- " ,
266
- gen . gen . return_area_size,
267
- gen . gen . return_area_align,
268
- ) ;
269
-
270
- gen. csharp_interop_src . push_str ( & ret_area_str) ;
271
- }
272
-
185
+ gen. add_export_return_area ( ) ;
273
186
gen. add_interface_fragment ( true ) ;
274
187
Ok ( ( ) )
275
188
}
@@ -678,6 +591,99 @@ impl InterfaceGenerator<'_> {
678
591
} ) ;
679
592
}
680
593
594
+ fn add_import_return_area ( & mut self ) {
595
+ let mut ret_struct_type = String :: new ( ) ;
596
+ if self . gen . return_area_size > 0 {
597
+ uwrite ! (
598
+ ret_struct_type,
599
+ r#"
600
+ private unsafe struct ReturnArea
601
+ {{
602
+ private int GetS32(IntPtr ptr, int offset)
603
+ {{
604
+ var span = new Span<byte>((void*)ptr, {});
605
+
606
+ return BitConverter.ToInt32(span.Slice(offset, 4));
607
+ }}
608
+
609
+ public string GetUTF8String(IntPtr ptr)
610
+ {{
611
+ return Encoding.UTF8.GetString((byte*)GetS32(ptr, 0), GetS32(ptr, 4));
612
+ }}
613
+
614
+ }}
615
+
616
+ [ThreadStatic]
617
+ [FixedAddressValueType]
618
+ private static ReturnArea returnArea;
619
+ "# ,
620
+ self . gen . return_area_size
621
+ ) ;
622
+ }
623
+
624
+ uwrite ! (
625
+ self . csharp_interop_src,
626
+ r#"
627
+ {ret_struct_type}
628
+ "#
629
+ ) ;
630
+ }
631
+
632
+ fn add_export_return_area ( & mut self ) {
633
+ // Declare a statically-allocated return area, if needed. We only do
634
+ // this for export bindings, because import bindings allocate their
635
+ // return-area on the stack.
636
+ if self . gen . return_area_size > 0 {
637
+ let mut ret_area_str = String :: new ( ) ;
638
+
639
+ uwrite ! (
640
+ ret_area_str,
641
+ "
642
+ [InlineArray({})]
643
+ [StructLayout(LayoutKind.Sequential, Pack = {})]
644
+ private struct ReturnArea
645
+ {{
646
+ private byte buffer;
647
+
648
+ private int GetS32(int offset)
649
+ {{
650
+ ReadOnlySpan<byte> span = this;
651
+
652
+ return BitConverter.ToInt32(span.Slice(offset, 4));
653
+ }}
654
+
655
+ public void SetS32(int offset, int value)
656
+ {{
657
+ Span<byte> span = this;
658
+
659
+ BitConverter.TryWriteBytes(span.Slice(offset), value);
660
+ }}
661
+
662
+ internal unsafe int AddrOfBuffer()
663
+ {{
664
+ fixed(byte* ptr = &buffer)
665
+ {{
666
+ return (int)ptr;
667
+ }}
668
+ }}
669
+
670
+ public unsafe string GetUTF8String(int p0, int p1)
671
+ {{
672
+ return Encoding.UTF8.GetString((byte*)p0, p1);
673
+ }}
674
+ }}
675
+
676
+ [ThreadStatic]
677
+ private static ReturnArea returnArea = default;
678
+ " ,
679
+ self . gen . return_area_size,
680
+ self . gen . return_area_align,
681
+ ) ;
682
+
683
+ self . csharp_interop_src . push_str ( & ret_area_str) ;
684
+ }
685
+ }
686
+
681
687
fn add_world_fragment ( self ) {
682
688
self . gen . world_fragments . push ( InterfaceFragment {
683
689
csharp_src : self . src ,
0 commit comments