Смешивание 32-битных и 64-битных P / вызывает - PullRequest
7 голосов
/ 09 декабря 2010

Я столкнулся с проблемой, на которую я почти уверен, что знаю ответ, но я решил по крайней мере спросить и посмотреть, есть ли какая-нибудь «волшебная пуля», которая может избавить меня от огромной головной боли.

Вот высокоуровневое представление.

У меня есть управляемое приложение. Это приложение взаимодействует с оборудованием через сторонние библиотеки разных производителей. У меня есть полный контроль над управляемым приложением-потребителем и нулевой контроль над библиотеками аппаратного API.

Поставщик A предоставляет только 32-битный собственный SDK. Чтобы мы могли использовать его в 64-битных системах, мы пометили приложение для запуска в 32-битном режиме. Все было хорошо.

Сейчас мы интегрируемся с поставщиком B, который предоставляет 64-битные библиотеки API-интерфейсов для 64-битных машин. 32-разрядная библиотека DLL от поставщика B не будет работать в 64-разрядной системе (пробовал это). Если я создаю тестовый жгут под управлением 64-битной или AnyCPU, он работает нормально. Если я отмечу его как 32-битный, он не будет работать при вызовах P / Invoke.

Похоже, что аппаратные средства Vendor A и Vendor B будут взаимоисключающими на 64-битных ПК, но мне интересно, есть ли у кого-нибудь предложения о том, как обойти это.

Ответы [ 4 ]

6 голосов
/ 09 декабря 2010

Проблема не в .NET или P / Invoke. Это проблема ОС. 64-разрядный процесс может загружать только 64-разрядные библиотеки DLL. 32-разрядный процесс может загружать только 32-разрядные библиотеки DLL. Между процессом пользовательского режима (EXE и DLL) и ядром существует волшебный слой Windows-on-Windows (или WoW), который позволяет 32-битным приложениям работать в 64-битной Windows. Невозможно запустить 32-битную DLL внутри 64-битного процесса. Слой WoW существует ниже этого. (По сути, WoW - это 32-битная оболочка для 64-битного Win32 API, которая объединяет вызовы данных и функций между 32-битным миром процесса и 64-битным миром операционной системы.)

Ваш лучший / единственный вариант - запускать 32-разрядные и 64-разрядные компоненты в отдельных процессах и использовать для связи некоторую форму IPC. Это дает дополнительное преимущество, заключающееся в отделении вашего основного приложения от потенциально нестабильных сторонних компонентов. Если сторонний компонент дает сбой или ведет себя неправильно, это просто вопрос перезапуска процесса, содержащего этот компонент.

1 голос
/ 09 декабря 2010

Поскольку вы не можете загрузить 32-битные и 64-битные изображения в один и тот же процесс, вам придется использовать многопроцессное решение.

1 голос
/ 09 декабря 2010

Вы можете создать отдельный 32-разрядный процесс для взаимодействия с поставщиком А, а затем связаться с ним с помощью WCF.

0 голосов
/ 09 декабря 2010

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

...