Вопрос

Я работаю над программой на C++, и скомпилированный объектный код из одного файла из 1200 строк (который инициализирует довольно сложный конечный автомат) занимает почти мегабайт.Что может сделать файл таким большим?Есть ли способ найти то, что занимает место внутри объектного файла?

Это было полезно?

Решение

Может быть несколько причин, по которым объектные файлы больше, чем должны быть как минимум:

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

Сначала я предлагаю проверить, используете ли вы отладочную информацию, это вызывает наибольшее раздувание, по моему опыту.

Другие советы

(я предполагаю, что у вас есть оптимизация и отключение мертвого кода).

Включите & вашего линкера; сгенерируйте файл карты " вариант и проверить вывод.

Распространенными виновниками являются макросы / шаблоны, которые генерируют большие объемы кода и большие глобальные объекты.

Возможно, некоторые экземпляры шаблона (особенно std::iostream) и, возможно, обширное встраивание (то есть классы, которые полностью определены в заголовке). Однако в чем проблема с 1-мегабайтным объектным файлом? Во время связывания это может привести к крошечному двоичному файлу. У меня здесь есть проект с 20 МБ объектных файлов, который, например, связан в двоичный файл 700 КБ.

Обновление: может быть также некоторый большой статический массив / объект. Кроме того, с помощью MSVC ++ и GCC вы можете посмотреть на сгенерированную сборку для файла, который может дать вам несколько советов (с GCC это g++ -S foo.cpp, для MSVC ++ это '/ FAs ). Либо вы увидите много экземпляров шаблона, но это и есть причина. Если нет, то это размер объекта static объектов.

Другой возможной причиной является Link-Time Code Generation, опция VC ++. Это перемещает серверную часть компилятора в компоновщик. Это обеспечивает лучшую оптимизацию, но теперь объектный файл должен содержать все внутренние структуры данных, обычно передаваемые между front- и backend.

Вот макрос, который я использую для просмотра значений времени компиляции:

template <size_t N> struct compile_time_number { private: typedef int check; };
#define compiler_check_number(N) ((compile_time_number< N >::check)0)

Тогда радуйтесь во время компиляции, чтобы увидеть, какие символы занимают место.

Изменить. Поскольку, похоже, никто этого не понимает, поясню: способ использовать это - добавить compiler_check_number(sizeof(<insert struct or global variable here>)). Компилятор выдаст размер переменной или структуры как ошибку времени компиляции. Очень редко код является причиной огромного объектного файла.

Я использую это все время, чтобы увидеть, насколько большие вещи без необходимости запуска отладчика.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top