Страница 1 из 1

Сборка rpm-пакетов

Добавлено: 14 дек 2010, 12:40
Raven

Удовлетворение зависимостей

Часто наиболее сложной задачей становится сборка ПО должным образом. Одна из потенциальных проблем - существование зависимостей ПО от других программ и библиотек. В процессе работы с make следует обращать внимание на сторонние библиотеки, которые требуются для сборки. Эти зависимости должны быть позднее включены в спецификацию пакета на стадии построения rpm. В общем случае, каждая зависимость удовлетворяется собственным rpm-пакетом, таким образом нужно будет озаботиться обеспечением доступности этих rpm-пакетов.

Когда достигнуты три цели: обеспечена воспроизводимая сборка, спланированы обновления, удовлетворены все зависимости, можно приступать к собственно сборке rpm-пакета.

Разворачивание структуры директорий

RPM использует для сборки пакетов пять каталогов, они описаны в таблице.
КаталогИспользование
BUILDУтилита rpmbuild использует этот каталог в качестве каталога сборки ПО.
RPMSУтилита rpmbuild помещает в этот каталог собранные бинарные rpm-пакеты.
SOURCESВ этот каталог необходимо поместить тарболлы с исходным кодом проектов, запланированных на сборку.
SPECSВ этот каталог помещаются spec-файлы всех rpm-пакетов, которые запланированы на сборку.
SRPMSУтилита rpmbuild помещает в этот каталог собранные src.rpm-пакеты с исходным кодом.
Обычно каталог RPMS содержит подкаталоги для разных платформ, например на Intel-машине это будет следующий список:

Код: Выделить всё

$ ls RPMS 

athlon 

i386 

i486 

i586 

i686 

noarch 
В системе Red Hat Linux родительским каталогом для дерева каталогов сборки обычно бывает /usr/src/redhat.
Поскольку изначально RPM был спроектирован для построения дистрибутивов Linux в целом, этот путь может отличаться от указанного в других системах и его можно изменить редактированием rpmrc файлов.

Самый легкий способ - использовать уже имеющийся в системе путь к каталогам сборки. Для сборки под непривилегированным пользователем может потребоваться изменить права доступа к ним. Следует помнить, что ошибки сборки rpm-пакетов могут привести к серьезным проблемам в системе, если сборка производится от пользователя root.

Для того, чтобы приступить к сборке пакета осталось выполнить два действия:
  • - поместить исходный код в SOURCE;
    - поместить spec-файл в SPECS.

Размещение исходного кода в дереве сборки

Вообще говоря, можно поместить в SOURCES дерево каталогов с исходным кодом проекта. Но гораздо удобнее (и так и делается), особенно, если собирается много пакетов, поместить туда тарболл. Тогда в простом случае на каждый собираемый пакет будет приходится один файл с архивом. Раскрываться архив будет с помощью макросов RPM, тривиально с точки зрения пользователя. Это помогает держать исходный код разных проектов отдельно друг от друга, так как все они находятся в директории SOURCES.

Соглашение об именовании тарболлов с исходным кодом предлагает следующую форму имен: имя_пакета-версия.tar.gz. Поместив архив в SOURCES, оператор делает скрипты сборки, исходный код и все необходимое доступным для RPM.

Создание spec-файла

Spec-файл, сокращение от "файл спецификации", определяет все действия утилиты rpmbuild, которые должны быть выполнены при построении приложения, так же как и все действия, необходимые при установке/удалении приложения. Каждый src.rpm-пакет имеет в своем составе spec-файл для последующей пересборки пакета.

Spec-файл - это текстовый файл. Соглашение об именовании предлагает называть spec-файл таким образом:

Код: Выделить всё

имя_пакета.spec.
Текст внутри spec-файла имеет специальный синтаксис. Синтаксические определения имеют значения, задающие порядок сборки, номер версии, информацию о зависимостях и вообще всю информацию о пакете, которая может быть впоследствии запрошена из БД RPM.

Секция общей информации (introduction)

Секция общей информации содержит сведения о пакете, которые после его установки могут быть запрошены командой rpm -qi имя_пакета. Например:

Код: Выделить всё

Summary: java source to bytecode compiler 

Summary(ru): Исходный код компилятора байт-кода java 

