title: Using C++ COM interface in C# for both client and server
body: <p>I need to make a piece of C# code interact through COM with all kinds of implementations.</p>
  
  <p>To make it easeier for users of that integration, I included the interacted interfaces in IDL (as part of a relevant existing DLL, but without coclass or implementation), then got that into my C# code by running Tlbimp to create the types definition.</p>
  
  <p>I implemented my C#, creating COM objects based on Windows registry info and casting the object into the interface I need.</p>
  
  <p>I then created a C# implementation of the interface in a seperate project and registered it.
  The main program creates the testing COM object correctly but fails to cast it into the interface (gets a null object when using C# 'as', gets an InvalidCastException of explicit cast).</p>
  
  <p>Can someone suggest why the interface is not identified as implemented by the testing object?</p>
  
  <p>This is the interface defition in IDL (compiled in C++ in VS 2005):</p>
  
  <pre><code>    [
      object,
      uuid(B60C546F-EE91-48a2-A352-CFC36E613CB7),
      dual,
      nonextensible,
      helpstring("IScriptGenerator Interface"),
      pointer_default(unique)
  ]
  interface IScriptGenerator : IDispatch{
  
      [helpstring("Init the Script generator")] 
          HRESULT Init();
      [helpstring("General purpose error reporting")] 
          HRESULT GetLastError([out] BSTR *Error);
  };
  </code></pre>
  
  <p>This is the stub created for C# by Tlbimp:</p>
  
  <pre><code>[TypeLibType(4288)]
  [Guid("B60C546F-EE91-48A2-A352-CFC36E613CB7")]
    public interface IScriptGenerator
    {
      [DispId(1610743813)]
      void GetLastError(out string Error);
      [DispId(1610743808)]
      void Init();
    }
  </code></pre>
  
  <p>This is part of the main C# code, creating a COM object by its ProgID and casting it to the IScriptGenerator interface:</p>
  
  <pre><code>public ScriptGenerator(string GUID)
  {
    Type comType = Type.GetTypeFromProgID(GUID);
    object comObj = null;
    if (comType != null)
    {
      try
      {
        comObj = Activator.CreateInstance(comType);
      }
      catch (Exception ex)
      {
        Debug.Fail("Cannot create the script generator COM object due to the following exception: " + ex, ex.Message + "\n" + ex.StackTrace);
        throw ex;
      }
    }
    else
      throw new ArgumentException("The GUID does not match a registetred COM object", "GUID");
  
    m_internalGenerator = comObj as IScriptGenerator;
    if (m_internalGenerator == null)
    {
      Debug.Fail("The script generator doesn't support the required interface - IScriptGenerator");
      throw new InvalidCastException("The script generator with the GUID " + GUID + " doesn't support the required interface - IScriptGenerator");
    }
  
  }
  </code></pre>
  
  <p>And this is the implementing C# code, to test it's working (and it's not):</p>
  
  <pre><code>  [Guid("EB46E31F-0961-4179-8A56-3895DDF2884E"),
    ProgId("ScriptGeneratorExample.ScriptGenerator"),
    ClassInterface(ClassInterfaceType.None),
    ComSourceInterfaces(typeof(SOAAPIOLELib.IScriptGeneratorCallback))]
    public class ScriptGenerator : IScriptGenerator
    {
     public void GetLastError(out string Error)
      {
        throw new NotImplementedException();
      }
      public void Init()
      {
        // nothing to do
      }
    }
  </code></pre>