No-std Windows DLL linker error

I am trying to write a Windows DLL in Rust which will be later relocated to an environment without access to the operating system.

So I wrote 3 rlibs (all no_std):

  • A -sys crate providing the generated bindings to the C functions I will have access to from the DLL after it is relocated
  • A -env crate providing a memcpy/memmove/memset and a memcmp function using the -sys-bindings as well as an global allocator
  • A -lib crate providing a saver wrapper around the -sys crate, importing the -env crate and providing generic library functionality by exporting symbols of libcore and liballoc

These Libraries do compile, but if I am trying to build a cdylib-crate (no_std of course) using the -lib crate I get a linker error regarding 4 not resolved symbols:

  • “_DllMainCrtStartup” - is this one not automatically defined with no_std? The error disappears if I define it manually in the DLL, although it will never be used
  • “__umodti3” in “ZN4core3fmt3num53$LT$impl$u20$core…fmt…Display$u20$for$u20$i128$GT$3fmt17hae8aafde5f70b339E”
  • “__udivti3” in “ZN4core3fmt3num53$LT$impl$u20$core…fmt…Display$u20$for$u20$i128$GT$3fmt17hae8aafde5f70b339E”
  • and “__CxxFrameHandler3” multiple times from all over the place

I am not sure where these symbols are referenced and why :frowning: I hope someone can help me with that…

Finally, I have successfully compiled the dll, although with some workarounds…

I have defined the “_DllMainCrtStartup" function and exported it as an starting point which will never be used. Visual Studio defines this automatically if you don’t define it by yourself, but i can live with that.

The “__CxxFrameHandler3" was a bit more tricky. It’s part of the unwinding-handling and even if you compile with panic=“abort”, cargo will use the precompiled binaries of libcore which use unwinding. Iiballoc seems to use these symbol even if you compile as release… Only way around this is using xargo instead of cargo and recompile these libraries too.
I think this is a bit strange. [no_std] seems basically useless if you use cargo.

The most strange part are “__umodti3" and “__udivti3". It seems like they are used in the Implementation of Display for i128, but I have not activated the i128 language feature. For now I just defined them by hand and hope they get never called…

I think you can knock out the missing math symbols by depending on the compiler_builtins crate.

1 Like

Thanks, this helped a lot. Didn’t know about the compiler_builtins crate before. The “__umodti3” and “__udivti3” symbols are resolved now :slight_smile: