«Была предпринята попытка загрузить программу с неверным форматом», даже если платформы одинаковы

461

Я вызываю функции из 32-разрядной неуправляемой библиотеки DLL в 64-разрядной системе. Что я получаю это:

BadImageFormatException: была предпринята попытка загрузить программу с неверным форматом. (Исключение из HRESULT: 0x8007000B)

Сначала мои проекты были настроены на платформу Any CPU, поэтому я изменил их оба на x86, но эта ошибка все еще происходит. Это действительно единственное исправление, которое я знаю для этого.

DLL не повреждены или что-то еще, потому что я могу использовать их с другими программами (для которых у меня нет источника). Я подумал, что, возможно, он не нашел зависимости, но я проверил, и все они там. Плюс, не бросит ли это DllNotFoundExceptionв этом случае?

Что еще я могу сделать? И прежде чем вы скажете: «Вместо этого используйте 64-разрядную неуправляемую DLL», позвольте мне отметить, что ее нет. ;)

Дэвид Браун
источник
1
Какие проекты вы поменяли на x86? И как вы их выполняете, когда получаете исключение, через отладчик или вручную? Если последнее, вы заметили, что при переходе на x86, вы получили новую папку в каталоге bin \? В основном это bin \ x86 \ Debug для файлов.
Лассе В. Карлсен
Можете ли вы проверить, что исполняемый файл работает в 32-битном режиме (* 32 в диспетчере процессов)?
JP Alioto
@Lasse V. Karlsen: Да, я удалил бит x86 из пути вывода, когда менял платформу в каждом проекте. Мой первый проект - это DLL, которая оборачивает функции в неуправляемую DLL. Второй проект - это исполняемый файл, который использует обертку в первой DLL. Оба установлены на x86.
Дэвид Браун
@JP: На самом деле, менеджер процессов не показывает, что он работает как 32-битный процесс. Это почему?
Дэвид Браун

Ответы:

532

Если вы попытаетесь запустить 32-разрядные приложения на IIS 7 (и / или на компьютере с 64-разрядной ОС), вы получите ту же ошибку. Итак, в IIS 7 щелкните правой кнопкой мыши пул приложений приложений и перейдите в раздел «Дополнительные параметры» и измените «Включить 32-разрядные приложения» на «ИСТИНА».

Перезапустите ваш сайт, и он должен работать.

введите описание изображения здесь

bluwater2001
источник
1
О, мои дни я ловил рыбу вокруг установки дополнительных компонентов IIS, когда это был ответ ... Кто-нибудь может предложить обратную сторону выбора этой опции?
notidaho
3
Вот хорошее обсуждение вопроса производительности относительно этого: stackoverflow.com/questions/507820/…
Бен Пауэр
У меня проблема с SharpSvn, и это не помогает. :( Sth очень неправильно с этой сборкой, я говорю вам ...
user2173353
4
Этот ответ для меня лишний, потому что в вопросе IIS вообще не упоминается!
Кристианп
129

Каким-то образом флажок Build в Configuration Manager был снят для моего исполняемого файла, поэтому он все еще работал со старой сборкой Any CPU. После того, как я это исправил, Visual Studio пожаловалась, что не может отладить сборку, но это было исправлено путем перезапуска.

Дэвид Браун
источник
Большое спасибо. Это тоже меня достало. Проверил сборку в Configuration Manager и теперь она работает (настольное приложение WPF).
danglund
1
Если вы выполнили все вышеперечисленное и проверили настройки своей платформы, соберите параметры конфигурации, очистили решение, и оно все еще не работает - найдите все экземпляры DLL и удалите их.
Уилл Колдервуд
с VS 2015 это все еще действует - хотя мне не нужно было перезапускать :)
increddibelly
Это оно! Повторное посещение настроек Configuration Manager является ответом.
AndyUK
74

В Visual Studio щелкните правой кнопкой мыши свой проект -> На левой панели перейдите на вкладку Build ,

Свойства проекта, вкладка сборки

в разделе Platform Target выберите x86 (или, в более общем случае, архитектуру, соответствующую библиотеке, на которую вы ссылаетесь)

Свойства проекта, цель платформы

Я надеюсь, что это помогает кому-то! :)

Марвин Тобеджане
источник
2
Это исправило мою проблему в VS2013, я нашел альтернативное решение - оставить «Цель платформы» как «Любой процессор», но установить флажок «Предпочитать 32-разрядный».
user1069816
2
Хотя вам нужно использовать .NET 4.5 или выше, чтобы иметь возможность установить флажок «Предпочитать 32-разрядную
версию»
1
Да, но я преобразовал свой проект в «Любой процессор» в «x64». Мой 32-битный проект работает нормально, но тот же код, который я преобразовал в 64-битный, этот проект не работает нормально, как 32-битный. Можете ли вы дать мне правильный 64-битный процесс преобразования ...
Исмаил С.
@IsmayilS убедитесь, что вы используете 64-битную версию библиотеки, на которую вы
ссылаетесь
53

