locked
Exporting WinRT types from Metro DLLs

    Question

  • I have converted my Win32 DLL projects to become Metro DLL projects (using the project template). Now, I can't access any WinRT types in those DLLs from my main Metro app. I've included the DLL as a project-to-project reference and included the necessary headers. Both the app and the DLL are compiled with /ZW.

    If I try to use dllexport/dllimport like I used to for the Win32 DLLs, I get 

    Error 1 error C3387: '{ctor}' : __declspec(dllexport)/__declspec(dllimport) cannot be applied to a member of a WinRT type c:\users\matthew\projects...

    If I remove the dllexport/dllimport then I get 

    Error 2 error LNK2019: unresolved external symbol...

    What is the proper way to export these types? Or will I have to convert everything again to become WinRT Components?

    (I'm using Visual Studio 2012 RC on Windows 8 RC, the project is a DirectX3D XAML Metro App)


    • Edited by Matthew Plymale Saturday, June 16, 2012 9:51 PM add compile details
    Saturday, June 16, 2012 7:20 PM

Answers

  • For some bizarre reason, /WINMD was set to NO for all of the DLL projects, meaning none of my Metro DLLs were creating winmd files. After setting /WIMD for all DLL projects, rebuilding all of the projects, and re-adding them as references, the solution builds and the app runs as expected.

    Even more strange is that is the default for new Metro DLL projects (try it yourself, at least in the RC). Why is this the case? I had to search through the compiler option documentation to figure this out, and reason about the potential impact this will have on my build process.



    Tuesday, June 19, 2012 3:11 AM

All replies

  •  

    I think you can try to use the DLL template for metro.

     

    Best regards,

    Jesse


    Jesse Jiang [MSFT]
    MSDN Community Support | Feedback to us

    Monday, June 18, 2012 12:51 PM
  •  

    I think you can try to use the DLL template for metro.

    I did. (See the first line of my post.) Now, my DLLs contain a combination of native and WinRT types. I can export the native types, but not the WinRT types, and this is my problem. How do I deal with C3387, if I can't use dllexport like I'm used to?

    Monday, June 18, 2012 1:55 PM
  • Are you using C++/CX to author the WinRT types in your dll? If yes, you don't need to dllexport the WinRT types. As long as the types accessibility is marked as "public" they will be visible from your consuming project.

    Check the CL.exe command line switches on your consuming project. They should have a /FU:[path-to-winmd]MyDll.winmd. The winmd file contains a definition of your public WinRT types. If you don't see this switch, then try adding the Dll again as a project-to-project reference to your other project.

    Marian Luparu
    Visual C++


    Monday, June 18, 2012 11:17 PM
  • For some bizarre reason, /WINMD was set to NO for all of the DLL projects, meaning none of my Metro DLLs were creating winmd files. After setting /WIMD for all DLL projects, rebuilding all of the projects, and re-adding them as references, the solution builds and the app runs as expected.

    Even more strange is that is the default for new Metro DLL projects (try it yourself, at least in the RC). Why is this the case? I had to search through the compiler option documentation to figure this out, and reason about the potential impact this will have on my build process.



    Tuesday, June 19, 2012 3:11 AM
  • There are 2 different templates targeted for different scenarios:

    • Windows Runtime Component - this already has /ZW on the compiler and /WINMD on the linker in order to allow authoring on WinRT components
    • DLL (metro style apps) - this is targeted at existing/ported dll or new native dlls that don't use the WinRT technology but are meant to be compiled for the Metro environment (e.g. on a more restrictive SDK surface)

    Of course, these are only templates, and with changes to the project properties you can tweak their behavior. The relevant properties are:

    • C++ / General / Consume Windows Runtime Extension (/ZW) (turns on the C++/CX language extensions)
    • Linker / Windows Metadata / Generate Windows Metadata (/WINMD) (ensures that Linker will create a .winmd file)
    • Linker / General / Ignore Import Library (ensures that Linker will create a .lib file)

    Hope this helps,
    Marian

    Tuesday, June 19, 2012 3:44 AM