%define version 1.17 

Copyright: IBM Public License, http://ibm.com/developerworks/oss/license10.html 

Group: Development/Languages 

Name: jikes 

Prefix: /usr 

Provides: jikes 

Release: 1 

Source: jikes-%{version}.tar.gz 

URL: http://ibm.com/developerworks/opensource/jikes 

Version: %{version} 

Buildroot: /tmp/jikesrpm 

%description
The IBM Jikes compiler translates Java source files to bytecode.
It also supports incremental compilation and automatic
makefile generation, and is maintained by the Jikes Project:
http://ibm.com/developerworks/opensource/jikes/ 

%description -l ru
Компилятор Java производства IBM Jikes осуществляет
преобразование исходного кода Java в
байт-код. Он поддерживает инкрементную компиляцию и автоматическую генерацию Makefile. Мантейнер - Jikes Project: http://ibm.com/developerworks/opensource/jikes/ 

Из этого примера, в общем, понятно, как устроена секция общей информации. Этот пример не следует всем требованиям RPM. Например, тэг Copyright в настоящее время утратил значение и не используется, номер версии можно задать непосредственно, в примере задается через определение макроса.

Для отслеживания изменений требований от версии к версии rpm можно проанализировать spec-файлы пакетов современных сборок и сравнить их с прежними сборками.

Секция prep

Секция подготовки отвечает за команды, необходимые для начала сборки. Например, если в SOURCES положен тарболл проекта, его необходимо распаковать. В секции указываются для этого соответствующие макросы rpm:

Код: Выделить всё

%prep 

%setup -q 
Секция начинается со строки %prep. Этот пример использует макрос %setup, который умеет распаковывать компрессированные архивы. Как правило, это единственная строка в данной секции.

Секция build

Секция build содержит команды сборки ПО. Обычно здесь присутствует всего несколько команд, например:

Код: Выделить всё

%build 

./configure CXXFLAGS=-O3 --prefix=$RPM_BUILD_ROOT/usr

make 
В данном примере задействованы два параметра скрипта configure (флаги оптимизации компилятора и имя временного каталога сборки) и команда make (без параметра, то есть для цели all). Секция начинается строкой %build.

Секция install

Секция содержит команды установки файлов пакета в систему. Например:

Код: Выделить всё

%install 

rm -rf $RPM_BUILD_ROOT

make install
На данной стадии очищаем каталог сборки и копируем файлы пакета в каталог, определенный опцией --prefix. Если не очистить каталог сборки, файлы от прежних сборок могут нарушить чистоту установки. Секция начинается строкой %install.

Секция clean

Команды в этой секции вычищают файлы, созданные на других стадиях:

Код: Выделить всё

%clean 

rm -rf $RPM_BUILD_ROOT
Секция начинается строкой %clean.

Секция files

И, наконец, команды в секции files задают списки файлов и каталогов, которые с соответствующими атрибутами должны быть скопированы из дерева сборки в rpm-пакет и затем будут копироваться в целевую систему при установке этого пакета. Например:

Код: Выделить всё

%files 

%defattr(-,root,root)

/usr/bin/jikes

%doc /usr/doc/jikes-%{version}/license.htm 

%doc /usr/man/man1/jikes.1* 

Секция начинается строкой %files. Макрос %doc отмечает файлы документации. Это позволяет составить документацию из подходящих файлов проекта.

После окончания редактирования spec-файла осталось поместить его в каталог SPECS под /usr/src/redhat, а тарболл с исходным кодом в SOURCES. Все готово для сборки rpm.

Re: Сборка rpm-пакетов

Добавлено: 14 дек 2010, 12:49
Raven

Сборка пакета с помощью утилиты rpmbuild

Базовый синтаксис использования утилиты rpmbuild:

Код: Выделить всё