У меня тоже была эта проблема. Перепробовал все предложения здесь, но они не помогли.

Я нашел другую вещь, чтобы проверить, что исправило это для меня. В Visual Studio щелкните правой кнопкой мыши проект и откройте «Свойства». Нажмите на вкладку «Компиляция» (или «Сборка»), а затем нажмите «Дополнительные параметры компиляции» внизу.

Проверьте выпадающий список «Target CPU». Он должен соответствовать «Платформе», которую вы строите. То есть, если вы создаете «Любой процессор», тогда «Целевой процессор» должен сказать «Любой процессор». Просмотрите все свои платформы, сделав их активными, и проверьте этот параметр.

Денис
источник
2
И для тех из нас, кто только использовал компилятор, мое исправление заключалось в добавлении "/ platform: x86" к флагам компилятора.
Urchin
Это исправило это и для меня. Мне пришлось настроить «цель платформы» на вкладке «Сборка».
Йовен
если вы используете 64-битную версию, также установите флажок «предпочесть 32-битную версию». Я должен был отключить это для меня.
N4ppeL
51

Если вы столкнулись с этой ошибкой, когда нажимаете зеленую кнопку со стрелкой, чтобы запустить приложение, но по-прежнему хотите запустить приложение в 64-разрядной версии. Вы можете сделать это в VS 2013, 2015, 2017 и 2019

Перейдите: Инструменты> Параметры> Проекты и решения> Веб-проекты> Использовать 64-разрядную версию IIS Express

paibamboo
источник
3
Спасибо. Я пробовал так много, и ничего не помогло. Вы спасатель моей жизни. У меня 64-битная ОС, установлена ​​64-битная Visual Studio [которая по неизвестной причине все еще работает как 32-битная]. Когда я установил свою платформу Target в x64, она выдавала ошибку BadImageFormatException. С твоим исправлением это сработало. Я дал тебе голос. Вы рок
SKCS Камаль
Я рад, что смог помочь :)
paibamboo
Это ответ мне нужен. Большое спасибо!
yushulx
Большое спасибо, это решило проблему. Он хорошо работает с 32-разрядным процессом Visual Studio 2017.
samir105
1
все еще работает с VS 2019, спасибо
Джейк Гастон
36

Если вы используете любой ЦП , вы можете столкнуться с этой проблемой, если установлен флажок Предпочитать 32-разрядный :

Убедитесь, что вы сняли этот флажок на вкладке Build свойства проекта !

введите описание изображения здесь

Дрю Ноакс
источник
3
Было бы полезно, если бы вы могли указать, где в Visual Studio найти эту опцию.
trysis
@trysis, эта опция находится на странице Build панели настроек проекта.
Дрю Ноакс
1
Я говорил, что было бы полезно вставить это. Поскольку этот ответ стоит, нет никакого контекста, чтобы сказать несчастному, возможно новому пользователю StackOverflow, где его найти.
trysis
Каков путь для получения этой формы? Я не могу найти его
Адольфо Корреа
В Visual Studio щелкните проект правой кнопкой мыши и выберите «Свойства».
Дрю Ноакс
8

Немного не по теме для этого поста, но поиск этого сообщения об ошибке привел меня сюда.

Если вы собираете систему через систему Team и получаете эту ошибку, вкладка процесса определения сборки имеет параметр «MSBuild Platform». Если для этого параметра установлено значение «Авто», вы можете столкнуться с этой проблемой. Изменение его на «X86» также может устранить ошибку.

StingyJack
источник
это самый близкий ответ к тому, что я испытывал. У меня был dll, который должен был быть x86. Я использовал его в другом проекте, который по умолчанию был AnyCPU. Они просто должны соответствовать. В этом случае это не имело большого значения, поэтому я изменил новый проект на x86.
Грег
8

В моем случае я использовал нативную DLL в C #. Эта DLL зависела от нескольких других отсутствующих DLL. Как только эти другие библиотеки были добавлены, все работало.

Томаш Стыпич
источник
4

Опираясь на ответ @paibamboo

Он сказал: Перейти к: Инструменты> Параметры> Проекты и решения> Веб-проекты> Использовать 64-разрядную версию IIS Express

