@@ -9,6 +9,7 @@ use std::fmt::Write;
99use std:: ops:: Deref ;
1010use std:: { iter, mem} ;
1111use wit_bindgen_core:: { Direction , Files , InterfaceGenerator as _, Types , WorldGenerator , uwrite} ;
12+ use wit_component:: WitPrinter ;
1213use wit_parser:: abi:: WasmType ;
1314use wit_parser:: {
1415 Function , InterfaceId , Resolve , SizeAlign , Type , TypeDefKind , TypeId , TypeOwner , WorldId ,
@@ -813,15 +814,48 @@ impl WorldGenerator for CSharp {
813814 ) ;
814815 }
815816
816- // Embed component-type metadata as a wasm object file with a
817- // `component-type:<world>` custom section and a linking symbol.
818- // The symbol is force-linked via a `--undefined` linker arg in the
819- // generated csproj so the object is retained after GC, which makes
820- // the custom section available to `wasm-component-ld` for
821- // component synthesis. This path is independent of the bundled
822- // `wasm-component-ld`'s WIT parser and therefore works for WIT
823- // features (e.g. `map`) that the bundled version does not yet
824- // understand when fed a textual or binary WIT package.
817+ // For the time being, we generate both a .wit file and a .o file to
818+ // represent the component type. Newer releases of the .NET runtime
819+ // will be able to use the former, but older ones will need the
820+ // latter.
821+ //
822+ // TODO: stop generating the .o file once a new-enough release is
823+ // available for us to test using only the .wit file.
824+
825+ {
826+ // When generating a WIT file, we first round-trip through the
827+ // binary encoding. This has the effect of flattening any
828+ // `include`d worlds into the specified world and excluding
829+ // unrelated worlds, ensuring the output WIT contains no extra
830+ // information beyond what the binary representation contains.
831+ //
832+ // This is important because including more than one world in
833+ // the output would make it ambigious, and since this file is
834+ // intended to be used non-interactively at link time, the
835+ // linker will have no additional information to resolve such
836+ // ambiguity.
837+ let ( resolve, world) = wit_parser:: decoding:: decode_world (
838+ & wit_component:: metadata:: encode ( resolve, id, self . opts . string_encoding , None ) ?,
839+ ) ?;
840+ let pkg = resolve. worlds [ world] . package . unwrap ( ) ;
841+
842+ let mut printer = WitPrinter :: default ( ) ;
843+ printer. emit_docs ( false ) ;
844+ printer. print (
845+ & resolve,
846+ pkg,
847+ & resolve
848+ . packages
849+ . iter ( )
850+ . filter_map ( |( id, _) | if id == pkg { None } else { Some ( id) } )
851+ . collect :: < Vec < _ > > ( ) ,
852+ ) ?;
853+ files. push (
854+ & format ! ( "{world_namespace}_component_type.wit" ) ,
855+ String :: from ( printer. output ) . as_bytes ( ) ,
856+ ) ;
857+ }
858+
825859 files. push (
826860 & format ! ( "{world_namespace}_component_type.o" ) ,
827861 wit_bindgen_c:: component_type_object:: object (
0 commit comments