rpmbuild -bСтадия_сборки имя_пакета.spec 
Опция -b указывает на режим сборки. Второй ключ после -b говорит, до какой стадии осуществлять процесс. Возможные стадии процесса рассмотрены в таблице.
ОпцияЗначение
-baСобрать бинарный пакет и пакет с исходным кодом
-bbСобрать бинарный пакет
-bcСкомпилировать программу, но не собирать rpm-пакет, то есть выполнить до секции %build включительно
-bpВыполнить подготовку и остановиться сразу после завершения стадии %prep
-biВыполнить сборку бинарного пакета и остановиться сразу после завершения стадии %install
-blВыполнить проверку списка файлов для пакета и вывести резюме ошибок, если корневой каталог сборки не содержит каких-то файлов из списка
-bsСобрать только пакет с исходным кодом
Следующий пример показывает результат выполнения команды rpmbuild -bp jikes.spec, отданный из каталога /usr/src/redhat/SPECS :

Код: Выделить всё

$ rpmbuild -bp jikes.spec 

Executing(%prep): /bin/sh -e /var/tmp/rpm-tmp.72435 

+ umask 022 

+ cd /usr/src/redhat/BUILD 

+ LANG=C 

+ export LANG 

+ cd /usr/src/redhat/BUILD 

+ rm -rf jikes-1.17 

+ /usr/bin/gzip -dc /usr/src/redhat/SOURCES/jikes-1.17.tar.gz 

+ tar -xf - 

+ STATUS=0 

+ '[' 0 -ne 0 ']' 

+ cd jikes-1.17 

++ /usr/bin/id -u 

+ '[' 500 = 0 ']' 

++ /usr/bin/id -u 

+ '[' 500 = 0 ']' 

+ /bin/chmod -Rf a+rX,g-w,o-w . 

+ exit 0 
После запуска команды на выполнение файлы с исходным кодом распаковываются в каталог /usr/src/redhat/BUILD, в подкаталог jikes-1.17. Подкаталоги используются, чтобы избежать смешивания файлов сборки различных проектов. Если зайти в каталог jikes-1.17, можно увидеть все необходимое для сборки проекта с помощью make.

Помимо стадий сборки, определяемых вторичными ключами, описанными в таблице, утилита rpmbuild принимает некоторые другие опции. Например, команда

Код: Выделить всё

$ rpmbuild --clean specfile.spec 
очистит временный каталог установки файлов пакета и каталог сборки проекта:

Код: Выделить всё

$ rpmbuild --clean /usr/src/redhat/SPECS/jikes.spec 

Executing(--clean): /bin/sh -e /var/tmp/rpm-tmp.21908 

+ umask 022 

+ cd /usr/src/redhat/BUILD 

+ rm -rf jikes-1.17 

+ exit 0

Re: Сборка rpm-пакетов

Добавлено: 14 дек 2010, 12:54
Raven

Верификация собранных пакетов

После сборки пакета для его проверки может быть использована процедура верификации. Кроме того, с помощью опции -bl можно проверить список файлов пакета. Например:

Код: Выделить всё

$ rpmbuild -bl /usr/src/redhat/SPECS/jikes.spec 

Processing files: jikes-1.17-1 

error: File not found: /tmp/jikesrpm/usr/bin/jikes 

error: File not found: 

/tmp/jikesrpm/usr/doc/jikes-1.17/license.htm 

error: File not found by glob: 

/tmp/jikesrpm/usr/man/man1/jikes.1* 

Provides: jikes 

RPM build errors: 

File not found: /tmp/jikesrpm/usr/bin/jikes 

File not found: /tmp/jikesrpm/usr/doc/jikes-1.17/license.htm 

File not found by glob: /tmp/jikesrpm/usr/man/man1/jikes.1* 

В этом примере показан вывод диагностики некоторого количества ошибок. Опция -bl проверяет список всех необходимых файлов пакета, расположенных в директории сборки. Из вывода ясно, что пакет не собрался правильно.

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

Для верификации полностью собранного пакета используют следующий синтаксис:

Код: Выделить всё

$ rpm -Vp /usr/src/redhat/RPMS/i386/jikes-1.17-1.i386.rpm 

S.5....T /usr/bin/jikes 

.......T d /usr/doc/jikes-1.17/license.htm 

..5....T d /usr/man/man1/jikes.1.gz 

В выводе команды верификации видно, что имеются различия в контрольных суммах MD5 и времени создания некоторых файлов, что может указывать, например, на тот факт, что оригинальный пакет был собран на другой системе с более старой версией дистрибутива Red Hat. В случае, если файлы пакета были изменены вручную после его установки, вывод ошибок будет похожий.