У нас есть 32-битное Windows-приложение, которое использует C ++ и старую добрую модель Windows-приложения. Технически возможно ли иметь один исходный код и скомпилировать его как 32- и 64-битный, скажем, путем включения переключателя компилятора или с помощью некоторых макросов?
В настоящее время я не думаю, что код будет компилироваться как 64-битное приложение, мне придется исправлять ошибки компиляции, в общем, как мне поступить, чтобы он компилировался как в 64&32-битное приложение. Что я должен иметь в виду? Какие будут проблемы? Любые комментарии и советы будут оценены.
Спасибо
Что касается «Что я должен иметь в виду? Какие будут проблемы?«Это наиболее распространенные проблемы, с которыми я столкнулся при переносе кода с 32-битного на 64-битный:
Убедитесь, что вы используете самый строгий уровень предупреждения при компиляции (/W4
на компиляторе Microsoft или -Wall -Wextra -pedantic-errors
на gcc), чтобы помочь поймать преобразования из большего типа в меньший тип.
Вот Microsoft руководство для портирования, но подходит и для других компиляторов.
Компиляторы определяют макросы в зависимости от их целевой платформы. Например, GCC определяет __i386__
а также __amd64__
и MSVC определяет _M_IX86
а также _M_X64
для 32-битной и 64-битной соответственно. Вы можете использовать эти макросы, например, в вашем препроцессоре #ifdef
заявления для направления потока компиляции.
Есть отличный источник на Предопределенные макросы компилятора C / C ++ для разных компиляторов.
Это конечно возможно, так как мы делаем это. Самая сложная часть
получение Visual Studios, настроенного для x64 (и это не совсем
это сложно). Кроме этого, нет ничего особенного, в
по крайней мере, если C ++ является наименее чистым (и даже если это
не). Точно такие же источники работают для обоих; без условий
сборник или что-то необходимое.
Самая большая проблема при портировании должна быть разной sizeof () для разных типов здесь и там. Таким образом, фрагменты кода, которые работают правильно на 32-битной, могут вызвать эффект бомбы замедленного действия на 64-битной. Например, у вас может быть такой код:
size_t sz = GetSomethingBig();
DWORD dw = (DWORD)sz;
Таким образом, 32-битные оба типа size_t и DWORD имеют одинаковый размер (4 байта). В портированной версии size_t будет иметь длину 8 байт, а DWORD все равно. Так как мы выполняем необработанный тип-тип C, ошибки компиляции не возникает. И во время выполнения все в порядке, если sz меньше 0x100000000. Все остальные значения приведут к потере данных с трудно предсказуемым эффектом.