Вызов C # из C ++, трудности с "." в пространстве имен C # - PullRequest
1 голос
/ 27 октября 2011

Во-первых, я признаю, что я немного прикован к грузу - мой хороший чистый пример кода не работает, когда я вклиниваю его в реальный мир. Как говорится ...

У меня есть DLL с именем CPierce.CSharpCall.dll, в которой есть что-то вроде следующего C #:

namespace CPierce.CSharpBridge
{
    [System.Runtime.InteropServices.Guid("3D08DF02-EFBA-4A65-AD84-B08ADEADBEEF")]
    public interface ICSide
    {
        // interface definition omitted...
    }
    [System.Runtime.InteropServices.Guid("CBC04D81-398B-4B03-A3D1-C6D5DEADBEEF")]
    public partial class CSide : ICSide
    {
        // class definition omitted...
    }
}

Это зарегистрировано regasm /tlb и т. Д. Затем мой код C ++ выглядит примерно так:

#import "CPierce.CSharpCall.tlb" named_guids

    // Contains syntax errors!
int myfunc()
{
    HRESULT hRes = S_OK;
    CoInitialize(NULL);
    CPierce.CSharpBridge::ICSide *pManagedInterface = NULL;

    hRes = CoCreateInstance(
            CPierce.CSharpBridge::CLSID_Class1, 
            NULL, CLSCTX_INPROC_SERVER, 
            CPierce.CSharpBridge::ICSide, 
            reinterpret_cast<void**> (&pManagedInterface));

    // Calls to the interface omitted....

    CoUninitialize();
    return 0;
}

Проблема, конечно, в синтаксически неправильном бите около CPierce.CSharpBridge. Я знаю в C ++, хочу ли я иметь пространство имен, подобное коду C #, я мог бы сказать:

namespace CPierce
{
    namespace CSharpBridge
    {
        // definitions go here
    }
}

Но я не думаю, что это то, что я ищу здесь, поскольку мне просто нужно сослаться на две константы, которые находятся в другом пространстве имен, не помещая весь метод в это пространство имен.

Что такое синтаксис C ++, который мне нужен для завершения этого вызова CoCreateInstance?


Обновление: при более глубоком (гораздо более глубоком) осмотре я обнаружил, что мой файл .tlb, созданный программой regasm, почти пуст. Когда я собрал все мои исходники в один файл .cs и скомпилировал с:

csc /debug /t:library BigFile.cs 
regasm BigFile.dll /tlb:BigFile.tlb

Я получаю здоровенный (и полезный) файл tlb.

Когда я компилирую весь проект из Visual Studio, я получаю .DLL нормально, но regasm ничего с этим не делает, а создает минимальный файл .tlb. (ildasm почти не показывает различий между двумя DLL)

Если я компилирую BigFile.cs в Visual Studio, я получаю DLL, которая также бесполезна.

Я в тупике.

Ответы [ 2 ]

3 голосов
/ 27 октября 2011

C ++ не использует оператор . для разделения пространств имен; он использует ::. Вы бы использовали CPierce::CSharpBridge вместо CPierce.CSharpBridge. К сожалению, это не помогает вам, потому что вы не знаете, какое пространство имен на самом деле генерируется TLB.

Простое решение для этого состоит в том, чтобы вообще не использовать пространства имен и импортировать без них:

#import "CPierce.CSharpCall.tlb" named_guids no_namespace
0 голосов
/ 27 октября 2011

Это кажется проблемой на стороне C # / Visual Studio. Я оставлю этот вопрос и открою соответствующий. Спасибо за вашу помощь в сужении.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...