У меня есть приложение (CLI), которое ссылается на смешанную DLL. DLL реализует класс "ref" со статическими функциями.

Вот (частичный) код для ref-класса

public ref class AAA
{
public:
static bool Write(System::String^ sz);

// Not accessible!!!
public: static BOOL TraceRect(const CRect& rc);
};

В EXE в коде C++ я пытаюсь вызвать обе функции:

// This works
AAA::Write("hello");

// This doesn't !!!
CRect rc(0, 0, 12, 234);
AAA::TraceRect(rc);

Как я могу получить доступ ко второй функции?

2
Seb 11 Апр 2011 в 19:09
1
Это не похоже на C++ для меня.
 – 
John Dibling
11 Апр 2011 в 19:12
1
Добавлен тег c++-cli, так как это поможет вам больше.
 – 
Xeo
11 Апр 2011 в 19:14
Просто дикая догадка, но вы поместили неуправляемые типы данных в статический метод для управляемого класса. Кроме того, «const» не поддерживается CLR, поэтому я не уверен, как он будет интерпретировать его при компиляции класса в IL. Я бы разделил ваши общедоступные неуправляемые статические методы в отдельное место, а не пытался поместить их в управляемый класс.
 – 
Dan Bryant
11 Апр 2011 в 19:18
Дайте определение «не работает». Ошибка компиляции? Ошибка выполнения? Пожалуйста, покажите сообщение об ошибке и укажите, в какой строке кода она возникла.
 – 
Ben Voigt
11 Апр 2011 в 19:38
1
@Себ; Код, выполняющий вызов, скомпилирован с помощью /clr, верно? А не с #pragma unmanaged (или эквивалентом)? Я думаю, у вас проблемы с идентификацией, поскольку собственные классы должны быть скомпилированы в ссылки типа MSIL, чтобы их можно было использовать в методах управляемых типов, но CRect в DLL - это тип, отличный от CRect в EXE.
 – 
Ben Voigt
11 Апр 2011 в 19:50

1 ответ

Вероятно, это связано с тем, что нативные типы (в данном случае CRect) по умолчанию считаются закрытыми. Таким образом, хотя метод доступен, тип параметра для rc недоступен. Вы можете сделать его доступным с помощью make_public: http://msdn.microsoft.com/en-us/library/ms235607.aspx

Найдите C3767 и make_public, и вы найдете много другой информации по этой теме.

4
Matt Smith 11 Апр 2011 в 19:48
Хорошая идея, но она не работает. Я даже пытался изменить «CRect» на «RECT»… теперь DLL даже не связывается, я получаю LNK2022 (метаданные).
 – 
Seb
11 Апр 2011 в 20:01
Попробуйте свести это к тому, что вызывает проблему. У вас возникнет проблема, если она не принимает параметры no. Переключение между CRect и RECT на самом деле не означает попытки сделать что-то новое — они оба по-прежнему нативные типы.
 – 
Matt Smith
11 Апр 2011 в 20:32
@Seb: #pragma make_public (CRect) должно работать. Если CRect принадлежит пространству имен, его также следует записать, например NAMESPACE::CRect
 – 
ali_bahoo
12 Апр 2011 в 17:35
+1 за make_public. Иногда я забываю об этом и схожу с ума.
 – 
ali_bahoo
12 Апр 2011 в 17:38
Хорошо... Я использовал MS-Dev 2005... Попробовал это на MS-Dev 2010 и обнаружил, что все работает нормально! Когда я снова открыл свое рабочее пространство в MS-Dev 2005... это сработало! Так что я думаю, что решение было: выгрузить и перезагрузить проект ;) Спасибо всем, кто пытался помочь, это было очень ценно!
 – 
Seb
12 Апр 2011 в 18:49