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.2}
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 --define "_topdir ${TOPDIR}" --target ${TARGET_ARCH} \
1341 --define "KVERSION ${linuxrelease}" \
1343 --define "$K_SRC ${linux}" \
1344 ${OFA_KERNEL_RELEASE:+--define "_release $OFA_KERNEL_RELEASE"} \
1345 ${SOURCE} 2>&1; then
1346 fatal 1 "Error building ${kib_rpm}"
1348 # now that we have the kernel rpms, we need to lib rpms too
1349 # we don't have to rebuild since MOFED include the binaries
1350 # Starting from MOFED 5.1, rdma-core is required for libib*
1351 if compare_version 5.1 $ofed_version; then
1352 cp -f OFED_RPMS/rdma-core-*.${TARGET_ARCH}.rpm \
1353 ${TOPDIR}/RPMS/${TARGET_ARCH} || \
1354 fatal 1 "Failed to copy MOFED rpms"
1356 cp -f OFED_RPMS/{libib*,librdmacm*,ibutils*,opensm-*,infiniband-diags*}.${TARGET_ARCH}.rpm \
1357 ${TOPDIR}/RPMS/${TARGET_ARCH} || \
1358 fatal 1 "Failed to copy MOFED rpms"
1368 local signature="$4"
1369 local use_links="$5"
1376 local unique_id=$(hostname -s)
1377 if [ -z "$unique_id" ]; then
1378 fatal 1 "Failed to determine hostname."
1381 local finallocation="$location"/"$signature"/"$module"
1382 location="$location"/"$signature-${unique_id}"/"$module"
1383 mkdir -p "$location"
1384 # the cleanup script removes any directory that doesn't have a
1385 # .lastused, so let's try to prevent that as soon as we can
1386 # this solution still slightly racy with the cleanup script
1387 # but the race is a lot tighter now
1388 touch -t 197001010000 "$location/.lastused"
1389 ## use eval/echo here to make sure shell expansions are performed
1390 #if ! cp -a${linkflag} $(eval echo $articles) "$location"; then
1392 for article in $(eval echo $articles); do
1393 if ! cp -a${linkflag} "$article" "$location"; then
1394 error "Failed to copy \"$article\" to \"$location\" in store_for_reuse()"
1395 # rename the cache location so that it's not cached
1396 # product, but is around for analysis
1397 mv "$location"{,-bad-$(date +%s)} ||
1398 error "failed to clean up a failed cache attempt" \
1399 "in \"$location\" -- manual cleanup will be" \
1405 # flag the cache as complete (i.e. in case lbuild was previously
1406 # interrupted while caching)
1407 touch "$location/.lastused"
1409 # put the temporary location into the final location
1411 mkdir -p "${finallocation%/*}"
1412 mv "$location" "$finallocation"
1413 rmdir "${location%/*}"
1421 local use_links="${3:-false}"
1422 local signature="$4"
1424 if [ -n "$REUSEBUILD" ] && [ -d "$REUSEBUILD/$signature/$module" ]; then
1425 if [ ! -f "$REUSEBUILD/$signature/$module/.lastused" ]; then
1426 # the .lastused flag is populated at the end of the caching to
1427 # signal that the caching was completed. if that flag is not
1428 # there, then the cache is invalid (and should be removed in fact)
1429 mv "$REUSEBUILD/$signature/$module"{,-bad-$(date +%s)} ||
1430 fatal 1 "failed to clean up a bad cache in location $REUSEBUILD/$signature/$module\" -- manual cleanup will be necessary"
1434 # so that we know how stale this entry is
1435 touch $REUSEBUILD/$signature/$module/.lastused
1438 if ls $REUSEBUILD/$signature/$module/* >/dev/null 2>&1; then
1439 cp -al $REUSEBUILD/$signature/$module/* $dest/
1442 # copying is pretty heavy
1443 # cp -a $REUSEBUILD/$signature/$module/* $dest/
1444 # do some creative symlinking instead
1446 for dir in BUILD SRPMS SPECS; do
1447 if ls $REUSEBUILD/$signature/$module/$dir/* >/dev/null 2>&1; then
1448 ln -s $REUSEBUILD/$signature/$module/$dir/* $dest/$dir
1451 # sources have to be copied by file because we need SOURCES to
1452 # be a dir we can write into
1453 # could overrun ls's arg list here
1454 #ls $REUSEBUILD/$signature/$module/SOURCES/* |
1455 find $REUSEBUILD/$signature/$module/SOURCES/ -type f |
1456 xargs ln -t $dest/SOURCES -s
1458 # same for RPMS/* dirs
1459 # could overrun ls's arg list here
1460 #ls $REUSEBUILD/$signature/$module/RPMS/$TARGET_ARCH/* |
1462 for dir in $REUSEBUILD/$signature/$module/RPMS/*; do
1463 mkdir -p $dest/RPMS/${dir##*/}
1465 xargs ln -t $dest/RPMS/${dir##*/} -s
1477 if [[ $arch = i[3456]86 ]]; then
1479 elif [[ $arch = aarch64 ]]; then
1487 build_kernel_with_srpm() {
1490 if [ -z "$outfd" ] || [ $outfd = 1 ]; then
1491 fatal 1 "You must supply a file descriptor to ${FUNCNAME[0]} and it cannot be 1"
1494 # need to generate the patch for this target
1495 do_patch_linux false >&${outfd} # sets global $FULL_PATCH (yeah, yuck)
1497 # get an md5sum of the kernel patch + config for reuse check
1500 local release_str="RELEASE=$RELEASE\n"
1503 if $USE_BUILD_CACHE && [ -n "$REUSEBUILD" ]; then
1504 local REUSE_SIGNATURE=$({ echo -en $release_str;
1507 cat "$TARGET_FILE" |
1508 sed -e '/_VERSION=/s/_[0-9]*_g.*$//g';
1510 cat "$LBUILD_DIR/lbuild";
1511 test -f lbuild-${DISTROMAJ%%[0-9]*} &&
1512 cat lbuild-${DISTROMAJ%%[0-9]*};
1513 cat "$LBUILD_DIR/lbuild-$DISTROMAJ"; } |
1514 md5sum | cut -d" " -f1)
1515 # see if we can link to the reuse pool
1516 # XXX - hrm. i'm not convinced this doesn't belong in the reuse
1518 local CAN_LINK_FOR_REUSE=false
1519 touch $REUSEBUILD/$$
1520 if cp -al $REUSEBUILD/$$ $TOPDIR/ 2>/dev/null; then
1521 CAN_LINK_FOR_REUSE=true
1526 # the extra version string to use for the kernel (which might be a reused
1528 local kernel_extra_version=""
1529 if ! $USE_BUILD_CACHE || ! reuse kernel "$TOPDIR" "$CAN_LINK_FOR_REUSE" \
1530 "$REUSE_SIGNATURE"; then
1531 # nothing cached, build from scratch
1532 echo "Downloading kernel SRPM" >&${outfd}
1533 download_srpm "$CANONICAL_TARGET" "$KERNEL_SRPM" >&${outfd}
1535 if ! rpm -ivh $KERNELDIR/$KERNEL_SRPM \
1536 --define "_topdir $TOPDIR" >&${outfd} 2>&1; then
1537 # should we clean this up or leave it for analysis?
1539 fatal 1 "Error installing kernel SRPM."
1542 # put the Lustre kernel patch into the RPM build tree
1543 cp $FULL_PATCH $TOPDIR/SOURCES/linux-${lnxmaj}-lustre.patch
1544 prepare_and_build_srpm >&${outfd} ||
1545 fatal 1 "failed to prepare_and_build_srpm"
1547 if [ -z "$REUSE_SIGNATURE" ]; then
1548 echo "No reuse signature was caculated so not storing the built kernel" >&${outfd}
1550 # store the resulting kernel RPM build tree for future use
1551 echo "Storing the built kernel for future reuse" >&${outfd}
1552 if ! store_for_reuse "$TOPDIR/{SPECS,SOURCES,SRPMS,RPMS}" \
1553 "kernel" "$REUSEBUILD" "$REUSE_SIGNATURE" \
1554 "$CAN_LINK_FOR_REUSE"; then
1555 error "Failed to store kernel RPMS for reuse"
1556 echo "unknown" >&${outfd}
1562 # figure out the EXTRA_VERSION of the kernel we built or are re-using
1564 if ! KERNEL_RPM=$(find_rpm "$TOPDIR/RPMS/$TARGET_ARCH/" provides "^kernel(-default)? ="); then
1565 fatal 1 "Failed to find a kernel RPM in $TOPDIR/RPMS/$TARGET_ARCH/"
1567 kernel_extra_version=$(rpm -q --queryformat "%{RELEASE}" -p $TOPDIR/RPMS/$TARGET_ARCH/$KERNEL_RPM)
1569 # should now have the following RPMs
1570 # $TOPDIR/RPMS/$arch/kernel-lustre-2.6.18-53.1.21.el5_lustre.1.6.5.1.$arch.rpm
1571 # $TOPDIR/RPMS/$arch/kernel-lustre-devel-2.6.18-53.1.21.el5_lustre.1.6.5.1.$arch.rpm
1572 # $TOPDIR/RPMS/$arch/kernel-lustre-headers-2.6.18-53.1.21.el5_lustre.1.6.5.1.$arch.rpm
1573 # $TOPDIR/RPMS/$arch/kernel-lustre-debuginfo-common-2.6.18-53.1.21.el5_lustre.1.6.5.1.$arch.rpm
1574 # $TOPDIR/RPMS/$arch/kernel-lustre-debuginfo-2.6.18-53.1.21.el5_lustre.1.6.5.1.$arch.rpm
1576 echo $kernel_extra_version
1584 # REUSEBUILD, USE_BUILD_CACHE
1589 local ofed_type="$2"
1590 local ofed_version="$3"
1597 if [ "$ofed_version" = "inkernel" ]; then
1598 # see if there is a distro specific override for this and use
1600 # XXX we need to better integrate a distro specific override with
1601 # the rest of this function so that all of the reuse cache
1602 # stuff is leveraged given that 80% of this function is reuse
1603 if type -p build_ofed-$DISTROMAJ; then
1605 ofed_location=$(build_ofed-$DISTROMAJ ${STDOUT})
1606 local rc=${PIPESTATUS[0]}
1607 CONFIGURE_FLAGS="--with-o2ib=${ofed_location} ${CONFIGURE_FLAGS}"
1614 mlnx) # no compat-rdma for mlnx as of 3.1
1615 kib_prefix="ofa_kernel"
1617 kib_rpm="${pre_prefix}${kib_prefix}"
1620 if compare_version $ofed_version 3.0; then
1621 kib_prefix="ofa_kernel"
1622 kib_rpm="${pre_prefix}${kib_prefix}"
1624 kib_prefix="compat-rdma"
1625 kib_rpm="compat-rdma"
1631 # build kernel-ib/compat-rdma
1632 if $USE_BUILD_CACHE && [ -n "$REUSEBUILD" ]; then
1633 local REUSE_SIGNATURE=$({ echo "$ofed_version";
1634 echo "$(find_linux_release;
1635 echo "$BUILD_GEN")";
1636 cat "${linux}/include/linux/autoconf.h";
1637 cat "$LBUILD_DIR/lbuild";
1638 test -f lbuild-${DISTROMAJ%%[0-9]*} &&
1639 cat lbuild-${DISTROMAJ%%[0-9]*};
1640 cat "$LBUILD_DIR/lbuild-$DISTROMAJ"; } |
1641 md5sum | cut -d" " -f1)
1642 # see if we can link to the reuse pool
1643 # XXX - hrm. i'm not convinced this doesn't belong in the reuse
1645 local CAN_LINK_FOR_REUSE=false
1646 touch $REUSEBUILD/$$
1647 if cp -al $REUSEBUILD/$$ $TOPDIR/; then
1648 CAN_LINK_FOR_REUSE=true
1653 if ! $USE_BUILD_CACHE || ! reuse ofed "$TOPDIR" "$CAN_LINK_FOR_REUSE" \
1654 "$REUSE_SIGNATURE"; then
1655 if [ -n "$REUSE_SIGNATURE" ]; then
1656 # stash away the existing built articles for a moment
1658 mv {BUILD,{S,}RPMS,S{OURCE,PEC}S} bak
1661 find . | cpio -pudlm ..
1665 create_rpmbuild_dirs
1668 build_kernel_ib "${linux}" "${pre_prefix}${kib_prefix}" "${kib_rpm}" \
1669 "${ofed_type}" "${ofed_version}"
1671 if [ -z "$REUSE_SIGNATURE" ]; then
1672 echo "No reuse signature was caculated so not storing the built ofed"
1674 # store the resulting RPM build tree for future use
1675 echo "Storing the built ofed for future reuse"
1676 if ! store_for_reuse "$TOPDIR/{SPECS,SOURCES,BUILD,SRPMS,RPMS}" \
1677 "ofed" "$REUSEBUILD" "$REUSE_SIGNATURE" \
1678 "$CAN_LINK_FOR_REUSE"; then
1679 error "Failed to store OFED RPMS for reuse"
1683 # put the stuff we stashed away back
1688 pushd "$TOPDIR" >/dev/null
1689 rm -rf ${kib_rpm}-devel
1690 mkdir ${kib_rpm}-devel
1694 mlnx) # Prior to MOFED 3.1, we had to use build_kernel_ib=1 to
1695 # build devel rpm. not so after 3.1
1696 if compare_version $ofed_version 3.0; then
1697 rpm=$(ls $TOPDIR/RPMS/*/kernel-ib-devel-${ofed_version%%-*}-*.rpm)
1699 rpm=$(ls $TOPDIR/RPMS/*/${kib_rpm}-devel-${ofed_version%%-*}-*.rpm)
1702 ofa) # Prior to OFA 3.18, we had to use build_kernel_ib=1 during configure,
1704 if compare_version $ofed_version 3.18; then
1705 rpm=$(ls $TOPDIR/RPMS/*/kernel-ib-devel-${ofed_version%%-*}-*.rpm)
1707 rpm=$(ls $TOPDIR/RPMS/*/${kib_rpm}-devel-${ofed_version%%-*}-*.rpm)
1710 ifs) # ifs doesn't follow any convention (if any)
1711 rpm=$(ls $TOPDIR/RPMS/*/${kib_rpm}-devel-*.rpm)
1714 if ! rpm2cpio < $rpm | cpio -id; then
1715 fatal 1 "could not unpack the $rpm."
1717 # find the path (this might not work for ofa and ifs)
1718 o2ib_location=$(find $(pwd)/usr/src/${kib_prefix} -type d -name ofed_scripts)
1719 CONFIGURE_FLAGS="--with-o2ib=$(dirname ${o2ib_location}) ${CONFIGURE_FLAGS}"
1725 local ofed_type="$1"
1726 local ofed_version="$2"
1729 if ! $PATCHLESS; then
1730 if $PATCHLESS_SERVER; then
1731 # need to find and unpack the vendor's own kernel-devel
1732 # for patchless server build
1733 if ! kernelrpm=$(find_linux_rpm "-$DEVEL_KERNEL_TYPE"); then
1734 fatal 1 "Could not find the kernel-$DEVEL_KERNEL_TYPE RPM in $KERNELRPMSBASE/$lnxmaj/$DISTROMAJ"
1736 if ! lnxrel="$lnxrel" unpack_linux_devel_rpm "$kernelrpm" "-"; then
1737 fatal 1 "Could not find the Linux tree in $kernelrpm"
1739 # download and unpack kernel-debuginfo-common (only in EL)
1740 if [[ $DISTROMAJ =~ rhel ]]; then
1741 local KERNEL_DEBUGINFO="kernel-debuginfo-common-${TARGET_ARCH}-${lnxmaj}-${lnxrel}.${TARGET_ARCH}.rpm"
1742 download_debuginfo_common "$KERNEL_DEBUGINFO"
1743 if ! lnxrel="$lnxrel" unpack_linux_devel_rpm \
1744 "$KERNELRPMSBASE/$lnxmaj/$DISTROMAJ/$TARGET_ARCH/$KERNEL_DEBUGINFO"; then
1745 fatal 1 "Could not find the Linux debuginfo common rpm in $KERNELRPMSBASE/$lnxmaj/$DISTROMAJ/$TARGET_ARCH/$KERNEL_DEBUGINFO"
1749 local kernel_extra_version
1750 if ! kernel_extra_version=$(build_kernel_with_srpm ${STDOUT}); then
1751 fatal 1 "Failed to build the kernel from it's SRPM"
1754 local kernel_devel_rpm
1755 if ! kernel_devel_rpm=$(find_rpm "$TOPDIR/RPMS/${TARGET_ARCH}/" provides "^$(devel_kernel_name $KERNEL_LUSTRE_NAMING) ="); then
1756 fatal 1 "Failed to find a kernel development RPM in $TOPDIR/RPMS/${TARGET_ARCH}/"
1759 # install the -devel RPM in preparation for modules builds
1760 if ! lnxrel="$kernel_extra_version" unpack_linux_devel_rpm \
1761 "$TOPDIR/RPMS/${TARGET_ARCH}/$kernel_devel_rpm"; then
1762 fatal 1 "Could not find the Linux tree in $TOPDIR/RPMS/${TARGET_ARCH}/$kernel_devel_rpm"
1766 # need to find and unpack the vendor's own kernel-devel for patchless
1768 if ! kernelrpm=$(find_linux_rpm "-$DEVEL_KERNEL_TYPE"); then
1769 fatal 1 "Could not find the kernel-$DEVEL_KERNEL_TYPE RPM in $KERNELRPMSBASE/$lnxmaj/$DISTROMAJ"
1771 if ! lnxrel="$lnxrel" unpack_linux_devel_rpm "$kernelrpm" "-"; then
1772 fatal 1 "Could not find the Linux tree in $kernelrpm"
1776 # ~sigh~ have to make copies of and modify some of the rpm
1777 # infrastructure files so that find-requires can find our unpacked
1778 # kernel-devel artifacts
1779 cp $RPM_HELPERS_DIR/{symset-table,find-requires{,.ksyms}} .
1780 export FIND_REQUIRES="$(pwd)/find-requires"
1781 export FIND_KSYMS_REQUIRES="$(pwd)/find-requires.ksyms"
1782 chmod 755 {symset-table,find-requires{,.ksyms}}
1784 tmp="${tmp//\//\\/}"
1785 sed -i "s/\/.*find-requires.ksyms/$tmp\/find-requires.ksyms/g" find-requires
1786 sed -i "s/\/usr\/src\/kernels/$tmp\/reused\/usr\/src\/kernels/" find-requires.ksyms
1787 sed -i "s/\/boot/$tmp\/reused\/boot/; s/\/usr\/src\/kernels/$tmp\/reused\/usr\/src\/kernels/" symset-table
1789 build_ofed "${LINUXOBJ:-$LINUX}" "$ofed_type" "$ofed_version" ||
1790 fatal 1 "error building OFED"
1793 if build_lustre "$LINUX" "$LINUXOBJ"; then
1794 # the build worked. resolve any symlinked files (i.e. from reuse)
1795 # in RPMS/$arch to real files so that that that huge mess of
1796 # complication known as LTS can copy them yet somewhere else.
1797 # is it any wonder this whole process is so damn so? anyone ever
1798 # heard of hardlinks? it's this cool new thing that allows you save
1799 # tons of time and space by creating... well you can go read about
1800 # them if you have not heard about them yet.
1801 # can i say how much the implemenation of all of this really impedes
1804 for dir in RPMS/*; do
1806 for file in $(ls); do
1807 if [ -h $file ]; then
1814 # also, for i?86, make sure all of the RPMs are in RPMS/$TARGET_ARCH
1815 # as that's where LTS expects to find them
1816 for dir in RPMS/*; do
1817 if [ $dir = RPMS/$TARGET_ARCH ]; then
1822 if [ -n "$files" ]; then
1823 cp -al $files ../$TARGET_ARCH
1833 create_rpmbuild_dirs() {
1835 [ -d RPMS ] || mkdir RPMS
1836 [ -d RPMS/${TARGET_ARCH} ] || mkdir RPMS/${TARGET_ARCH}
1837 [ -d RPMS/noarch ] || mkdir RPMS/noarch
1838 [ -d BUILD ] || mkdir BUILD
1839 [ -d SOURCES ] || mkdir SOURCES
1840 [ -d SPECS ] || mkdir SPECS
1841 [ -d SRPMS ] || mkdir SRPMS
1863 [[ $list\ == *\ $item\ * ]]
1867 #########################################################################
1868 # Generate a backtrace through the call stack.
1872 #########################################################################
1876 local funcname="" sourcefile="" lineno="" n
1878 echo "Call stack: (most recent first)"
1879 for (( n = $strip ; n < ${#FUNCNAME[@]} ; ++n )) ; do
1880 funcname=${FUNCNAME[$n - 1]}
1881 sourcefile=$(basename ${BASH_SOURCE[$n]})
1882 lineno=${BASH_LINENO[$n - 1]}
1886 # Display function arguments
1887 if [[ ! -z "${BASH_ARGV[@]}" ]]; then
1888 local args newarg j p=0
1889 for (( j = ${BASH_ARGC[$n - 1]}; j > 0; j-- )); do
1890 newarg=${BASH_ARGV[$j + $p - 1]}
1891 args="${args:+${args} }'${newarg}'"
1893 let p+=${BASH_ARGC[$n - 1]}
1895 echo " ${funcname} ${args:+${args} }at ${sourcefile}:${lineno}"
1899 echo "BEGIN BACKTRACE"
1901 #echo ${BASH_LINENO[*]}
1902 #echo ${BASH_SOURCE[*]}
1903 #echo ${FUNCNAME[*]}
1904 local i=$((${#FUNCNAME[@]} - 1))
1905 while [ $i -ge 0 ]; do
1906 local lineno=${BASH_LINENO[$i]}
1910 local SOURCELINE="${BASH_SOURCE[$i + 1]}:${lineno}"
1911 # Can't figure out how to get function args from other frames...
1912 local FUNCTION="${FUNCNAME[$i]}()"
1913 echo "$SOURCELINE:$FUNCTION"
1917 echo "END BACKTRACE"
1923 seen_list=$(new_list)
1925 echo "An unexpected error has occurred at ${BASH_SOURCE[0]##*/}:$((LINENO-1)).
1926 Unfortunately the above line number in the message may or may not be correct,
1927 but details have been send to the lbuild maintainer. Attempting to continue."; (echo "Untrapped error"
1929 # have we seen this one
1930 echo "checking seen list for ${BASH_SOURCE[0]}:${BASH_LINENO[0]}"
1932 if is_list_member "$seen_list" "${BASH_SOURCE[0]}:${BASH_LINENO[0]}"; then
1933 echo "seen this one already"
1935 seen_list=$(add_list "$seen_list" "${BASH_SOURCE[0]}:${BASH_LINENO[0]}")
1938 ) ; set $xtrace' ERR
1941 [ -r ~/.lbuildrc ] && . ~/.lbuildrc
1943 options=$(getopt -o D:h -l kerneltree:,distro:,kernelrpm:,reusebuild:,\
1944 patchless,patchless-server,enable-kernel-debug,ccache,norpm,external-patches:,timestamp:,\
1945 extraversion:,kerneldir:,linux:,lustre:,nodownload,nosrc,noiokit,ofed-type:,\
1946 ofed-version:,mlnx-version:,ofed-src:,publish,disable-zfs,release,set-value:,\
1947 src,stage:,target:,with-linux:,xen -- "$@")
1949 if [ $? != 0 ]; then
1953 eval set -- "$options"
1984 if ! KERNELTREE=$(canon_path "$2"); then
1985 fatal 1 "Could not determine the canonical location of $2"
1989 --linux | --with-linux)
1990 if ! LINUX=$(canon_path "$2"); then
1991 fatal 1 "Could not determine the canonical location of $2"
2000 if ! REUSEBUILD=$(canon_path "$2"); then
2001 fatal 1 "Could not determine the canonical location of $2"
2017 PATCHLESS_SERVER=true
2020 --enable-kernel-debug)
2021 ENABLE_KERNEL_DEBUG=true
2025 if ! KERNELRPMSBASE=$(canon_path "$2"); then
2026 fatal 1 "Could not determine the canonical location of $2"
2035 if ! LUSTRE=$(canon_filepath "$2"); then
2036 fatal 1 "Could not determine the canonical location of $2"
2093 # there are actually some lustre configure flags that we need to
2094 # handle ourselves (but we still give them to configure)
2095 if [[ \ $@\ == *\ --disable-tests\ * ]]; then
2102 usage 1 "Unrecognized option: $1"
2113 if [ -n "$OFED_TYPE" -a "$OFED_TYPE" != "inkernel" ]; then
2114 download_ofed "$OFED_TYPE" "$OFED_VERSION"
2115 unpack_ofed "$OFED_TYPE" "$OFED_VERSION" || fatal 1 "Error unpacking OFED tarball"
2118 # make sure the RPM build environment is set up
2119 create_rpmbuild_dirs
2121 # if an unpacked kernel source tree was given on the command line
2122 # just build lustre with it (nothing distro kernel specific here)
2123 if [ -n "$LINUX" ]; then
2124 find_linux_release() {
2125 _find_linux_release $LINUX
2127 build_ofed "${LINUXOBJ:-$LINUX}" "$OFED_TYPE" "$OFED_VERSION" ||
2128 fatal 1 "error building OFED"
2129 build_lustre "$LINUX" "$LINUXOBJ"
2131 if [ ! -f "${LBUILD_DIR}/lbuild-$DISTROMAJ" ]; then
2132 fatal 1 "${LBUILD_DIR}/lbuild-$DISTROMAJ not found"
2134 source ${LBUILD_DIR}/lbuild-$DISTROMAJ
2135 build_with_srpm "$OFED_TYPE" "$OFED_VERSION" || fatal 1 "Failed to build_with_srpm"