почему несколько проходов для сборки Linux с нуля (LFS)?

#linux #cross-compiling #linux-from-scratch

#linux #gcc #linux-с нуля

Вопрос:

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

Зачем нам нужны pass1 и pass2 отдельно? Почему мы не можем создать инструменты на этапе 1, а затем использовать их для сборки gcc , glibc , libstdc , и т. Д.

Комментарии:

1. Кстати, не только Linux с нуля — так это работает практически везде, даже если это делается вашим поставщиком ОС на их собственных официальных системах сборки. Ни один ответственный поставщик дистрибутива не будет создавать пакеты дистрибутива на любой платформе, которая не соответствует самому дистрибутиву, потому что это означает, что ваши двоичные файлы могут не воспроизводиться клиентами, использующими то, что вы создаете.

2. Это классическая ситуация с курицей и яйцом. Возможно, это также можно назвать уловкой-22. Везде, где вам нужно создать инструмент, для которого этот инструмент необходим для его сборки, вы должны его загрузить. В вашем случае вы хотите создать Linux с использованием Linux, которого у вас нет.

3. @hek2mgl нет, это не так! В тексте на LFS говорится Slightly adjusting the name of the working platform, by changing the "vendor" field target triplet by way of the LFS_TGT variable, ensures that the first build of Binutils and GCC produces a compatible cross-linker and cross-compiler. Instead of producing binaries for another architecture, the cross-linker and cross-compiler will produce binaries compatible with the current hardware. , что это не объясняет two passes gcc или binutils

4. Я отменил свой голос против. Я не хочу быть дураком, и на самом деле мне нравится, когда кто-то играет с LFS. Это круто! Но книга LFS объясняет это очень хорошо: linuxfromscratch.org/lfs/view/stable/chapter05 /…

5. спасибо всем. Теперь все более ясно.

Ответ №1:

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

Допустим, вы создаете gcc 4.1 с помощью gcc 3.2 (я собираюсь назвать этот gcc 3.2 «этапом 0»). Люди, которые проводили контроль качества для gcc 4.1, не проверяли его корректную работу при сборке с любым компилятором, отличным от gcc 4.1, — следовательно, необходимо сначала создать gcc 1-го этапа, а затем использовать этот этап 1 для компиляции компилятора 2-го этапа, чтобы предотвратить любые ошибки на этапе-0 компилятор не влияет на конечный результат.

Затем процесс компиляции по умолчанию для gcc использует компилятор stage-2 для создания компилятора stage-3 и сравнивает два двоичных файла: любое различие между ними может быть использовано как доказательство наличия ошибки.

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


Это выходит за рамки gcc во всей цепочке инструментов, потому что повсюду применяются одни и те же принципы: если у вас есть какие-либо различия в результате между сборкой glibc-x.y в системе, в которой работает glibc-x.y, и системой, в которой работает glibc-x.(y-1), и вы не выполняете дополнительный проходчтобы убедиться, что вы создаете в соответствии с вашей целевой средой, затем воспроизвести эти ошибки (и протестировать предлагаемые исправления) намного сложнее, чем было бы в противном случае: никто, у кого нет вашей (обычно нераскрытой) среды сборки, не сможет воссоздать ошибку!

Комментарии:

1. Хорошо сказано. Раньше это называлось начальной загрузкой. Раньше я загружал gcc на Sparc / Solaris.

2. Если это так, то, учитывая шаги в документе LFS и ваш ответ, я должен выполнить сборку gcc дважды. Сначала с использованием компилятора хост-системы, а затем с использованием встроенного кросс-компилятора, верно? Почему существует три сборки gcc : Pass 1 , Pass 2 а затем внутри chroot ?

3. @Monku, в частности, для gcc двухпроходный подход является внутренним для системы сборки. Таким образом, построение вашей цепочки инструментов начальной загрузки включает в себя два прохода; и построение вашей цели также включает в себя два прохода.

4. @Monku, … теперь пользователи LFS могут использовать --disable-bootstrap во время настройки для целевого экземпляра (не для начальной загрузки), если они создают целевой gcc с той же версией, которую они использовали для начальной загрузки gcc, но говорят как кто-то, кто был половиной (не инструментальной) пользовательской команды дляраньше в коммерческом дистрибутиве Linux оптимизация производительности по сравнению с корректностью была неправильной.

Ответ №2:

Я знаю, что этот запрос немного устарел, но мне есть что добавить к ответам: разъяснение значения слова «bootstrap».

Основная причина многоступенчатой сборки заключается в том, чтобы исключить все остатки programs / config / libs узла сборки из результирующего программного обеспечения. Недостаточно скомпилировать свежее программное обеспечение. Вы также должны избегать любых ссылок на библиотеки хоста, интерфейсы ядра хоста (заголовки ядра), версии pkg хоста и все другие подобные зависимости от хост-системы.

Предположим, вы оказались мазохистом и хотели собрать Debian 4 на Fedora 27 (это должно быть возможно). Простая сборка программного обеспечения приведет к появлению ссылок на библиотеки 27 и другие вещи. И ваша результирующая система не будет работать, потому что эти вещи недоступны при установке окончательной системы.

LFS несколько упрощает процесс, создавая простые двоичные файлы x86-x86 и перекрестные инструменты gcc на этапе 1, затем устанавливая заголовки для ядра, которые будут использоваться в конечной системе, а затем glibc. Этап 2 (binutils и gcc) создается с использованием перекрестных инструментов, что гарантирует, что программы / библиотеки / конфигурации хоста вообще не используются. Остальная часть набора инструментов (я называю это этапом 3) создается с использованием инструментов из этапа 2. Теперь можно построить заключительный этап (с несколькими небольшими корректировками) с гарантией того, что ни на какую часть узла сборки не будут ссылаться или использоваться ссылки и что ни на какую часть набора инструментов не будут ссылаться или использоваться. Заключительный этап строится с использованием пути, очень похожего на PATH=/bin:/usr/bin:/tools/bin; таким образом, по мере создания окончательных инструментов они будут использоваться вместо инструментов в цепочке инструментов.

Создание цепочки инструментов не для нетерпеливых. Мне потребовались месяцы, чтобы обновить систему сборки Smoothwall Express и используемые pkgs, потому что создание цепочки инструментов сопряжено с опасностью. Я сражался со многими драконами, балроками и гномами. Я часто ссылался на LFS, чтобы выяснить, как они это сделали. В результате получается автоматизированная система повторной сборки, которая создает весь дистрибутив без ссылок на хост-систему. Я в основном собираю его на Debian 8, но известно, что он построен на Gentoo, и он должен быть способен строить сам.