Construyendo módulos para el núcleo
En ocasiones usted necesita modificar un módulo del núcleo o crear uno nuevo. Esto puede adicionar algunas características o simplemente aplicar un parche. En este ejemplo, trataremos de aplicar una rectificación de error a un módulo existente y luego recompilarlo.
|
Importante |
|
Contents
Asumimos que ya tenga un árbol con el código fuente del núcleo. Si usted siguió Necesito el código fuente del núcleo, el árbol con el código fuente está en /usr/src/redhat/BUILD/kernel-<version>/linux-<version>. Si usted siguió Necesito construir un núcleo personalizado, el árbol con el código fuente está en ~/rpmbuild/BUILD/kernel-<version>/linux-<version>.
Está contraindicado realizar la construcción de módulos como root. Para correr el proceso como un usuario diferente a root, haga lo siguiente:
cd
mkdir -p rpmbuild/{SRPMS,RPMS,SPECS,BUILD,SOURCES}
echo "%_topdir %(echo $HOME)/rpmbuild" > .rpmmacros
Esto creará el árbol de directorio en ~/rpmbuild y el código fuente del núcleo estará en ~/rpmbuild/BUILD/kernel-<version>/linux-<version>.
Vea además: Artículo de Construcción de RPMs en CentOS con usuarios diferentes a root: http://www.owlriver.com/tips/
1. Construyendo un módulo *.ko para el núcleo
Vamos a asumir que nuestro código fuente para el núcleo esta en ~/rpmbuild/BUILD/kernel-2.6.18/linux-2.6.18.i686 y vamos a arreglar el módulo cifs que está en ~/rpmbuild/BUILD/kernel-2.6.18/linux-2.6.18.i686/fs/cifs.
- Aplicar parches a los ficheros fuentes que lo requieran.
- Cambiar al directorio root del código fuente del núcleo y si esta es la primera vez que el núcleo es compilado, configure el núcleo.
cd ~/rpmbuild/BUILD/kernel-2.6.18/linux-2.6.18.i686 make oldconfig make prepare
- Crear los ficheros requeridos por la compilación externa de módulos.
make modules_prepare
Nota
modules_prepare no construirán Module.symvers aun si CONFIG_MODULEERSIONING está fijada. Sin embargo una construcción completa del núcleo necesita ser ejecutada para crear versiones de módulos que trabajen. Para los detalles, vea: /usr/share/doc/<kernel_version>/Documentation/kbuild/modules.txt .
- Compilar el módulo especificando el camino relativo al Makefile y al código fuente del módulo.
make M=fs/cifs
Nota
el directorio completo que contiene el módulo puede ser ubicado en cualquier parte. Si este está en ~mycifs, ejecute el comando siguiente asegurándose que se encuentre en el directorio raiz del código fuente del núcleo.make M=~/mycifs
En nuestro ejemplo, hemos creado cifs.ko en el directorio fuente del módulo. Si usted compiló el módulo fuera de el árbol fuente, copie el fichero .ko a /lib/modules/[version]/updates y ejecute el comando: (donde [version] es la cadena referente a la versión del núcleo)
depmod -v [version]
Usando el directorio updates actualizará los módulos del núcleo estándar y será fácil moverlos a nuevos núcleos más tarde según convenga.
Para hacer esto un par de pasos más largo, es necesario obtener diferentes módulos para diferentes tipos de núcleos.
En uno necesitamos editar el Makefile en el directorio principal del fuente del núcleo ... para el caso de CentOS 5 usted puede abrir el Makefile y buscar:
EXTRAVERSION = -prep
y reemplazarla con (a conveniencia):
EXTRAVERSION = -8.1.1.el5 EXTRAVERSION = -8.1.1.el5PAE EXTRAVERSION = -8.1.1.el5xen EXTRAVERSION = -8.1.1.el5.centos.plus EXTRAVERSION = -8.1.1.el5.centos.plusPAE EXTRAVERSION = -8.1.1.el5.centos.plusxen
El número no es muy importante si usted va a realizar un modprobe del módulo .ko ( un -8.el5 instalará un núcleo -8.1.1.el5). Sin embargo los modificadores PAE y xen son requeridos para usar esos tipos de núcleos.
|
Truco |
|
2. Construir un módulo para el núcleo usando Mantención Dinámica para los Módulos del Núcleo
El método descrito arriba construye un módulo para una versión específica del núcleo. Si usted mejora el núcleo o cambia de arquitectura, usted tendrá que reconstruir el módulo manualmente otra vez. El marco de trabajo para la mantención dinámica de módulos para el núcleo (DKMS) es básicamente un árbol duplicado fuera del árbol del núcleo que mantiene el fuente del módulo y los binarios de los módulos compilados. DKMS crea un ejecutable que puede ser llamado para construir, instalar o desinstalar módulos. DKMS necesita tener localizado el código fuente del módulo solo en el sistema del usuario. El ejecutable DKMS se encarga de construir e instalar el módulo para cualquier núcleo que los usuarios puedan tener en sus sistemas.
Aquí, usaremos el mismo ejemplo de arriba y construye el módulo cifs y crea su fichero rpm.
Instale el paquete dkms desde RPMForge.
Cree un directorio mkdir /usr/src/<module>-<module-version>/. En nuestro ejemplo este debe verse de la siguiente forma:
mkdir /usr/src/cifs-1.45fixed/
En este directorio, necesita tener:
- dkms.conf
- el código fuente del módulo.
<module>-dkms-mkrpm.spec (copielo desde /etc/dkms/template-dkms-mkrpm.spec).
El fichero dkms.conf tiene las líneas siguientes:
PACKAGE_NAME=cifs PACKAGE_VERSION=1.45fixed BUILT_MODULE_NAME[0]=cifs AUTOINSTALL="YES"
|
Nota |
|
Ejecute dkms <command> -m <module> -v <module-version> en este orden:
dkms add -m cifs -v 1.45fixed dkms build -m cifs -v 1.45fixed dkms mkrpm -m cifs -v 1.45fixed
El fichero rpm será creado en la ubicación /usr/src/redhat/RPMS/noarch.
/usr/src/redhat/RPMS/noarch/cifs-1.45fixed-1dkms.noarch.rpm
Vea además:
página man: http://linux.dell.com/dkms/manpage.html
3. Construyendo el paquete de un módulo para el núcleo (kmod)
(Borrador)
Usted puede producir ficheros rpm para los módulos de su núcleo. El paquete del módulo para el núcleo (kmod) será cargado usando el comando rpm como para los otro paquetes. Sin embargo, el empaquetado rpm de módulos para el núcleo es manipulado de forma diferente al proceso estándar de empaquetado. El ejemplo siguiente muestra algunas técnicas básicas de empaquetado que pueden servirle de punto de partida.
Aquí continuaremos con la construcción del módulo cifs y trataremos de crear un rpm kmod-cifs.
Lo primero que necesitamos es el tarball que contiene el fuente del módulo. Suponiendo que el árbol de construcción está en /usr/src/redhat/ y los ficheros fuentes están en /usr/src/cifs-1.45fixed/ como en la sección de arriba.
cd /usr/src/cifs-1.45fixed cp Makefile Kbuild cd .. tar cifs-1.45fixed.tar cifs-1.45fixed/ bzip2 cifs-1.45fixed.tar
Esto escribe un fichero con el nombre cifs-1.45fixed.tar.bz2. Fíjense que usted necesita incluir el nombre del directorio. Copie este fichero a /usr/src/redhat/SOURCES/.
Lo siguiente que necesitamos es un script llamado kmodtool. Este forma parte del paquete redhat-rpm-config. Copie el script a el directorio SOURCE.
cp /usr/lib/rpm/redhat/kmodtool /usr/src/redhat/SOURCES/
Edite el fichero kmodtool y comente las líneas que contengan kmod-common
# Requires: ${kmod_name}-kmod-common >= %{?epoch:%{epoch}:}%{version}
Ahora necesitamos crear un fichero .spec. Aquí esta un fichero de ejemplo para el módulo cfis que estamos construyendo.
%define kmodtool sh ../SOURCES/kmodtool
# hardcode for now:
%{!?kversion: %{expand: %%define kversion %(uname -r)}}
%define kmod_name cifs
%define kverrel %(%{kmodtool} verrel %{?kversion} 2>/dev/null)
%define upvar ""
%ifarch i686
%define paevar PAE
%endif
%ifarch i686 x86_64
%define xenvar xen
%endif
%{!?kvariants: %define kvariants %{?upvar} %{?xenvar} %{paevar} %{?kdumpvar}}
Name: %{kmod_name}-kmod
Version: 1.45
Release: 1.1.2.6.18_8.1.3.el5.centos
Summary: cifs 1.45 CentOS5 kmod (bug fix)
License: Distributable
Group: System Environment/Kernel
URL: http://www.centos.org/
#Source is created from these files:
Source0: cifs-1.45-el5.centos.tar.bz2
BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
ExclusiveArch: i686 x86_64
%description
This package provides a cifs kernel module with a bug fix (centos bug# 1776). It is
built to depend upon the specific ABI provided by a range of releases of the
same variant of the RHEL kernel and not on any one specific build.
# magic hidden here:
%define kmp_version %{version}
%define kmp_release %{release}
{expand:%(%{kmodtool} rpmtemplate_kmp %{kmod_name} %{kverrel} %{kvariants} 2>/dev/null)}
%prep
%setup -q -c -T -a 0
for kvariant in %{kvariants} ; do
cp -a cifs-1.45 _kmod_build_$kvariant
done
%build
for kvariant in %{kvariants}
do
ksrc=%{_usrsrc}/kernels/%{kverrel}${kvariant:+-$kvariant}-%{_target_cpu}
pushd _kmod_build_$kvariant
make -C "${ksrc}" modules M=$PWD
popd
done
%install
export INSTALL_MOD_PATH=$RPM_BUILD_ROOT
export INSTALL_MOD_DIR=extra/%{kmod_name}
for kvariant in %{kvariants}
do
ksrc=%{_usrsrc}/kernels/%{kverrel}${kvariant:+-$kvariant}-%{_target_cpu}
pushd _kmod_build_$kvariant
make -C "${ksrc}" modules_install M=$PWD
popd
done
%clean
rm -rf $RPM_BUILD_ROOT
%changelog
* Fri May 18 2007 Akemi Yagi <amyagi@gmail.com>
- Example file. 1.45-1.1.2.6.18_8.1.3.el5.centos
Nombre este fichero cfis.45fixed.spec y ubíquelo en /usr/src/redhat/SPECS.
Ahora estamos listos para construir el paquete
rpmbuild -ba --target `uname -m` cifs1.45fixed.spec
Si todo va bien, usted encontrará los ficheros kmod-cifs-xxx.rpm en /usr/src/redhat/RPMS/`uname -m`.
Vea además:
construcción kmod: http://www.kerneldrivers.org/RedHatKernelModulePackages
construcción de rpm (general): http://docs.fedoraproject.org/drafts/rpm-guide-en/ch08s02.html
