Связывание неуправляемой библиотеки DLL C ++ с управляемой библиотекой библиотеки классов C ++ - PullRequest
8 голосов
/ 23 октября 2010

Как и в вопросе Создание простой оболочки c ++. Net.Шаг за шагом

Я пытаюсь использовать классы C ++ в .NET, но у меня возникают проблемы при сборке в Visual Studio (2008).

У меня есть неуправляемый класс A (C ++ скомпилирован с / clr).Я создал класс C ++ / clr 'Class1', который оборачивает A и с соответствующими делегатами методов для методов A.

Если я включаю исходный файл модуля класса A в проект библиотеки классов для Class1 (управляемый), у меня нет проблемвсе связывает и работает нормально, но у меня есть много неуправляемых классов C ++, таких как A, и я стараюсь поместить их в DLL и связать эту DLL с управляемой библиотекой (оберток классов).[На самом деле я не вижу необходимости связывать эти DLL вместе, но компилятор, похоже, требует этого, выдавая те же ошибки, что показаны ниже.]

Я создал библиотеку VisualC ++ / CLR / Class идобавил мой класс C ++ (указан ниже) и собрал.[Я использовал настройки по умолчанию, но в настройках компоновщика проекта я пробовал как зарегистрировать вывод с да и нет.] Не было ошибок, и был создан файл .DLL.

Я создал VisualC ++ / CLR / ClassБиблиотека и созданный класс оболочки 'Class1' Я использовал все настройки по умолчанию.В свойствах проекта я нажал «Ссылки», «Добавить новую ссылку» и выбрал DLL, созданную на первом шаге.

Я получаю ошибки компоновщика:

test_NET_library.obj : error LNK2028: unresolved token (0A000009) "public: int __thiscall Z::A::m1(int,int)" (?m1@A@Z@@$$FQAEHHH@Z) referenced in function "public: int __clrcall test_NET_library::Class1::m1(int,int)" (?m1@Class1@test_NET_library@@$$FQ$AAMHHH@Z)
test_NET_library.obj : error LNK2028: unresolved token (0A00000A) "public: int __thiscall Z::A::m2(int,int)" (?m2@A@Z@@$$FQAEHHH@Z) referenced in function "public: int __clrcall test_NET_library::Class1::m2(int,int)" (?m2@Class1@test_NET_library@@$$FQ$AAMHHH@Z)
test_NET_library.obj : error LNK2019: unresolved external symbol "public: int __thiscall Z::A::m1(int,int)" (?m1@A@Z@@$$FQAEHHH@Z) referenced in function "public: int __clrcall test_NET_library::Class1::m1(int,int)" (?m1@Class1@test_NET_library@@$$FQ$AAMHHH@Z)
test_NET_library.obj : error LNK2019: unresolved external symbol "public: int __thiscall Z::A::m2(int,int)" (?m2@A@Z@@$$FQAEHHH@Z) referenced in function "public: int __clrcall test_NET_library::Class1::m2(int,int)" (?m2@Class1@test_NET_library@@$$FQ$AAMHHH@Z)
C:\temp\test_Cpp_CLI\test_NET_library\Debug\test_NET_library.dll : fatal error LNK1120: 4 unresolved externals

Те же ошибки, что и при удаленииA.cpp в проекте библиотеки классов-оболочек (опция, которая работает). Я не понимаю, почему сборка пытается разрешить внешние проблемы, потому что это библиотека, а не программа.

Есть что-то еще, что мне нужно добавить в свойства проекта библиотеки классов-оболочек или зарегистрировать DLL неуправляемых классов или параметры компилятора? Мне также нужен файл .lib для работы с DLL? (файл lib не появляется в целевом каталоге проектов)

Нужно ли мне по-прежнему использовать __declspec (dllexport) [считалось, что это было только для функций стиля C, а не для членов класса.] Как в вопросе: Экспорт неуправляемых классов из DLL-библиотеки Visual C ++? даже при том, что неуправляемая библиотека C ++ скомпилирована с включенным CLR.

(я также пробовал компилировать как статическую библиотеку, но не могупонять, как добавить файл .lib в проект библиотеки классов CLR).

Мой тестовый класс -

namespace Z 
{
class A
{
public:

   int m1(int p1, int p2);
   int m2(int p3, int p4);
};
};

с реализацией:

#include "A.h"
namespace Z 
{
int A::m1(int p1, int p2) { return p1+p2; };
int A::m2(int p3, int p4) { return p3 * p4; };
};

Икласс-оболочка

#pragma once
#include "../A.h"
using namespace System;
namespace test_NET_library {
 public ref class Class1
 {
 private: Z::A *a;
 public: Class1()
  : a(new Z::A)
   {}
 public: inline int m1(int p1, int p2)
  {  return a->m1(p1,p2);
  };
 public: inline int m2(int p3, int p4)
  {return a->m2(p3,p4);
  };
 };
}

В соответствии с вопросом: Создание DLL в смешанном режиме C ++ / CLI Я также пробовал:

#pragma managed(push, off) 
#include "../A.h"
#pragma managed(pop)

А также это нажатие удалосьвокруг A.cpp.

Обновление: согласно ответу mcdave, я удалил / clr, это произвело DLL, теперь, как мне сделать эту DLL доступной для моей test_NET_library?

Я попробовал References / Add New Reference и выбрал новую эту новую DLL;и получил сообщение «Не удалось добавить ссылку на файл« C: .. \ unmanaged_lib.dll », поскольку он не является сборкой .NET или зарегистрированным элементом управления ActiveX».DLL была добавлена ​​в список файлов проекта, но компилятор, похоже, игнорирует ее.

Я попытался добавить / создать элемент и выбрал новую DLL.но файлы .DLL не доступны для выбора.

1 Ответ

6 голосов
/ 07 ноября 2010

С несколькими подсказками из вашего обновления я попробую два предположения ...

  1. Когда unmanaged_lib является статически связанной библиотекой, вы установили для проекта unmanaged_lib зависимость test_NET_library?(В окне Project Explorer щелкните правой кнопкой мыши test_NET_library, выберите «Зависимости проекта ...» и выберите unmanaged_lib.)
  2. Если unmanaged_lib - это DLL, вам нужно экспортировать класс из DLL, выполнив следующую команду этот ответ, а также зависимость test_NET_library от проекта unmanaged_lib.
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...