locked
C++ - C# interop grief

    Question

  • I created a simple class to help having meaningful exception, it looks like that

    	public enum class ErrorCodes
    	{
    		CodeStart = 0x0200, CodeEnd = CodeStart + 100, NotErrorCode = CodeEnd - 1,
    		StupideError1 = CodeStart + 1,
    		StupideError2 = CodeStart + 2,
    	};
    
    	public ref class Class1 sealed
    	{
    	private:
    		Class1() {}
    
    	public:
    		static void Throw(ErrorCodes c);
    		static ErrorCodes GetCode(Platform::Exception^ ex);
    	};
    

    However, when I try to use it in C#, with code like that

    			try
    			{
    				Class1.Throw(ErrorCodes.StupideError1);
    			}
    			catch (Exception ex)
    			{
    				var c = Class1.GetCode(ex);
    			}
    

    I got the following compiler error in my C# project:

    2>C:\Dev\W8\App1\App1\App.xaml.cs(42,5,42,8): error CS0012: The type 'Platform.Exception' is defined in an assembly that is not referenced. You must add a reference to assembly 'platform, Version=255.255.255.255, Culture=neutral, PublicKeyToken=null, ContentType=WindowsRuntime'.
    2>C:\Dev\W8\App1\App1\App.xaml.cs(42,13,42,31): error CS1502: The best overloaded method match for 'CppComp.Class1.GetCode(Platform.Exception)' has some invalid arguments
    2>C:\Dev\W8\App1\App1\App.xaml.cs(42,28,42,30): error CS1503: Argument 1: cannot convert from 'System.Exception' to 'Platform.Exception'

    How could I fix that?

    Wednesday, December 05, 2012 3:36 PM

Answers

All replies

  • I worked around the problem by not exposing Platform::Exception (taking the HRESULT as argument instead).

    If I add platform.winmd (from C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\vcpackages)

    I got a huge amount of senseless compiler error suddenly appearing in my C# project like only C++ project will usually give!

    • Marked as answer by Lloyd Wednesday, December 05, 2012 4:26 PM
    • Unmarked as answer by Lloyd Wednesday, December 05, 2012 4:26 PM
    Wednesday, December 05, 2012 4:26 PM
  • Hi,

    As far as I know, the C++/CX throw error is COM error. Would you please provide us the whole codes to reproduce this issue?

    There is no realization of Throw and ErrorCodes function.

    Best regards,
    Jesse


    Jesse Jiang
    MSDN Community Support | Feedback to us
    Develop and promote your apps in Windows Store
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    Friday, December 07, 2012 8:26 AM
  • I don't quite understand the question.. and I moved on!

    But to restate the problem, it's about consuming a C++ component in C#

    The code below will work fine

    	public enum class ErrorCodes
    	{
    		CodeStart = 0x0200, CodeEnd = CodeStart + 100, NotErrorCode = CodeEnd - 1,
    		StupideError1 = CodeStart + 1,
    		StupideError2 = CodeStart + 2,
    	};
    
    	public ref class Class1 sealed
    	{
    	private:
    		Class1();
    
    	public:
    		static void Throw(ErrorCodes c);
    		static ErrorCodes GetCode(int exHResult);
    
    	internal:
    		static ErrorCodes GetCode(Platform::Exception^ ex);
    	};

    But if I make the last method (ErrorCodes GetCode(Platform::Exception^ ex))
    public instead of internal, I got the following compile error in my C# project

    error CS0012: The type 'Platform.Exception' is defined in an assembly that is not referenced. You must add a reference to assembly 'platform, Version=255.255.255.255, Culture=neutral, PublicKeyToken=null, ContentType=WindowsRuntime'.

    If I add the reference to platform.winmd to my C# project
    from (C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\vcpackages)

    Then I'm starting to have humonguous compiler errors!


    • Edited by Lloyd Friday, December 07, 2012 9:32 AM
    Friday, December 07, 2012 9:32 AM
  • Hi lloyd,

    You're getting close. The WinRT/C# mapping is Windows::Foundation::HResult to System.Exception.

    See http://msdn.microsoft.com/en-us/magazine/jj651569.aspx and http://msdn.microsoft.com/en-us/library/windows/apps/windows.foundation.hresult.aspx

    So, this is probably what you want for your original code snippet:

    public enum class ErrorCodes
    {
    	CodeStart = 0x0200, 
    	CodeEnd = CodeStart + 100, 
    	NotErrorCode = CodeEnd - 1,
    	StupideError1 = CodeStart + 1,
    	StupideError2 = CodeStart + 2,
    };
    
    public ref class Class1 sealed
    {
    private:
    	Class1();
    public:
    	static void Throw(ErrorCodes c);
    	static ErrorCodes GetCode(Windows::Foundation::HResult ex);
    };

    -Steve

    Saturday, December 15, 2012 2:17 AM
    Moderator
  • Awesome, thanks for the info! :)
    Saturday, December 15, 2012 3:47 AM