4

What is, or should I ask, is there, an equivalent to DllMain when creating a DLL using C++/CLI?

Are there any restrictions on what cannot be called from this initialization code?

Daniel Trebbien
  • 38,421
  • 18
  • 121
  • 193
DanJ
  • 3,435
  • 3
  • 33
  • 44

4 Answers4

4

Dan: With respect to the loader lock, C++/CLI's delay load of the CLR and proper initialization for a mixed mode binary, I just posted yesterday on the subject here.

More or less, if you have a mixed mode binary, you must not cause any managed code to run while you are in DllMain().

Community
  • 1
  • 1
RandomNickName42
  • 5,923
  • 1
  • 36
  • 35
3

Since .NET 2.0 you have a "module initializer". See here for more information on how that solves the loader lock problem and also here

For a direct answer to your question, this page quotes the standard which says: "There are no limitations on what code is permitted in a module initializer. Module initializers are permitted to run and call both managed and unmanaged code."

Ben Voigt
  • 277,958
  • 43
  • 419
  • 720
  • 1
    The module initializer will NOT be called before the application accesses any type in the assembly. It is NOT the same as DllMain() ! – Elmue Feb 12 '15 at 14:49
  • 1
    @Elmue: You are wrong. The specification actually says that "No method other than those called directly or indirectly from the module initializer will be able to access the types, methods, or data in a module before its initializer completes execution." – Ben Voigt Sep 23 '15 at 18:17
  • 1
    No matter what the spec says. I TRIED it and I PROVED that no code in the DLL is executed before you access any managed class, function or Type in the DLL from your calling code. Please try it! Call Assembly.Load(). This is an optimization that Microsoft implemented to improve speed. – Elmue Oct 20 '15 at 11:16
  • @Elmue: Your test is invalid. The claim you tested ("The module initializer runs before `Assembly.Load()` returns") is your own theory, and is very different from the claim made in the specification. I'm not sure whether you have misunderstood the meaning of *before* or the meaning of *access the types, methods, or data*, but if you are talking about `Assembly.Load()`, you clearly don't understand what the guarantee actually means. – Ben Voigt Oct 20 '15 at 14:18
  • 1
    The question above asks for an equivalent for DllMain. If you ever programmed in C/C++ you know that code in DlllMain ALWAYS executes when LoadLibrary() executes. An equivalent for managed Assemblies would be a code that ALWAYS executes when the DLL is loaded into the process like for example the managed EXE calling Assembly.Load(). But this is not the case in the method recomended in this answer. You must first access a class or function in the Assembly DLL to invoke the execution of the module initializer. – Elmue Oct 27 '15 at 06:32
  • @Elmue: Ah, now you are correct. It does not execute when the assembly is loaded (as `DllMain` would do), it executes before any type in the assembly is accessed (which you initially denied). This is sufficient for setting up context for the other code (like calling `WSAStartup` before using any socket functions), but not so good for e.g. self-registering factory functions. – Ben Voigt Oct 27 '15 at 12:52
  • This is exactly what I said from the beginning. At the end we understand us. Yeah! – Elmue Nov 01 '15 at 13:59
  • @Elmue I believe it is what you *meant* but this whole time you have been saying something different. I think you are failing to differentiate between requesting (attempting) to access a type and the actual access. The initializer typically runs between the first request and before the actual access takes place. This "just in time" call is the latest allowed by the rule I cited. But the specification allows it to happen even earlier. – Ben Voigt Nov 01 '15 at 14:16
1

If you're using the dll in another managed project (a c# application for example), you don't need to do anything... As long as the classes you try to access are ref classes, you can access them from any other managed application.

shash
  • 965
  • 8
  • 16
0

One giant advantage of .Net dlls is that they avoid the loader lock. One side effect is that there's no DllMain.

Windows programmer
  • 7,871
  • 1
  • 22
  • 23
  • how do they avoid the loader lock? if the need to load a native dll couldn't that cause a loader lock? – DanJ Dec 13 '08 at 20:05
  • Loading a .Net dll avoids the loader lock because a .Net dll isn't a native dll. Loading a native dll would contend for the loader lock because a native dll is a native dll. – Windows programmer Dec 15 '08 at 02:38
  • These comments only apply when compiling with /clr:pure Simply /clr by itself creates a mixed library, containing both native and managed code, and the native part will have a DllMain that runs under loader lock. – Ben Voigt Feb 06 '10 at 18:39
  • Here you find more details about DLLMain and Loader Lock: http://stackoverflow.com/questions/647310/c-sharp-to-c-cli-to-c-dll-system-io-filenotfoundexception/881110#881110 – Elmue Feb 12 '15 at 15:36