Мой коллега проверил этот флажок (он явно искал его), но имел сообщение об ошибке в вопросе. Через несколько часов он снял флажок и снова проверил. И вот, код теперь работает с успехом.

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

Вопрос для более знающих пользователей: было ли обновление или что-то на прошлой неделе (для VS 2015), которые отменили синхронизацию состояний?

MilConDoin
источник
3

Также посмотрите этот ответ , который решил ту же проблему для меня.

Написал Luis Mack 5/12/2010 в 8:50 AM Я обнаружил ту же проблему, только для конкретного проекта при компиляции на 64-битной машине. Исправление, которое SEEMS работает, состоит в том, чтобы вручную изменять один символ в потоке изображения КАЖДЫЙ РАЗ, когда пользовательский контроль или форма редактируются в конструкторе.

 AAEAAAD/////AQAAAAAAAAAMAgAAAFdTeXN0ZW0uV2luZG93cy5Gb3JtcywgVmVyc2lvbj00LjAuMC4w

Изменить на

 AAEAAAD/////AQAAAAAAAAAMAgAAAFdTeXN0ZW0uV2luZG93cy5Gb3JtcywgVmVyc2lvbj0yLjAuMC4w

То есть 00LjAuMC4w обратно в 0yLjAuMC4w в конце строки (00 назад в 0y)

Шауль Бер
источник
1
Краткое резюме ссылки будет полезно @Shaul :)
Марвин Thobejane
Великолепный. Спасибо, брифинг добавляет содержание к вашему комментарию
Марвин Тобеджейн
2

В моем случае я использую крошечный .exe, который перезагружает ссылочные библиотеки DLL через Reflection. Так что я просто делаю эти шаги, которые спасают мой день:

Из свойств проекта в обозревателе решений на вкладке «Сборка» я выбираю целевой платформу от x86

asdf_enel_hak
источник
2

В моем случае я выполнял тесты через MSTest и обнаружил, что развертываю 32-битную и 64-битную DLL в каталог test. Программа отдавала предпочтение 64-битной DLL и вызывала ее сбой.

TL; DR Убедитесь, что в тестах используются только 32-битные библиотеки DLL.

Майк Клак
источник
2

У нас была похожая проблема, и нам удалось ее исправить, установив целевую платформу на x86. Свойства проекта-> построить

Джо
источник
Значит, x86-библиотеки отличаются от x64? Есть ли способ обнаружить это в указанном файле DLL?
NoBugs
@ NoBugs Похоже, вы можете. Взгляните на эту тему
Joe
1

Я решил эту проблему способом «Windows». После проверки всех моих настроек, очистки решения и его восстановления я просто закрыл решение и снова открыл его. Тогда это сработало, поэтому VS, вероятно, не избавился от некоторых вещей во время уборки. Когда логические решения не работают, я обычно обращаюсь к нелогичным (или, казалось бы, нелогичным). Windows не подводит меня. :)

user1771386
источник
1

Я смог решить эту проблему, сопоставив мою версию сборки с версией .NET на сервере.

Я дважды щелкнул .exe, чтобы посмотреть, что произойдет, и он сказал мне установить 4.5 ....

Так что я понизился до 4.0, и это сработало!

Поэтому убедитесь, что ваши версии совпадают. Он отлично работал на моем устройстве dev, но на сервере была более старая версия .NET.

Nateous
источник
1

В моем случае это было неправильное содержание файла. DLL была загружена из Интернета, но содержимое DLL было HTML-страницей: D Попробуйте проверить, является ли это двоичным файлом, если он кажется правильным DLL :)

Ludwo
источник
1

У нас была такая же проблема в ядре .NET. Решение состояло в том, чтобы загрузить 32-разрядную среду выполнения .netcore и получить цель вашего проекта.x86

В вашем csprojфайле добавьте

  <PropertyGroup>
    <PlatformTarget>x86</PlatformTarget>  
  </PropertyGroup>

  <PropertyGroup>
    <RunCommand Condition="'$(PlatformTarget)' == 'x86'">$(MSBuildProgramFiles32)\dotnet\dotnet</RunCommand>    
  </PropertyGroup>

Это использовалось для компьютера с Windows, вам нужно будет настроить пути и так далее для Linux / OSX

Самир Банянович
источник
0

Если вы импортируете неуправляемую DLL, используйте

CallingConvention = CallingConvention.Cdecl 

в вашем методе импорта DLL.

Рамкумар Шанмугам
источник
0

1: Перейдите: Инструменты> Параметры> Проекты и решения> Веб-проекты> Использовать 64-разрядную версию IIS Express 2: измените настройки ниже для проекта веб-службы. введите описание изображения здесь

Mani
источник