3 # vim:expandtab:shiftwidth=4:softtabstop=4:tabstop=4:
5 # this is an alternative FD for stdout, to be used especially when we are
6 # taking stdout from a function as it's return value. i.e. foo=$(bar)
7 # this is a workaround until a version of bash where we can put xtrace
13 if [[ $SHELLOPTS = *xtrace* ]]; then
18 # Assume that lbuild's support files can be found in the same
19 # canonicalized path as this very script.
20 LBUILD_SCRIPT=$(readlink -f ${0})
21 LBUILD_DIR=${LBUILD_DIR:-$(dirname ${LBUILD_SCRIPT})}
23 # include the exit_traps library
24 . ${LBUILD_DIR}/exit_traps.sh
25 . ${LBUILD_DIR}/funcs.sh
27 # our children should die when we do
28 push_exit_trap "kill -INT -$$ || true" kill_children
30 # increment this if you have made a change that should force a new kernel
40 # XXX - some recent hacking has pretty much neutered this option.
41 # search through this file for "-bb" and see how many places
42 # simply don't account for this option
47 TARGET_ARCH="$(uname -m)"
52 TMPDIR=${TMPDIR:-"/var/tmp"}
56 # this is the dir that should be used to store reuse products
58 # should cached products be used or force rebuilding?
60 # what does this do exactly? does it imply no kernel build?
64 SMPTYPES="smp bigsmp default ''"
66 PATCHLESS_SERVER=false
72 # default to not adding -lustre- into the kernel RPM package names
73 KERNEL_LUSTRE_NAMING=false
74 ENABLE_KERNEL_DEBUG=false
75 # default not use kabi check.
93 # not in the target file any more
96 # build the lustre-tests rpm?
105 # Readlink is not present on some older distributions: emulate it.
109 if [ -L "$path" ]; then
110 ll="$(LC_ALL=C ls -l "$path" 2> /dev/null)" &&
119 Usage: ${0##*/} [OPTION]... [-- <lustre configure options>]
121 --external-patches=EXTERNAL_PATCHES
122 Directory similar to lustre/lustre/kernel_patches/ that lbuild should
123 look for seres and config files in before looking in the lustre
126 --extraversion=EXTRAVERSION
127 Text to use for the rpm release and kernel extraversion.
129 --timestamp=TIMESTAMP
130 Date of building lustre in format YYYYMMDDhhmmss
133 Try to reuse old kernel builds from DIR
136 Path to distro kernel RPM collection
145 Build lustre client only
148 Build lustre server without patching the kernel
151 Which distro using. Autodetect by default
153 --kerneldir=KERNELDIR
154 Directory containing Linux source tarballs referenced by target
157 --kerneltree=KERNELTREE
158 Directory containing dirs with Linux source tarballs referenced by target
159 files. Dir names in format kernel version ('2.6.9', etc.)
161 --enable-kernel-debug
162 Build with kernel-<version>.config-debug instead
164 --linux=LINUX --with-linux=LINUX
165 Directory of Linux kernel sources. When this option is used, only
166 Lustre modules and userspace are built.
169 Path to an existing lustre source tarball to use.
172 Do not try to download a kernel from downloads.whamcloud.com
175 Do not build a .src.rpm, a full kernel patch, or a patched kernel
179 Type of OFED to build with lustre: inkernel, ofa, mlnx, ifs
180 ofa: OpenFabrics Alliance
182 ifs: Intel True Scale Fabric
185 Version of external OFED to build with lustre
188 Version of external Mellanox OFED to build with lustre
191 Tarball for either OFED. Tarball must follow below format
192 OFED-<ofed-version>.tgz regardless of vendors
193 It's likely that you need to reconstruct the directory name
194 It must be placed under KERNELTREE directory
197 Build with ldiskfs support. (Deprecated, always true)
200 Do not build lustre-iokit RPM. Now true by default
206 Specifies that the files generated do not include timestamps, and
207 that this is an official release.
210 Build Lustre without ZFS.
213 Build a .src.rpm, a full kernel patch, and a patched kernel tarball.
216 Directory used to stage packages for release. RPMs will be placed
217 more or less in DIR/<target>-<arch>, and the tarball will be
221 The name of the target to build. The available targets are listed
225 Builds a Xen domX kernel.
228 Sets a variable to a given value.
237 # canonicalize a relative path to a file
241 if [ ! -f "$PATH" ]; then
245 local FILE=${PATH##*/}
248 echo $(canon_path "$DIR")/$FILE
252 # canonicalize a relative path to a dir
256 if [ ! -d "$PATH" ]; then
260 pushd "$PATH" >/dev/null || return 1
270 if [ -z "$LUSTRE" -o ! -r "$LUSTRE" ]; then
271 usage 1 "Could not find Lustre source tarball '$LUSTRE'."
274 if $PATCHLESS && $PATCHLESS_SERVER; then
275 usage 1 "Can not use both --patchless and --patchless-server."
278 if [ -n "${OFED_SRC}" ]; then
279 if [ -z "${OFED_VERSION}" ]; then
280 usage 1 "Need to provide version for file ${OFED_SRC}."
282 if [ "${OFED_TYPE}" = "inkernel" ]; then
283 usage 1 "Need to provide ofed type for file ${OFED_SRC}."
286 if [ "${OFED_TYPE}" != "inkernel" -a -z "${OFED_VERSION}" ]; then
287 usage 1 "Need to provide version for $OFED_TYPE OFED"
290 if [ "${OFED_TYPE}" = "inkernel" -a -n "${OFED_VERSION}" ]; then
291 usage 1 "Can not specify version with inkernel OFED"
295 if [ -z "$DISTRO" ] ; then
296 DISTRO=$(autodetect_distro)
300 DISTROMAJ=${DISTRO%%.*}
302 [ -z "$TARGET" ] && TARGET=$(autodetect_target "$DISTRO")
304 if [ -z "$LINUX" ]; then
305 [ "$KERNELDIR" -o "$KERNELTREE" ] || \
306 usage 1 "A kernel directory must be specified with --kerneldir or --kerneltree."
308 [ -d "$KERNELDIR" -o -d "$KERNELTREE" ] || \
309 usage 1 "$KERNELDIR and $KERNELTREE are not a directory."
311 # TARGET_FILE="$TOPDIR/lustre/kernel_patches/targets/$TARGET.target"
312 # [ -r "$TARGET_FILE" ] || \
313 # usage 1 "Target '$TARGET' was not found."
317 3.12-sles12 | 4.4-sles12)
318 CANONICAL_TARGET="sles12"
321 CANONICAL_TARGET="rhel9"
324 CANONICAL_TARGET="rhel8"
327 CANONICAL_TARGET="rhel7"
330 CANONICAL_TARGET="sles11"
334 local timestampnodig=$(echo $TIMESTAMP | sed -e s/[0-9]*//g)
335 [ "$timestampnodig" = "" ] || TIMESTAMP=$(date -d "$DATE" "+%Y%m%d%H%M%S")
336 local timestamplength="${#TIMESTAMP}"
337 if [ $timestamplength -eq 12 ]; then
338 TIMESTAMP="${TIMESTAMP}00"
339 elif [ $timestamplength -ne 14 ]; then
340 TIMESTAMP=$(date -d "$DATE" "+%Y%m%d%H%M%S")
343 RPMBUILD=$(which rpmbuild 2>/dev/null | head -n 1)
344 RPMBUILD=${RPMBUILD:-$(which rpm 2>/dev/null | head -n 1)}
345 if [ -z "$RPMBUILD" ]; then
346 usage 1 "Could not find binary for making rpms (tried rpmbuild and rpm)."
349 local BINDIR="$TOPDIR/bin"
350 if [ -d $BINDIR ]; then
351 rm -rf $BINDIR >/dev/null 2>&1 || true
354 mkdir -p $BINDIR || fatal 1 "error trying to create $BINDIR"
355 export PATH=$BINDIR:$PATH
357 cat >${BINDIR}/rpmbuild <<EOF
360 ARGS="\${FIND_REQUIRES:+--define \"__find_requires \$FIND_REQUIRES\"}
361 \${FIND_KSYMS_REQUIRES:+--define \"__required_ksyms_requires \$FIND_KSYMS_REQUIRES\"}"
364 *\'* ) ARGS="\$ARGS \"\$arg\"" ;;
365 * ) ARGS="\$ARGS '\$arg'" ;;
369 eval $RPMBUILD \$ARGS
371 chmod 755 ${BINDIR}/rpmbuild
373 if [ -n "$CCACHE" ]; then
374 which "$DISTCC" &>/dev/null && export DISTCC RPM_BUILD_NCPUS
376 if which "$CCACHE" &>/dev/null; then
377 local ccache=$(which "$CCACHE" 2>/dev/null | head -n 1)
379 ln -s "$ccache" ${BINDIR}/ccache
380 ln -s "$ccache" ${BINDIR}/cc
381 ln -s "$ccache" ${BINDIR}/$CC
384 export CC="ccache $CC"
385 # zero the cache so we can see how effective we are being with it
389 # get some ccache stats when we are done
390 push_exit_trap '[ -n "$CCACHE" ] && ccache -s' "ccache_summary"
391 # should remove the ccache trap if lbuild is interrupted
392 trap 'echo "Received an INT TERM or HUP signal, terminating."; delete_exit_trap "ccache_summary"; exit 1' INT TERM HUP
399 # compare two versions $1 and $2. if $1 < $2, return 0 otherwise return 1.
401 [[ $1 == $2 ]] && return 1
403 local i val1=($1) val2=($2)
405 # padding zero to val1 if it needs
406 for ((i=${#val1[@]}; i<${#val2[@]}; i++)); do
409 for ((i=0; i<${#val1[@]}; i++)); do
410 [[ -z ${val2[i]} ]] && return 1
412 if [[ ${val1[i]} < ${val2[i]} ]]; then
414 elif [[ ${val1[i]} > ${val2[i]} ]]; then
421 # Return a numeric version code based on a version string. The version
422 # code is useful for comparison two version strings to see which is newer.
424 # split arguments like "0.8.0" into "0", "8", "0"
425 eval set -- $(tr "[:punct:]" " " <<< $*)
426 echo -n "$((($1 << 16) | ($2 << 8) | $3))"
431 echo $(echo "$*" | xargs -n 1 | sort -u)
439 if [ -z "$target" ]; then
440 fatal 1 "fetch_url() called without a target to fetch to"
443 if [ -d $target ]; then
444 target+="/${url##*/}"
448 if which wget >/dev/null 2>&1; then
449 if ! wget -nv "$url" -O "$target"; then
452 elif which curl >/dev/null 2>&1; then
453 if ! curl -n -L -s -o "$target" "$url"; then
457 fatal 1 "Could not find either wget or curl to fetch URLs."
467 local force="${3:-false}"
469 # let the download_file handle the concurrency
472 # get the location from a distro specific method if it exists
473 if type -p kernel_srpm_location; then
474 location=$(kernel_srpm_location)
476 fatal 1 "Must specify location for download kernel SRPM."
478 echo "Downloading $location/$srpm..."
480 "$location/$srpm" "$KERNELDIR/$srpm" "$force" 2>&1 ||
481 [ ! -s "$KERNELDIR/$srpm" ]; then
482 rm -f $KERNELDIR/$srpm
483 fatal 1 "Could not download target $target's kernel \
484 SRPM $srpm from $location."
489 download_debuginfo_common() {
491 local force="${2:-false}"
493 # let the download_file handle the concurrency
495 # get the location from a distro specific method if it exists
496 if type -p kernel_debuginfo_location; then
497 location=$(kernel_debuginfo_location)
499 echo "Downloading $location/$rpm"
501 "$location/$rpm" "$KERNELRPMSBASE/$lnxmaj/$DISTROMAJ/$TARGET_ARCH/$rpm" "$force" 2>&1 ||
502 [ ! -s "$KERNELRPMSBASE/$lnxmaj/$DISTROMAJ/$TARGET_ARCH/$rpm" ]; then
503 rm -f $KERNELRPMSBASE/$lnxmaj/$DISTROMAJ/$TARGET_ARCH/$rpm
504 fatal 1 "Could not download $rpm from $location."
514 local file=${from##*/}
520 local semaphore="$to-downloading"
523 if [ ! -f $semaphore ]; then
527 # make sure the download has not been aborted
528 local now=$(date +%s)
529 local file_mtime=$(stat -c %Y "$to")
530 local staleness=$((now - file_mtime))
531 # let's assume an active download will write at least once a minute
532 if [ $staleness -gt 60 ]; then
540 # if the semaphore file exists, the file is either still downloading
541 # or a download was aborted and we cannot trust the target file
542 if [ -f $semaphore ]; then
546 if ! is_downloading && [ -r "$to" ] && [ -s "$to" ]; then
553 if $force || ! is_downloaded; then
554 if is_downloading; then
555 echo "Somebody else is downloading $from..."
556 while is_downloading; do
557 echo "Waiting for $to to finish downloading"
560 if is_downloaded; then
563 echo "The download we were waiting for seems to have been aborted"
569 echo "Downloading $from..."
570 # flag others so they don't try to download also
571 push_exit_trap "rm -f $to $semaphore" "download"
573 if ! fetch_url "$from" "$to" || [ ! -s "$to" ]; then
574 # the trap will remove the files via the fatal below
575 fatal 1 "Could not download ${to##*/} from ${from%/*}/."
578 delete_exit_trap "download"
580 fatal 1 "${to##*/} not found in directory ${to%/*}."
590 local ofed_version="$2"
591 local force="${3:-false}"
592 local distro_name="${DISTRO}"
593 local arch="${TARGET_ARCH}"
597 #if a src tarball has been given in the command line, we use it
598 #The format of the tarball must be OFED-${OFED_VERSION}.tgz
599 [ -n "${OFED_SRC}" ] && return 0
603 location="https://www.openfabrics.org/downloads/OFED/ofed-${ofed_version}/"
605 if [[ $ofed_version = *-[rR][cC][0-9] ]]; then
606 ofed_version_loc=${ofed_version%%-[rR][cC][0-9]}
607 location="https://www.openfabrics.org/downloads/OFED/ofed-${ofed_version_loc}/"
610 if [[ $ofed_version = *-daily ]]; then
611 ofed_version=${ofed_version/-daily/}
612 location="https://www.openfabrics.org/downloads/OFED/ofed-${ofed_version}-daily/"
613 # find the filename for latest version
614 ofed_version=$(curl -1 -s "$location" | sed -nre "s/.*href=\"OFED-(${ofed_version//./\\.}-[0-9]{8}-[0-9]{4}).tgz.*$/\1/p" | tail -1)
615 if [ -z "$ofed_version" ]; then
616 fatal 1 "Could not determine the filename of the OFED snapshot from daily "
620 file="OFED-${ofed_version}.tgz"
621 download_file "$location/$file" "$KERNELTREE" "$force"
624 location="http://www.mellanox.com/downloads/ofed/MLNX_OFED-${ofed_version}"
625 # this is a work around for suse distro (sles11.3). what we need is
626 # sles11sp3. We really need to redesign how we use target and distro
627 [[ $distro_name =~ sles ]] && distro_name=${DISTRO/./sp}
628 if [[ $arch = "aarch64" ]] && [[ $DISTROMAJ < "rhel8" ]]; then
629 file="MLNX_OFED_LINUX-${ofed_version}-${distro_name}alternate-${arch}.tgz"
631 file="MLNX_OFED_LINUX-${ofed_version}-${distro_name}-${arch}.tgz"
633 download_file "$location/$file" "$KERNELTREE" "$force"
636 location="http://downloadmirror.intel.com/24625/eng/"
637 file="IntelIB-Basic.$(echo ${distro_name%%.*} | tr '[:lower:]' '[:upper:]')-${arch}.${ofed_version}.tgz"
638 download_file "$location/$file" "$KERNELTREE" "$force"
641 fatal 1 "Error: unknown OFED type: $ofed_type"
644 # version might change due to detect daily version
645 OFED_VERSION=${ofed_version}
651 EXTRA_VERSION_save="$EXTRA_VERSION"
652 for patchesdir in "$EXTERNAL_PATCHES" \
653 "$TOPDIR/lustre/lustre/kernel_patches"; do
654 TARGET_FILE="$patchesdir/targets/$TARGET.target"
655 [ -r "$TARGET_FILE" ] && break
657 [ -r "$TARGET_FILE" ] || fatal 1 "Target $TARGET was not found."
659 echo "Loading target config file $TARGET.target..."
661 # if the caller specified an OFED_VERSION it should override whatever
662 # the target file specifies
663 local env_OFED_VERSION="$OFED_VERSION"
667 if [ -n "$env_OFED_VERSION" ]; then
668 OFED_VERSION="$env_OFED_VERSION"
671 # doesn't make any sense to build OFED for xen domX's
676 # XXX - set_rpm_smp_type is an ugly undeterministic hack. it needs to
677 # go away and the target just specify the $RPMSMPTYPE
678 [ -z "$RPMSMPTYPE" ] && set_rpm_smp_type
680 # CC might have been overwritten in TARGET_FILE
681 if [[ $CC != ccache\ * ]] && which "$CCACHE" &>/dev/null; then
682 export CCACHE && export CC="ccache $CC"
685 if [ ! "$KERNELTREE" = "" ] && [ -d "$KERNELTREE" ]; then
686 KERNELDIR="$KERNELTREE/${lnxmaj}"
687 [ -d "$KERNELDIR" ] || mkdir "$KERNELDIR"
690 # verify the series is available
691 if [ "$SERIES" ]; then
692 for series in $SERIES; do
693 for patchesdir in "$EXTERNAL_PATCHES" "$TOPDIR/lustre/lustre/kernel_patches"; do
694 [ -r "$patchesdir/series/$series" ] && continue 2
696 fatal 1 "Target $TARGET's series $SERIES could not be found.\nSearched:\n\t$EXTERNAL_PATCHES/series\n\t$TOPDIR/lustre/lustre/kernel_patches/series."
700 # set the location of the .config file
706 if $ENABLE_KERNEL_DEBUG; then
707 if [ -f $TOPDIR/lustre/lustre/kernel_patches/kernel_configs/kernel-$lnxmaj-$TARGET-$TARGET_ARCH.config-debug ]; then
708 CONFIG_FILE="$TOPDIR/lustre/lustre/kernel_patches/kernel_configs/kernel-$lnxmaj-$TARGET$XENPOSTFIX-$TARGET_ARCH.config-debug"
711 if [ -f $TOPDIR/lustre/lustre/kernel_patches/kernel_configs/kernel-$lnxmaj-$TARGET-$TARGET_ARCH.config ]; then
712 CONFIG_FILE="$TOPDIR/lustre/lustre/kernel_patches/kernel_configs/kernel-$lnxmaj-$TARGET$XENPOSTFIX-$TARGET_ARCH.config"
716 local lnxrelnew=${lnxrel//-/_}
718 # remember the EXTRA_VERSION before we diddle it here
719 # XXX - we really should not diddle with any values read in from the
720 # target file. if we want to modify a value, we should create
722 PRISTINE_EXTRA_VERSION=$EXTRA_VERSION
724 if ! $PATCHLESS && [ ! -f "$CONFIG_FILE" ]; then
725 fatal 1 "Config file for target $TARGET missing from $TOPDIR/lustre/lustre/kernel_patches/kernel_configs/."
728 if [ "$EXTRA_VERSION_save" ]; then
729 EXTRA_VERSION="$EXTRA_VERSION_save"
730 elif ! $RELEASE; then
731 # if there is no patch series, then this is not a lustre specific
732 # kernel. don't make it look like one
733 if $PATCHLESS || [ -n "$SERIES" ]; then
734 EXTRA_VERSION=$(echo $EXTRA_VERSION | sed -e "s/\(.*_lustre\)\..*/\1/")
737 # EXTRA_VERSION=${EXTRA_VERSION//-/_}
743 echo -n '--wildcards '
746 fatal 1 "tarflags(): File name argument missing."
758 fatal 1 "tarflags(): Unrecognized tar extension in file: $1"
767 local extractfile="$@"
769 echo "Untarring ${tarfile##*/}..."
770 tar $(tarflags "$tarfile") "$tarfile" $extractfile
776 local ofed_version="$2"
777 local distro_name="${DISTRO}"
778 local arch="${TARGET_ARCH}"
781 #if a src tarball has been given in the command line, we use it
782 #The format of the directory after untar MUST be in OFED-${version}
783 #even if it's from MLNX or IFS...or whatever
784 if [ -n "${OFED_SRC}" ]; then
785 if ! untar "$KERNELTREE/${OFED_SRC}"; then
788 [ -d OFED ] || ln -sf OFED-[0-9].[0-9]* OFED
793 file="OFED-${ofed_version}"
794 if ! untar "$KERNELTREE/${file}.tgz"; then
797 [ -d OFED ] || ln -sf OFED-[0-9].[0-9]* OFED
800 # this is a work around for suse distro (sles11.3). what we need is
801 # sles11sp3. We really need to redesign how we use target and distro
802 [[ $distro_name =~ sles ]] && distro_name=${DISTRO/./sp}
803 if [[ $arch = "aarch64" ]] && [[ $DISTROMAJ < "rhel8" ]]; then
804 file="MLNX_OFED_LINUX-${ofed_version}-${distro_name}alternate-${arch}"
806 file="MLNX_OFED_LINUX-${ofed_version}-${distro_name}-${arch}"
808 # it's not important what distro we get the tarball since we only
809 # interest in the src
810 if ! untar "$KERNELTREE/${file}.tgz"; then
813 # we need to untar again to get the src since it's being
814 # wrapped inside the tarball
815 # There are cases where the source version is different
817 # (ie. MLNX_OFED_LINUX-2.3-1.0.1 but MLNX_OFED_SRC-2.3-1.0.0)
818 local src=$(ls ${file}/src/MLNX_OFED_SRC-${ofed_version%.*}*.tgz)
819 if ! untar "$src"; then
822 [ -d OFED ] || ln -sf MLNX_OFED_SRC-[0-9].[0-9]* OFED
823 if compare_version $ofed_version 4.7 ||
824 compare_version 5.1 $ofed_version; then
825 [ -d OFED_RPMS ] || ln -sf ${file}/RPMS OFED_RPMS
827 [ -d OFED_RPMS ] || ln -sf ${file}/RPMS/MLNX_LIBS OFED_RPMS
831 file="IntelIB-Basic.$(echo ${distro_name%%.*} | tr '[:lower:]' '[:upper:]')-${arch}.${ofed_version}"
832 if ! untar "$KERNELTREE/${file}.tgz"; then
835 [ -d OFED ] || ln -sf $file/IntelIB-OFED.$(echo ${distro_name%%.*} | tr '[:lower:]' '[:upper:]')-${arch}.* OFED
836 ofed_version="$(cat OFED/Version)"
839 # version might change due to detect daily version
840 OFED_VERSION=${ofed_version}
845 untar "$LUSTRE" || fatal 1 "Error unpacking Lustre tarball"
846 [ -d lustre ] || ln -sf lustre-[0-9].[0-9]* lustre
852 local do_patch=${1:-true}
854 FULL_PATCH="$PWD/lustre-kernel-${TARGET}-${EXTRA_VERSION}.patch"
855 [ -f "$FULL_PATCH" ] && rm -f "$FULL_PATCH"
856 $do_patch && pushd linux >/dev/null
857 for series in $SERIES; do
858 echo -n "Applying series $series:"
859 for patchesdir in "$EXTERNAL_PATCHES" "$TOPDIR/lustre/lustre/kernel_patches"; do
860 [ -r "$patchesdir/series/$series" ] || continue
861 SERIES_FILE="$patchesdir/series/$series"
862 for patch in $(<"$SERIES_FILE"); do
864 PATCH_FILE="$patchesdir/patches/$patch"
865 [ -r "$PATCH_FILE" ] || \
866 fatal 1 "Patch $patch does not exist in Lustre tree."
867 cat "$PATCH_FILE" >> "$FULL_PATCH" || {
869 fatal 1 "Error adding patch $patch to full patch."
872 patch -s -p1 < "$PATCH_FILE" 2>&1 || {
874 fatal 1 "Error applying patch $patch."
882 $do_patch && popd >/dev/null
883 echo "Full patch has been saved in ${FULL_PATCH##*/}."
890 local configure_args=""
894 pushd lustre >/dev/null
896 if ! build_lustre_dkms; then
897 popd >/dev/null # pushd lustre
901 echo "Building Lustre RPMs for: $TARGET_ARCH"
903 # If server we now build the spl and zfs modules against the lustre kernel.
904 # These are required prior to the building of lustre server. Client does
905 # not require spl/zfs. Use !PATCHLESS to indicate server which follows the
906 # line above so is at least consistant.
907 if [ $PATCHLESS == false ] && [ "x$WITH_ZFS" == "x" ]; then
908 if ! build_spl_zfs; then
909 popd >/dev/null # pushd lustre
915 configure_args="$configure_args --disable-server"
918 # ditto for the lustre-tests boolean
919 if ! $LUSTRE_TESTS; then
920 configure_args="$configure_args --disable-tests"
924 configure_args="$configure_args --disable-iokit"
927 if ! $OSDZFSRPM; then
928 configure_args="$configure_args --without-zfs"
931 if ! $OSDLDISKFSRPM; then
932 configure_args="$configure_args --disable-ldiskfs"
935 configure_args="$configure_args --with-linux=$linux"
936 configure_args="$configure_args ${linuxobj:+--with-linux-obj=$linuxobj}"
938 # allow environment setting to override ldiskfs series selection
939 [ -n "$LDISKFS_SERIES" ] && export LDISKFS_SERIES
941 ./configure $configure_args $CONFIGURE_FLAGS 2>&1 ||
942 fatal 1 "Error in configure."
944 if type -p apply_kmod_requires_conflicts; then
945 apply_kmod_requires_conflicts
949 fatal 1 "Error building rpms for $TARGET_ARCH."
951 # move RPMs into place where they are expected to be
952 mv -f *lustre*.${TARGET_ARCH}.rpm $TOPDIR/RPMS/${TARGET_ARCH}/
953 mv -f lustre-*.src.rpm $TOPDIR/SRPMS/
956 if type -p cleanup_rpmmacros; then
963 build_lustre_dkms() {
965 local ver=$(sed -n -e 's/^LUSTRE_VERSION = //p' LUSTRE-VERSION-FILE)
967 echo "Building Lustre DKMS RPMs for: $TARGET_ARCH"
968 ./configure --enable-dist || fatal 1 "Error in DKMS configure."
971 build_args="--without servers"
974 rpmbuild --define "_topdir $TOPDIR" $build_args -bs lustre-dkms.spec ||
975 fatal 1 "Error building DKMS .src.rpm for $TARGET_ARCH."
978 rpmbuild --define "_topdir $TOPDIR" $build_args \
979 --rebuild $TOPDIR/SRPMS/lustre-client-dkms-$ver-*.src.rpm ||
980 fatal 1 "Error building DKMS .rpm for $TARGET_ARCH."
982 rpmbuild --define="_topdir $TOPDIR" --with servers \
983 --with zfs --without ldiskfs -bs lustre-dkms.spec ||
984 fatal 1 "Error creating DKMS (zfs) .srpm for $TARGET_ARCH."
985 rpmbuild --define="_topdir $TOPDIR" --with servers \
986 --without zfs --with ldiskfs -bs lustre-dkms.spec ||
987 fatal 1 "Error creating DKMS (ldiskfs) .srpm for $TARGET_ARCH."
988 rpmbuild --define="_topdir $TOPDIR" --with servers \
989 --with zfs --with ldiskfs -bs lustre-dkms.spec ||
990 fatal 1 "Error creating DKMS (all) .srpm for $TARGET_ARCH."
992 rpmbuild --rebuild --define="_topdir $TOPDIR" --with servers \
993 --with zfs --without ldiskfs $TOPDIR/SRPMS/lustre-zfs-dkms-$ver-*.src.rpm ||
994 fatal 1 "Error building DKMS (zfs) .rpm for $TARGET_ARCH."
995 rpmbuild --rebuild --define="_topdir $TOPDIR" --with servers \
996 --without zfs --with ldiskfs $TOPDIR/SRPMS/lustre-ldiskfs-dkms-$ver-*.src.rpm ||
997 fatal 1 "Error building DKMS (ldiskfs) .rpm for $TARGET_ARCH."
998 rpmbuild --rebuild --define="_topdir $TOPDIR" --with servers \
999 --with zfs --with ldiskfs $TOPDIR/SRPMS/lustre-all-dkms-$ver-*.src.rpm ||
1000 fatal 1 "Error building DKMS (all) .rpm for $TARGET_ARCH."
1009 # Fetch spl/zfs from the git repo and prepare for lustre build
1012 # SPLZFSGITREPO - URI of directory where spl.git and zfs.git are located
1013 # SPLZFSTAG - Tag to checkout of clone repositories
1014 # SPLZFSVER - Version to checkout of both (format zfs/spl-$SPLZFSVER)
1016 # return 0 if successful, else 255
1018 # make sure the RPM build environment is set up
1020 create_rpmbuild_dirs
1023 # The spl/zfs spec files expect RPM_BUILD_ROOT to point to the root of the
1024 # destination for the rpms
1025 export RPM_BUILD_ROOT=$TOPDIR
1026 SPLZFSVER=${SPLZFSVER:-2.1.5}
1027 SPLZFSTAG=${SPLZFSTAG:-}
1028 # "spl zfs" prior to 0.8.0
1029 # "zfs" for 0.8.0 and later
1030 (( $(version_code $SPLZFSVER) < $(version_code 0.8.0) )) &&
1031 SPLZFSPKGS="spl zfs" || SPLZFSPKGS="zfs"
1033 # The files expect a kver to be set to the kernel version .
1034 local kver=$(find_linux_release)
1036 # build and install the spl and zfs (and -devel) RPMs for lustre to use
1039 for pkg in $SPLZFSPKGS; do
1043 # need to fetch the repo in order to build it.
1044 # default to github but allow override
1045 git clone -n ${SPLZFSGITREPO:-"https://github.com/zfsonlinux"}/$pkg.git $pkg 2>&1
1047 pushd $pkg || return 255
1049 if [ -n "$SPLZFSTAG" ]; then
1054 git checkout -b lbuild $tag || fatal 1 "Failed to checkout \"$tag\" for $pkg.git"
1056 # This differentiates between older zfs versions
1057 if [ -f $pkg-modules.spec.in ]; then
1060 speclist="$pkg.spec $rpmpkg.spec"
1062 rpmpkg=kmod-$pkg-devel
1064 speclist="$pkg.spec $pkg-kmod.spec $pkg-dkms.spec"
1067 sh autogen.sh || return 255
1069 if ! ./configure --with-linux=${LINUX} --with-linux-obj=${LINUXOBJ:-$LINUX} \
1070 ${spldir:+--with-spl="${spldir}"} 2>&1 ||
1071 ! make dist 2>&1; then
1077 ln -f $pkg/$pkg-*.tar.gz $TOPDIR/SOURCES ||
1078 error "failed to link $pkg/$pkg-*.tar.gz into $TOPDIR/SOURCES"
1079 if [ -f $pkg/scripts/kmodtool ]; then
1080 ln -f $pkg/scripts/kmodtool $TOPDIR/SOURCES/
1090 # set search dir for our own kmodtool to find correct
1092 export KERNELSOURCE=$(dirname ${LINUX})
1093 # Manually build rpms
1094 for spec in $speclist; do
1095 echo "Building RPMs from $pkg/$specdir/$spec"
1096 if ! rpmbuild $rpmb $pkg/$specdir/$spec \
1098 --define "_use_internal_dependency_generator 0" \
1099 --define "require_kdir ${LINUX}" \
1100 ${LINUXOBJ:+--define "require_kobj ${LINUXOBJ}"} \
1101 ${spldir:+--define "require_spldir ${spldir}"} \
1102 --define "kver $kver" \
1103 --define "kernels $kver" \
1104 --define "_tmppath /var/tmp" \
1105 --define "kernelbuildroot $TOPDIR/reused" \
1106 --define "_topdir $TOPDIR" 2>&1; then
1111 # We have built the rpms for the package. Now we need to extract the
1112 # contained files so we can build further things against them
1113 local rpms=$(ls -1 $TOPDIR/RPMS/*/$rpmpkg-*.rpm)
1115 # cpio only extract to pwd so we need to go there.
1118 for rpm in $rpms; do
1119 rpm2cpio $rpm | cpio -id
1122 if [ "$pkg" == "zfs" ]; then
1123 # We also need to extract both the zfs and zfs-devel rpms
1124 # the zfs rpm is needed because it has the actual libraries in
1125 # it and the zfs-devel rpm only has unversioned symlinks to the
1126 # libraries in the zfs rpm
1127 # this will all change one day when we have a libzfs rpm per
1128 # https://github.com/zfsonlinux/zfs/issues/2329
1129 # and it looks like it could be one day soon:
1130 # https://github.com/zfsonlinux/zfs/pull/2341
1131 local devel_rpms=$(ls -1 $TOPDIR/RPMS/*/{$pkg-devel,$pkg-$SPLZFSVER,lib*}-*.rpm)
1132 for rpm in $devel_rpms; do
1133 rpm2cpio $rpm | cpio -id
1135 CONFIGURE_FLAGS="--with-$pkg-devel=$TOPDIR ${CONFIGURE_FLAGS}"
1136 if [ -z "$spldir" ]; then
1137 # if spldir is empty, then we are only building ZFS and need to define SPL config flags
1138 CONFIGURE_FLAGS="--with-spl=$(ls -d $TOPDIR/usr/src/spl-*|tail -1) ${CONFIGURE_FLAGS}"
1139 CONFIGURE_FLAGS="--with-spl-obj=$(ls -d $TOPDIR/usr/src/$pkg-*/$kver*|tail -1) ${CONFIGURE_FLAGS}"
1141 elif [ "$pkg" == "spl" ]; then
1142 spldir="$(ls -d $TOPDIR/usr/src/spl-*|tail -1)"
1146 CONFIGURE_FLAGS="--with-$pkg=$(ls -d $TOPDIR/usr/src/$pkg-*|tail -1) ${CONFIGURE_FLAGS}"
1147 CONFIGURE_FLAGS="--with-$pkg-obj=$(ls -d $TOPDIR/usr/src/$pkg-*/$kver*|tail -1) ${CONFIGURE_FLAGS}"
1157 [ "$STAGEDIR" ] || return 0
1159 rpmdir="${STAGEDIR}/${CANONICAL_TARGET}-${TARGET_ARCH}"
1160 echo "${0##*/}: Copying RPMs into ${rpmdir}"
1161 mkdir -p "${rpmdir}"
1162 for rpm in $(ls RPMS/${TARGET_ARCH}/*.rpm RPMS/noarch/*.rpm); do
1163 cp -v $rpm "${rpmdir}"
1166 cp -v "$LUSTRE" "$STAGEDIR"
1170 set_rpm_smp_type() {
1172 local infact_arch="${TARGET_ARCH}"
1175 [ "$infact_arch" == "i586" ] && infact_arch="i686"
1178 for smp_type in $SMP_ARCHS; do
1179 [ $infact_arch == $smp_type ] && RPMSMPTYPE=smp && break
1182 for smp_type in $BIGSMP_ARCHS; do
1183 [ $infact_arch == $smp_type ] && RPMSMPTYPE=bigsmp && break
1186 for smp_type in $PPC64_ARCHS; do
1187 [ $infact_arch == $smp_type ] && RPMSMPTYPE=ppc64 && break
1190 for smp_type in $DEFAULT_ARCHS; do
1191 [ $infact_arch == $smp_type ] && RPMSMPTYPE=default && break
1196 # This function takes a linux include tree and digs out the linux release
1197 # from it. It is never called directly, only called from the distro
1198 # specific function find_linux_release() in lbuild-{rhel,sles}.
1199 _find_linux_release() {
1201 local LINUXRELEASEHEADER=""
1203 LINUXRELEASEHEADER=$SRC/include/linux/version.h
1204 if [ -s $SRC/include/generated/utsrelease.h ]; then
1205 LINUXRELEASEHEADER=$SRC/include/generated/utsrelease.h
1206 elif [ -s $SRC/include/linux/utsrelease.h ]; then
1207 LINUXRELEASEHEADER=$SRC/include/linux/utsrelease.h
1210 if [ ! -s $LINUXRELEASEHEADER ]; then
1211 fatal 1 "could not find UTS_RELEASE"
1214 sed -ne 's/#define UTS_RELEASE "\(.*\)"$/\1/p' $LINUXRELEASEHEADER
1217 # unpack kernel(/source/devel) RPM
1219 unpack_linux_devel_rpm() {
1220 local kernelrpm="${1}"
1222 [ -f "$kernelrpm" ] || return 255
1223 [ -d $TOPDIR/reused ] || mkdir $TOPDIR/reused || return 255
1225 pushd $TOPDIR/reused &>/dev/null || return 255
1227 if ! rpm2cpio < "$kernelrpm" | cpio -id > /dev/null 2>&1; then
1231 # call a distro specific hook, if available
1232 if type -p unpack_linux_devel_rpm-$DISTROMAJ; then
1233 if ! unpack_linux_devel_rpm-$DISTROMAJ "$kernelrpm"; then
1240 find_linux_devel_paths $TOPDIR/reused
1248 local kib_prefix="$2"
1250 local ofed_type="${4}"
1251 local ofed_version="${5}"
1253 # build kernel-ib{,-devel}/compat-rdma{,-devel}
1256 local OFED_CORE="--with-core-mod --with-ipoib-mod --with-user_mad-mod \
1257 --with-user_access-mod --with-addr_trans-mod --with-innova-flex "
1258 local OFED_HARDWARE="--with-mlx4-mod --with-mlx4_en-mod \
1259 --with-srp-mod --with-iser-mod --with-isert-mod --with-mlx5-mod \
1262 # some I/B drivers are architecture dependent and kernel-ib's configure
1263 # does not figure it out for us ~sigh~
1264 case "$TARGET_ARCH" in
1266 OFED_HARDWARE="$OFED_HARDWARE --with-ehca-mod"
1270 # assume we are just rebuilding the SRPM
1271 local BUILD_TYPE=${BUILD_TYPE:-"--rebuild"}
1272 local SOURCE="${TOPDIR}/OFED/SRPMS/${kib_prefix}-*.src.rpm"
1274 # but switch to building from the SPEC if we need to apply patches
1275 if ls ${TOPDIR}/lustre/contrib/patches/ofed/* >/dev/null; then
1277 rpm --define "_topdir ${TOPDIR}" -ivh $SOURCE
1278 SOURCE="${TOPDIR}/SPECS/${kib_prefix}.spec"
1279 local file ed_fragment1 ed_fragment2 n=1
1280 for file in $(ls ${TOPDIR}/lustre/contrib/patches/ofed/*.patch 2>/dev/null); do
1281 ed_fragment1="$ed_fragment1
1282 Patch$n: ${file%%*/}"
1283 ed_fragment2="$ed_fragment2
1285 cp $file ${TOPDIR}/SOURCES
1288 for file in $(ls ${TOPDIR}/lustre/contrib/patches/ofed/*.ed 2>/dev/null); do
1289 # Only apply the ed-scripts that should be used for the canonical target
1290 # ed-files in ${TOPDIR}/lustre/contrib/patches/ofed/ have to follow the naming
1292 # <two-digits>-<descriptive-name>:<canonical_target_1>: ...:<canonical_target_N>.ed
1293 # To apply the same change to multiple canonical target simply specify
1294 # a list of colon separated canoncial target names in the file name.
1295 echo "$file" | grep -q -e ":${CANONICAL_TARGET}:" \
1296 -e ":${CANONICAL_TARGET}.ed$"
1297 if [ $? -eq 0 ] ; then
1298 ed_fragment3="$ed_fragment3
1304 if [ $n -gt 1 ]; then
1318 local linuxrelease=$(find_linux_release)
1319 # a place to change/add any unique config
1321 ofa|ifs) local K_SRC_OBJ="K_SRC_OBJ"
1322 if ! $RPMBUILD $BUILD_TYPE --define 'build_kernel_ib 1' \
1323 --define 'build_kernel_ib_devel 1' \
1324 ${FIND_REQUIRES:+--define "__find_requires $FIND_REQUIRES"} \
1325 ${FIND_KSYMS_REQUIRES:+--define "__required_ksyms_requires $FIND_KSYMS_REQUIRES"} \
1326 --define "_topdir ${TOPDIR}" --target ${TARGET_ARCH} \
1327 --define "KVERSION ${linuxrelease}" \
1328 --define "$K_SRC ${linux}" \
1329 ${K_SRC_OBJ:+--define "$K_SRC_OBJ ${linux}"} \
1330 ${OFA_KERNEL_RELEASE:+--define "_release $OFA_KERNEL_RELEASE"} \
1331 --define "configure_options --without-quilt $OFED_CORE $OFED_HARDWARE $OFED_ISCSI" \
1332 ${SOURCE} 2>&1; then
1333 fatal 1 "Error building ${kib_rpm}"
1337 if ! $RPMBUILD $BUILD_TYPE \
1338 ${FIND_REQUIRES:+--define "__find_requires $FIND_REQUIRES"} \
1339 ${FIND_KSYMS_REQUIRES:+--define "__required_ksyms_requires $FIND_KSYMS_REQUIRES"} \
1340 ${MOFED_FLAVOR:+--define "flavors_to_build $MOFED_FLAVOR"} \
1341 --define "_topdir ${TOPDIR}" --target ${TARGET_ARCH} \
1342 --define "KVERSION ${linuxrelease}" \
1344 --define "$K_SRC ${linux}" \
1345 ${OFA_KERNEL_RELEASE:+--define "_release $OFA_KERNEL_RELEASE"} \
1346 ${SOURCE} 2>&1; then
1347 fatal 1 "Error building ${kib_rpm}"
1349 # now that we have the kernel rpms, we need to lib rpms too
1350 # we don't have to rebuild since MOFED include the binaries
1351 # Starting from MOFED 5.1, rdma-core is required for libib*
1352 if compare_version 5.1 $ofed_version; then
1353 cp -f OFED_RPMS/rdma-core-*.${TARGET_ARCH}.rpm \
1354 ${TOPDIR}/RPMS/${TARGET_ARCH} || \
1355 fatal 1 "Failed to copy MOFED rpms"
1357 cp -f OFED_RPMS/{libib*,librdmacm*,ibutils*,opensm-*,infiniband-diags*}.${TARGET_ARCH}.rpm \
1358 ${TOPDIR}/RPMS/${TARGET_ARCH} || \
1359 fatal 1 "Failed to copy MOFED rpms"
1369 local signature="$4"
1370 local use_links="$5"
1377 local unique_id=$(hostname -s)
1378 if [ -z "$unique_id" ]; then
1379 fatal 1 "Failed to determine hostname."
1382 local finallocation="$location"/"$signature"/"$module"
1383 location="$location"/"$signature-${unique_id}"/"$module"
1384 mkdir -p "$location"
1385 # the cleanup script removes any directory that doesn't have a
1386 # .lastused, so let's try to prevent that as soon as we can
1387 # this solution still slightly racy with the cleanup script
1388 # but the race is a lot tighter now
1389 touch -t 197001010000 "$location/.lastused"
1390 ## use eval/echo here to make sure shell expansions are performed
1391 #if ! cp -a${linkflag} $(eval echo $articles) "$location"; then
1393 for article in $(eval echo $articles); do
1394 if ! cp -a${linkflag} "$article" "$location"; then
1395 error "Failed to copy \"$article\" to \"$location\" in store_for_reuse()"
1396 # rename the cache location so that it's not cached
1397 # product, but is around for analysis
1398 mv "$location"{,-bad-$(date +%s)} ||
1399 error "failed to clean up a failed cache attempt" \
1400 "in \"$location\" -- manual cleanup will be" \
1406 # flag the cache as complete (i.e. in case lbuild was previously
1407 # interrupted while caching)
1408 touch "$location/.lastused"
1410 # put the temporary location into the final location
1412 mkdir -p "${finallocation%/*}"
1413 mv "$location" "$finallocation"
1414 rmdir "${location%/*}"
1422 local use_links="${3:-false}"
1423 local signature="$4"
1425 if [ -n "$REUSEBUILD" ] && [ -d "$REUSEBUILD/$signature/$module" ]; then
1426 if [ ! -f "$REUSEBUILD/$signature/$module/.lastused" ]; then
1427 # the .lastused flag is populated at the end of the caching to
1428 # signal that the caching was completed. if that flag is not
1429 # there, then the cache is invalid (and should be removed in fact)
1430 mv "$REUSEBUILD/$signature/$module"{,-bad-$(date +%s)} ||
1431 fatal 1 "failed to clean up a bad cache in location $REUSEBUILD/$signature/$module\" -- manual cleanup will be necessary"
1435 # so that we know how stale this entry is
1436 touch $REUSEBUILD/$signature/$module/.lastused
1439 if ls $REUSEBUILD/$signature/$module/* >/dev/null 2>&1; then
1440 cp -al $REUSEBUILD/$signature/$module/* $dest/
1443 # copying is pretty heavy
1444 # cp -a $REUSEBUILD/$signature/$module/* $dest/
1445 # do some creative symlinking instead
1447 for dir in BUILD SRPMS SPECS; do
1448 if ls $REUSEBUILD/$signature/$module/$dir/* >/dev/null 2>&1; then
1449 ln -s $REUSEBUILD/$signature/$module/$dir/* $dest/$dir
1452 # sources have to be copied by file because we need SOURCES to
1453 # be a dir we can write into
1454 # could overrun ls's arg list here
1455 #ls $REUSEBUILD/$signature/$module/SOURCES/* |
1456 find $REUSEBUILD/$signature/$module/SOURCES/ -type f |
1457 xargs ln -t $dest/SOURCES -s
1459 # same for RPMS/* dirs
1460 # could overrun ls's arg list here
1461 #ls $REUSEBUILD/$signature/$module/RPMS/$TARGET_ARCH/* |
1463 for dir in $REUSEBUILD/$signature/$module/RPMS/*; do
1464 mkdir -p $dest/RPMS/${dir##*/}
1466 xargs ln -t $dest/RPMS/${dir##*/} -s
1478 if [[ $arch = i[3456]86 ]]; then
1480 elif [[ $arch = aarch64 ]]; then
1488 build_kernel_with_srpm() {
1491 if [ -z "$outfd" ] || [ $outfd = 1 ]; then
1492 fatal 1 "You must supply a file descriptor to ${FUNCNAME[0]} and it cannot be 1"
1495 # need to generate the patch for this target
1496 do_patch_linux false >&${outfd} # sets global $FULL_PATCH (yeah, yuck)
1498 # get an md5sum of the kernel patch + config for reuse check
1501 local release_str="RELEASE=$RELEASE\n"
1504 if $USE_BUILD_CACHE && [ -n "$REUSEBUILD" ]; then
1505 local REUSE_SIGNATURE=$({ echo -en $release_str;
1508 cat "$TARGET_FILE" |
1509 sed -e '/_VERSION=/s/_[0-9]*_g.*$//g';
1511 cat "$LBUILD_DIR/lbuild";
1512 test -f lbuild-${DISTROMAJ%%[0-9]*} &&
1513 cat lbuild-${DISTROMAJ%%[0-9]*};
1514 cat "$LBUILD_DIR/lbuild-$DISTROMAJ"; } |
1515 md5sum | cut -d" " -f1)
1516 # see if we can link to the reuse pool
1517 # XXX - hrm. i'm not convinced this doesn't belong in the reuse
1519 local CAN_LINK_FOR_REUSE=false
1520 touch $REUSEBUILD/$$
1521 if cp -al $REUSEBUILD/$$ $TOPDIR/ 2>/dev/null; then
1522 CAN_LINK_FOR_REUSE=true
1527 # the extra version string to use for the kernel (which might be a reused
1529 local kernel_extra_version=""
1530 if ! $USE_BUILD_CACHE || ! reuse kernel "$TOPDIR" "$CAN_LINK_FOR_REUSE" \
1531 "$REUSE_SIGNATURE"; then
1532 # nothing cached, build from scratch
1533 echo "Downloading kernel SRPM" >&${outfd}
1534 download_srpm "$CANONICAL_TARGET" "$KERNEL_SRPM" >&${outfd}
1536 if ! rpm -ivh $KERNELDIR/$KERNEL_SRPM \
1537 --define "_topdir $TOPDIR" >&${outfd} 2>&1; then
1538 # should we clean this up or leave it for analysis?
1540 fatal 1 "Error installing kernel SRPM."
1543 # put the Lustre kernel patch into the RPM build tree
1544 cp $FULL_PATCH $TOPDIR/SOURCES/linux-${lnxmaj}-lustre.patch
1545 prepare_and_build_srpm >&${outfd} ||
1546 fatal 1 "failed to prepare_and_build_srpm"
1548 if [ -z "$REUSE_SIGNATURE" ]; then
1549 echo "No reuse signature was caculated so not storing the built kernel" >&${outfd}
1551 # store the resulting kernel RPM build tree for future use
1552 echo "Storing the built kernel for future reuse" >&${outfd}
1553 if ! store_for_reuse "$TOPDIR/{SPECS,SOURCES,SRPMS,RPMS}" \
1554 "kernel" "$REUSEBUILD" "$REUSE_SIGNATURE" \
1555 "$CAN_LINK_FOR_REUSE"; then
1556 error "Failed to store kernel RPMS for reuse"
1557 echo "unknown" >&${outfd}
1563 # figure out the EXTRA_VERSION of the kernel we built or are re-using
1565 if ! KERNEL_RPM=$(find_rpm "$TOPDIR/RPMS/$TARGET_ARCH/" provides "^kernel(-default)? ="); then
1566 fatal 1 "Failed to find a kernel RPM in $TOPDIR/RPMS/$TARGET_ARCH/"
1568 kernel_extra_version=$(rpm -q --queryformat "%{RELEASE}" -p $TOPDIR/RPMS/$TARGET_ARCH/$KERNEL_RPM)
1570 # should now have the following RPMs
1571 # $TOPDIR/RPMS/$arch/kernel-lustre-2.6.18-53.1.21.el5_lustre.1.6.5.1.$arch.rpm
1572 # $TOPDIR/RPMS/$arch/kernel-lustre-devel-2.6.18-53.1.21.el5_lustre.1.6.5.1.$arch.rpm
1573 # $TOPDIR/RPMS/$arch/kernel-lustre-headers-2.6.18-53.1.21.el5_lustre.1.6.5.1.$arch.rpm
1574 # $TOPDIR/RPMS/$arch/kernel-lustre-debuginfo-common-2.6.18-53.1.21.el5_lustre.1.6.5.1.$arch.rpm
1575 # $TOPDIR/RPMS/$arch/kernel-lustre-debuginfo-2.6.18-53.1.21.el5_lustre.1.6.5.1.$arch.rpm
1577 echo $kernel_extra_version
1585 # REUSEBUILD, USE_BUILD_CACHE
1590 local ofed_type="$2"
1591 local ofed_version="$3"
1598 if [ "$ofed_version" = "inkernel" ]; then
1599 # see if there is a distro specific override for this and use
1601 # XXX we need to better integrate a distro specific override with
1602 # the rest of this function so that all of the reuse cache
1603 # stuff is leveraged given that 80% of this function is reuse
1604 if type -p build_ofed-$DISTROMAJ; then
1606 ofed_location=$(build_ofed-$DISTROMAJ ${STDOUT})
1607 local rc=${PIPESTATUS[0]}
1608 CONFIGURE_FLAGS="--with-o2ib=${ofed_location} ${CONFIGURE_FLAGS}"
1615 mlnx) # no compat-rdma for mlnx as of 3.1
1616 kib_prefix="ofa_kernel"
1618 kib_rpm="${pre_prefix}${kib_prefix}"
1621 if compare_version $ofed_version 3.0; then
1622 kib_prefix="ofa_kernel"
1623 kib_rpm="${pre_prefix}${kib_prefix}"
1625 kib_prefix="compat-rdma"
1626 kib_rpm="compat-rdma"
1632 # build kernel-ib/compat-rdma
1633 if $USE_BUILD_CACHE && [ -n "$REUSEBUILD" ]; then
1634 local REUSE_SIGNATURE=$({ echo "$ofed_version";
1635 echo "$(find_linux_release;
1636 echo "$BUILD_GEN")";
1637 cat "${linux}/include/linux/autoconf.h";
1638 cat "$LBUILD_DIR/lbuild";
1639 test -f lbuild-${DISTROMAJ%%[0-9]*} &&
1640 cat lbuild-${DISTROMAJ%%[0-9]*};
1641 cat "$LBUILD_DIR/lbuild-$DISTROMAJ"; } |
1642 md5sum | cut -d" " -f1)
1643 # see if we can link to the reuse pool
1644 # XXX - hrm. i'm not convinced this doesn't belong in the reuse
1646 local CAN_LINK_FOR_REUSE=false
1647 touch $REUSEBUILD/$$
1648 if cp -al $REUSEBUILD/$$ $TOPDIR/; then
1649 CAN_LINK_FOR_REUSE=true
1654 if ! $USE_BUILD_CACHE || ! reuse ofed "$TOPDIR" "$CAN_LINK_FOR_REUSE" \
1655 "$REUSE_SIGNATURE"; then
1656 if [ -n "$REUSE_SIGNATURE" ]; then
1657 # stash away the existing built articles for a moment
1659 mv {BUILD,{S,}RPMS,S{OURCE,PEC}S} bak
1662 find . | cpio -pudlm ..
1666 create_rpmbuild_dirs
1669 build_kernel_ib "${linux}" "${pre_prefix}${kib_prefix}" "${kib_rpm}" \
1670 "${ofed_type}" "${ofed_version}"
1672 if [ -z "$REUSE_SIGNATURE" ]; then
1673 echo "No reuse signature was caculated so not storing the built ofed"
1675 # store the resulting RPM build tree for future use
1676 echo "Storing the built ofed for future reuse"
1677 if ! store_for_reuse "$TOPDIR/{SPECS,SOURCES,BUILD,SRPMS,RPMS}" \
1678 "ofed" "$REUSEBUILD" "$REUSE_SIGNATURE" \
1679 "$CAN_LINK_FOR_REUSE"; then
1680 error "Failed to store OFED RPMS for reuse"
1684 # put the stuff we stashed away back
1689 pushd "$TOPDIR" >/dev/null
1690 rm -rf ${kib_rpm}-devel
1691 mkdir ${kib_rpm}-devel
1695 mlnx) # Prior to MOFED 3.1, we had to use build_kernel_ib=1 to
1696 # build devel rpm. not so after 3.1
1697 if compare_version $ofed_version 3.0; then
1698 rpm=$(ls $TOPDIR/RPMS/*/kernel-ib-devel-${ofed_version%%-*}-*.rpm)
1700 rpm=$(ls $TOPDIR/RPMS/*/${kib_rpm}-devel-${ofed_version%%-*}-*.rpm)
1703 ofa) # Prior to OFA 3.18, we had to use build_kernel_ib=1 during configure,
1705 if compare_version $ofed_version 3.18; then
1706 rpm=$(ls $TOPDIR/RPMS/*/kernel-ib-devel-${ofed_version%%-*}-*.rpm)
1708 rpm=$(ls $TOPDIR/RPMS/*/${kib_rpm}-devel-${ofed_version%%-*}-*.rpm)
1711 ifs) # ifs doesn't follow any convention (if any)
1712 rpm=$(ls $TOPDIR/RPMS/*/${kib_rpm}-devel-*.rpm)
1715 if ! rpm2cpio < $rpm | cpio -id; then
1716 fatal 1 "could not unpack the $rpm."
1718 # find the path (this might not work for ofa and ifs)
1719 o2ib_location=$(find $(pwd)/usr/src/${kib_prefix} -type d -name ofed_scripts)
1720 CONFIGURE_FLAGS="--with-o2ib=$(dirname ${o2ib_location}) ${CONFIGURE_FLAGS}"
1726 local ofed_type="$1"
1727 local ofed_version="$2"
1730 if ! $PATCHLESS; then
1731 if $PATCHLESS_SERVER; then
1732 # need to find and unpack the vendor's own kernel-devel
1733 # for patchless server build
1734 if ! kernelrpm=$(find_linux_rpm "-$DEVEL_KERNEL_TYPE"); then
1735 fatal 1 "Could not find the kernel-$DEVEL_KERNEL_TYPE RPM in $KERNELRPMSBASE/$lnxmaj/$DISTROMAJ"
1737 if ! lnxrel="$lnxrel" unpack_linux_devel_rpm "$kernelrpm" "-"; then
1738 fatal 1 "Could not find the Linux tree in $kernelrpm"
1740 # download and unpack kernel-debuginfo-common (only in EL)
1741 if [[ $DISTROMAJ =~ rhel ]]; then
1742 local KERNEL_DEBUGINFO="kernel-debuginfo-common-${TARGET_ARCH}-${lnxmaj}-${lnxrel}.${TARGET_ARCH}.rpm"
1743 download_debuginfo_common "$KERNEL_DEBUGINFO"
1744 if ! lnxrel="$lnxrel" unpack_linux_devel_rpm \
1745 "$KERNELRPMSBASE/$lnxmaj/$DISTROMAJ/$TARGET_ARCH/$KERNEL_DEBUGINFO"; then
1746 fatal 1 "Could not find the Linux debuginfo common rpm in $KERNELRPMSBASE/$lnxmaj/$DISTROMAJ/$TARGET_ARCH/$KERNEL_DEBUGINFO"
1750 local kernel_extra_version
1751 if ! kernel_extra_version=$(build_kernel_with_srpm ${STDOUT}); then
1752 fatal 1 "Failed to build the kernel from it's SRPM"
1755 local kernel_devel_rpm
1756 if ! kernel_devel_rpm=$(find_rpm "$TOPDIR/RPMS/${TARGET_ARCH}/" provides "^$(devel_kernel_name $KERNEL_LUSTRE_NAMING) ="); then
1757 fatal 1 "Failed to find a kernel development RPM in $TOPDIR/RPMS/${TARGET_ARCH}/"
1760 # install the -devel RPM in preparation for modules builds
1761 if ! lnxrel="$kernel_extra_version" unpack_linux_devel_rpm \
1762 "$TOPDIR/RPMS/${TARGET_ARCH}/$kernel_devel_rpm"; then
1763 fatal 1 "Could not find the Linux tree in $TOPDIR/RPMS/${TARGET_ARCH}/$kernel_devel_rpm"
1767 # need to find and unpack the vendor's own kernel-devel for patchless
1769 if ! kernelrpm=$(find_linux_rpm "-$DEVEL_KERNEL_TYPE"); then
1770 fatal 1 "Could not find the kernel-$DEVEL_KERNEL_TYPE RPM in $KERNELRPMSBASE/$lnxmaj/$DISTROMAJ"
1772 if ! lnxrel="$lnxrel" unpack_linux_devel_rpm "$kernelrpm" "-"; then
1773 fatal 1 "Could not find the Linux tree in $kernelrpm"
1777 # ~sigh~ have to make copies of and modify some of the rpm
1778 # infrastructure files so that find-requires can find our unpacked
1779 # kernel-devel artifacts
1780 cp $RPM_HELPERS_DIR/{symset-table,find-requires{,.ksyms}} .
1781 export FIND_REQUIRES="$(pwd)/find-requires"
1782 export FIND_KSYMS_REQUIRES="$(pwd)/find-requires.ksyms"
1783 chmod 755 {symset-table,find-requires{,.ksyms}}
1785 tmp="${tmp//\//\\/}"
1786 sed -i "s/\/.*find-requires.ksyms/$tmp\/find-requires.ksyms/g" find-requires
1787 sed -i "s/\/usr\/src\/kernels/$tmp\/reused\/usr\/src\/kernels/" find-requires.ksyms
1788 sed -i "s/\/boot/$tmp\/reused\/boot/; s/\/usr\/src\/kernels/$tmp\/reused\/usr\/src\/kernels/" symset-table
1790 build_ofed "${LINUXOBJ:-$LINUX}" "$ofed_type" "$ofed_version" ||
1791 fatal 1 "error building OFED"
1794 if build_lustre "$LINUX" "$LINUXOBJ"; then
1795 # the build worked. resolve any symlinked files (i.e. from reuse)
1796 # in RPMS/$arch to real files so that that that huge mess of
1797 # complication known as LTS can copy them yet somewhere else.
1798 # is it any wonder this whole process is so damn so? anyone ever
1799 # heard of hardlinks? it's this cool new thing that allows you save
1800 # tons of time and space by creating... well you can go read about
1801 # them if you have not heard about them yet.
1802 # can i say how much the implemenation of all of this really impedes
1805 for dir in RPMS/*; do
1807 for file in $(ls); do
1808 if [ -h $file ]; then
1815 # also, for i?86, make sure all of the RPMs are in RPMS/$TARGET_ARCH
1816 # as that's where LTS expects to find them
1817 for dir in RPMS/*; do
1818 if [ $dir = RPMS/$TARGET_ARCH ]; then
1823 if [ -n "$files" ]; then
1824 cp -al $files ../$TARGET_ARCH
1834 create_rpmbuild_dirs() {
1836 [ -d RPMS ] || mkdir RPMS
1837 [ -d RPMS/${TARGET_ARCH} ] || mkdir RPMS/${TARGET_ARCH}
1838 [ -d RPMS/noarch ] || mkdir RPMS/noarch
1839 [ -d BUILD ] || mkdir BUILD
1840 [ -d SOURCES ] || mkdir SOURCES
1841 [ -d SPECS ] || mkdir SPECS
1842 [ -d SRPMS ] || mkdir SRPMS
1864 [[ $list\ == *\ $item\ * ]]
1868 #########################################################################
1869 # Generate a backtrace through the call stack.
1873 #########################################################################
1877 local funcname="" sourcefile="" lineno="" n
1879 echo "Call stack: (most recent first)"
1880 for (( n = $strip ; n < ${#FUNCNAME[@]} ; ++n )) ; do
1881 funcname=${FUNCNAME[$n - 1]}
1882 sourcefile=$(basename ${BASH_SOURCE[$n]})
1883 lineno=${BASH_LINENO[$n - 1]}
1887 # Display function arguments
1888 if [[ ! -z "${BASH_ARGV[@]}" ]]; then
1889 local args newarg j p=0
1890 for (( j = ${BASH_ARGC[$n - 1]}; j > 0; j-- )); do
1891 newarg=${BASH_ARGV[$j + $p - 1]}
1892 args="${args:+${args} }'${newarg}'"
1894 let p+=${BASH_ARGC[$n - 1]}
1896 echo " ${funcname} ${args:+${args} }at ${sourcefile}:${lineno}"
1900 echo "BEGIN BACKTRACE"
1902 #echo ${BASH_LINENO[*]}
1903 #echo ${BASH_SOURCE[*]}
1904 #echo ${FUNCNAME[*]}
1905 local i=$((${#FUNCNAME[@]} - 1))
1906 while [ $i -ge 0 ]; do
1907 local lineno=${BASH_LINENO[$i]}
1911 local SOURCELINE="${BASH_SOURCE[$i + 1]}:${lineno}"
1912 # Can't figure out how to get function args from other frames...
1913 local FUNCTION="${FUNCNAME[$i]}()"
1914 echo "$SOURCELINE:$FUNCTION"
1918 echo "END BACKTRACE"
1924 seen_list=$(new_list)
1926 echo "An unexpected error has occurred at ${BASH_SOURCE[0]##*/}:$((LINENO-1)).
1927 Unfortunately the above line number in the message may or may not be correct,
1928 but details have been send to the lbuild maintainer. Attempting to continue."; (echo "Untrapped error"
1930 # have we seen this one
1931 echo "checking seen list for ${BASH_SOURCE[0]}:${BASH_LINENO[0]}"
1933 if is_list_member "$seen_list" "${BASH_SOURCE[0]}:${BASH_LINENO[0]}"; then
1934 echo "seen this one already"
1936 seen_list=$(add_list "$seen_list" "${BASH_SOURCE[0]}:${BASH_LINENO[0]}")
1939 ) ; set $xtrace' ERR
1942 [ -r ~/.lbuildrc ] && . ~/.lbuildrc
1944 options=$(getopt -o D:h -l kerneltree:,distro:,kernelrpm:,reusebuild:,\
1945 patchless,patchless-server,enable-kernel-debug,ccache,norpm,external-patches:,timestamp:,\
1946 extraversion:,kerneldir:,linux:,lustre:,nodownload,nosrc,noiokit,ofed-type:,\
1947 ofed-version:,mlnx-version:,ofed-src:,publish,disable-zfs,release,set-value:,\
1948 src,stage:,target:,with-linux:,xen -- "$@")
1950 if [ $? != 0 ]; then
1954 eval set -- "$options"
1985 if ! KERNELTREE=$(canon_path "$2"); then
1986 fatal 1 "Could not determine the canonical location of $2"
1990 --linux | --with-linux)
1991 if ! LINUX=$(canon_path "$2"); then
1992 fatal 1 "Could not determine the canonical location of $2"
2001 if ! REUSEBUILD=$(canon_path "$2"); then
2002 fatal 1 "Could not determine the canonical location of $2"
2018 PATCHLESS_SERVER=true
2021 --enable-kernel-debug)
2022 ENABLE_KERNEL_DEBUG=true
2026 if ! KERNELRPMSBASE=$(canon_path "$2"); then
2027 fatal 1 "Could not determine the canonical location of $2"
2036 if ! LUSTRE=$(canon_filepath "$2"); then
2037 fatal 1 "Could not determine the canonical location of $2"
2094 # there are actually some lustre configure flags that we need to
2095 # handle ourselves (but we still give them to configure)
2096 if [[ \ $@\ == *\ --disable-tests\ * ]]; then
2103 usage 1 "Unrecognized option: $1"
2114 if [ -n "$OFED_TYPE" -a "$OFED_TYPE" != "inkernel" ]; then
2115 download_ofed "$OFED_TYPE" "$OFED_VERSION"
2116 unpack_ofed "$OFED_TYPE" "$OFED_VERSION" || fatal 1 "Error unpacking OFED tarball"
2119 # make sure the RPM build environment is set up
2120 create_rpmbuild_dirs
2122 # if an unpacked kernel source tree was given on the command line
2123 # just build lustre with it (nothing distro kernel specific here)
2124 if [ -n "$LINUX" ]; then
2125 find_linux_release() {
2126 _find_linux_release $LINUX
2128 build_ofed "${LINUXOBJ:-$LINUX}" "$OFED_TYPE" "$OFED_VERSION" ||
2129 fatal 1 "error building OFED"
2130 build_lustre "$LINUX" "$LINUXOBJ"
2132 if [ ! -f "${LBUILD_DIR}/lbuild-$DISTROMAJ" ]; then
2133 fatal 1 "${LBUILD_DIR}/lbuild-$DISTROMAJ not found"
2135 source ${LBUILD_DIR}/lbuild-$DISTROMAJ
2136 build_with_srpm "$OFED_TYPE" "$OFED_VERSION" || fatal 1 "Failed to build_with_srpm"