Как мне скомпилировать boost, используя соглашение о вызовах __cdecl?
У меня есть проект, скомпилированный с использованием __cdecl
соглашение о вызовах (msvc2010) и я скомпилировали boost, используя тот же компилятор, используя настройки по умолчанию.
Проект связан с Boost, но я во время выполнения получил сообщение об утверждении, подобное этому: File: ...\boost\boost\program_options\detail\parsers.hpp Строка: 79
Ошибка проверки времени выполнения #0 - значение ESP не было должным образом сохранено при вызове функции. Это обычно является результатом вызова функции, объявленной с одним соглашением о вызовах с указателем функции, объявленным с другим соглашением о вызовах.
Есть следующие вопросы:
- какое соглашение о вызовах ускоряет сборку по умолчанию в Windows (msvc2010)
- как мне скомпилировать boost с __cdecl
- почему boost не смог предотвратить соединение с кодом с другими соглашениями о вызовах? Я понял, что boost имеет действительно умный код автоматического включения библиотеки.
Обновление № 1
Похоже, что Boost компилирует и связывает с соответствующим соглашением о вызовах, но все же во время выполнения я получаю вышеуказанную проблему. Я сделал пример приложения, используя тот же код, и он работает, но в моем приложении это не удается. Единственное отличие может быть от конфигурации проекта или включает /stdafx.h
3 ответа
Я нашел причину проблемы в одном из файлов общих свойств: <StructMemberAlignment>4Bytes</StructMemberAlignment>
Если я удалю его, код будет работать. Тем не менее, я не уверен, почему это происходит и как я могу решить эту проблему, не удаляя приведенный выше код (это требовалось другой библиотекой).
Я добавил еще один вопрос, касающийся усиления и выравнивания элементов конструкции.
Просто используйте
bjam ... **cxxflags=/Zp4**
при создании буст библиотеки.
Насколько я знаю, нет способа заставить C++ использовать соглашения о вызовах cdecl (см. MSDN Calling Convention). Вызов метода C++ просто отличается от C. Единственная возможность использовать одно из соглашений о вызовах C - это функции, которые включают статические функции класса в C++. Если вы знаете, что это так, вы можете попытаться принудительно включить параметр при сборке, добавив его во время сборки:
bjam cxxflags = / Gd...
(см. встроенные функции BBv2)
Или чтобы сделать его "постоянным", настройте user-config.jam с вашим компилятором и добавьте его в параметры сборки для всех сборок BBv2 msvc (см. Конфигурация BBv2 и соответствующие документы). Что касается вас, другие вопросы:
- Boost использует соглашение о вызовах по умолчанию, используемое MSVC, за исключением случаев, когда оно переопределяет его на уровне кода. Я не знаю, где они, так как они специфичны для конкретной библиотеки. Поэтому вам придется искать код для "__*" декораторов кода.
- Смотрите выше для частичного ответа.
- Обнаружение; Есть две причины: существует ограничение на количество различных вариантов, которые мы можем разумно определить для строительства, поскольку это экспоненциальный рост различных возможных вариантов, поэтому мы ограничиваем его наиболее важными случаями. А в случае соглашения о вызовах это на самом деле невозможно, поскольку это то, что можно изменить для каждой функции.