Viewing: lustre-lnet.m4

# SPDX-License-Identifier: GPL-2.0

#
# This file is part of Lustre, http://www.lustre.org/
#

# LN_CONFIG_BACKOFF
#
# check if tunable tcp backoff is available/wanted
#
AC_DEFUN([LN_CONFIG_BACKOFF], [
AC_MSG_CHECKING([whether to enable tunable backoff TCP support])
AC_ARG_ENABLE([backoff],
	AS_HELP_STRING([--disable-backoff],
		[disable socknal tunable backoff]),
	[], [enable_backoff="yes"])
AC_MSG_RESULT([$enable_backoff])
AS_IF([test "x$enable_backoff" = xyes], [
	AC_MSG_CHECKING([if Linux kernel has tunable backoff TCP support])
	AS_IF([grep -c TCP_BACKOFF $LINUX/include/linux/tcp.h >/dev/null], [
		AC_MSG_RESULT([yes])
		AC_DEFINE(SOCKNAL_BACKOFF, 1, [use tunable backoff TCP])
		AS_IF([grep rto_max $LINUX/include/linux/tcp.h | grep -q __u16 >/dev/null],
			[AC_DEFINE(SOCKNAL_BACKOFF_MS, 1,
				[tunable backoff TCP in ms])])
	], [
		AC_MSG_RESULT([no])
	])

	AC_SUBST(ENABLE_BACKOFF, yes)
], [
	AC_SUBST(ENABLE_BACKOFF, no)

])
]) # LN_CONFIG_BACKOFF

#
# LN_CONFIG_DLC
#
# Configure dlc
#
# fail to build if libyaml is not installed
#
AC_DEFUN([LN_CONFIG_DLC], [
	AS_IF([test "x$enable_dist" = xno], [
		AC_CHECK_LIB([yaml], [yaml_parser_initialize],
			     [LIBYAML="libyaml"],
			     [AC_MSG_ERROR([YAML development libraries not not installed])],
			     [-lm])
	])
]) # LN_CONFIG_DLC

#
# LN_CONFIG_O2IB
#
# If current OFED installed (assume with "ofed_info") and devel
# headers are not found, error because we assume OFED infiniband
# driver needs to be used and we must configure/build with it.
# Current OFED headers detection mechanism allow for non-standard
# prefix but relies on "ofed_info" command and on "%prefix/openib"
# link (both are ok for 1.5.x and 3.x versions), and should work
# for both source and DKMS builds.
#
AC_DEFUN([LN_CONFIG_O2IB], [
AC_ARG_ENABLE([multiple-lnds],
	[AS_HELP_STRING([--enable-multiple-lnds],
		[enable multiple lnds to build in-kernel and external o2iblnd])],
	[AS_IF([test x$enable_multiple_lnds != xyes -a x$enable_multiple_lnds != xno],
		[AC_MSG_ERROR([multiple-lnds valid options are "yes" or "no"])])],
	[enable_multiple_lnds="no"])
	ENABLE_MULTIPLE_LNDS="$enable_multiple_lnds"

AC_MSG_CHECKING([if external o2iblnd needs to use Compat RDMA])
AC_ARG_WITH([o2ib],
	AS_HELP_STRING([--with-o2ib=[yes|no|<path>]],
		[build o2iblnd against path]),
	[], [with_o2ib="yes"])

case $with_o2ib in
	yes)	INT_O2IBPATHS="$LINUX $LINUX/drivers/infiniband"
		BUILT_IN_KO2IBLND="yes"
		# Use ofed_info to find external driver
		AS_IF([command -v ofed_info >/dev/null], [
			AS_IF([test x$uses_dpkg = xyes], [
				LSPKG="dpkg --listfiles"
			], [
				LSPKG="rpm -ql"
			])

			O2IBPKG="mlnx-ofed-kernel-dkms"
			O2IBPKG+=" mlnx-ofed-kernel-modules"
			O2IBPKG+=" mlnx-ofa_kernel-devel"
			O2IBPKG+=" compat-rdma-devel"
			O2IBPKG+=" kernel-ib-devel"
			O2IBPKG+=" ofa_kernel-devel"

			O2IBDIR="/ofa_kernel"
			O2IBDIR+="|/ofa_kernel/default"
			O2IBDIR+="|/openib"

			O2IBDIR_PATH=$(eval $LSPKG $O2IBPKG 2>/dev/null |
				       grep -E "${O2IBDIR}$" |
				       grep -v /ofed_scripts/ | head -n1)

			# Nowadays, path should always be
			# /usr/src/ofa_kernel/$ARCH/${LINUXRELEASE}
			# and we could clean all that complexity
			# but I don't know how far we should be retro-compatible.

			# The steps above cannot retrieve the path in some cases
			# (e.g mlnx-ofa_kernel-source and mlnx-ofa_kernel-dksm),
			# so set it to a default value if it is NULL.
			if test -z "$O2IBDIR_PATH"; then
				O2IBDIR_PATH="/usr/src/ofa_kernel"
			fi
			if test -d $O2IBDIR_PATH; then
				if test -d $O2IBDIR_PATH/$(uname -m)/${LINUXRELEASE}; then
					O2IBDIR_PATH=$O2IBDIR_PATH/$(uname -m)/${LINUXRELEASE}
				fi
				EXT_O2IBPATHS=$(find -H $O2IBDIR_PATH -name rdma_cm.h |
					sed -e 's/\/include\/rdma\/rdma_cm.h//')
			fi

			# When ofed-scripts are installed and either the devel
			# package is missing or multiple devel packages are
			# installed. Give the user a warning
			# The in-kernel ofed stack can be built .. so we can
			# proceed.

			EXTERNAL_KO2IBLND="yes"
			AS_IF([test -z "$EXT_O2IBPATHS"], [
				EXTERNAL_KO2IBLND="no"
				AC_MSG_WARN([
* You seem to have an OFED installed but have not installed the associated
* devel package.
* If you still want to build Lustre for your External OFED I/B stack,
* you need to install its devel headers RPM.
* Only the kernel built-in I/B stack support will be built.
					     ])
			])
			AS_IF([test $(echo $EXT_O2IBPATHS | wc -w) -ge 2], [
				BUILT_IN_KO2IBLND="no"
				AC_MSG_WARN([
* It appears that you have multiple OFED versions installed.
* If you still want to build Lustre for your External OFED I/B stack, you
* need to install a single version with the associated devel package.
* Only the kernel built-in I/B stack support will be built.
				     ])
			])
			if test x$EXTERNAL_KO2IBLND != "xno" ; then
				if test -e $EXT_O2IBPATHS/${LINUXRELEASE}; then
				    EXT_O2IBPATHS=$EXT_O2IBPATHS/${LINUXRELEASE}
				elif test -e $EXT_O2IBPATHS/default; then
				    EXT_O2IBPATHS=$EXT_O2IBPATHS/default
				fi
			fi
		])
		ENABLEO2IB="yes"
		;;
	no)	ENABLEO2IB="no"
		EXTERNAL_KO2IBLND="no"
		BUILT_IN_KO2IBLND="no"
		;;
	*)	ENABLEO2IB="withpath"
		EXT_O2IBPATHS=$with_o2ib
		EXTERNAL_KO2IBLND="yes"
		INT_O2IBPATHS="$LINUX $LINUX/drivers/infiniband"
		BUILT_IN_KO2IBLND="yes"
		;;
esac

AS_IF([test $ENABLEO2IB = "no"], [
	AC_MSG_RESULT([no])
	AC_DEFUN([LN_CONFIG_O2IB_SRC], [])
	AC_DEFUN([LN_CONFIG_O2IB_RESULTS], [])
	EXT_O2IB_SYMBOLS=""
	INT_O2IB_SYMBOLS=""
], [
	EXT_O2IB_VER=""
	# Verify in-kernel O2IB can be built (headers exist) ... or disable it.
	int_o2ib_found=false
	for INT_O2IBPATH in $INT_O2IBPATHS; do
		AS_IF([test \( -f ${INT_O2IBPATH}/include/rdma/rdma_cm.h -a \
			   -f ${INT_O2IBPATH}/include/rdma/ib_cm.h -a \
			   -f ${INT_O2IBPATH}/include/rdma/ib_verbs.h \)], [
			int_o2ib_found=true
			break
		])
	done
	if ! $int_o2ib_found; then
		AC_MSG_WARN([kernel does not support in-kernel o2ib, it will not be built])
		BUILT_IN_KO2IBLND="no"
	fi

	# Verify external O2IB can be built (headers exist), or abort
	ext_o2ib_found=false
	for EXT_O2IBPATH in $EXT_O2IBPATHS; do
		AS_IF([test \( -f ${EXT_O2IBPATH}/include/rdma/rdma_cm.h -a \
			   -f ${EXT_O2IBPATH}/include/rdma/ib_cm.h -a \
			   -f ${EXT_O2IBPATH}/include/rdma/ib_verbs.h \)], [
			ext_o2ib_found=true
			break
		])
	done
	if ! $ext_o2ib_found; then
		case $ENABLEO2IB in
			"withpath") AC_MSG_ERROR([bad --with-o2ib path]) ;;
			*) 	AC_MSG_WARN([
Auto detection of external O2IB failed. Build of external o2ib disabled.])
				EXTERNAL_KO2IBLND="no"
				;;
		esac
	fi

	if test "x$EXTERNAL_KO2IBLND" != no ; then
		# Additional checks for external O2IB
		COMPAT_AUTOCONF=""
		compatrdma_found=false
		if test -f ${EXT_O2IBPATH}/include/linux/compat-2.6.h; then
			AC_MSG_RESULT([yes])
			compatrdma_found=true
			AC_DEFINE(HAVE_OFED_COMPAT_RDMA, 1, [compat rdma found])
			EXTRA_OFED_CONFIG="$EXTRA_OFED_CONFIG -include ${EXT_O2IBPATH}/include/linux/compat-2.6.h"
			if test -f "$EXT_O2IBPATH/include/linux/compat_autoconf.h"; then
				COMPAT_AUTOCONF="$EXT_O2IBPATH/include/linux/compat_autoconf.h"
			fi
		else
			AC_MSG_RESULT([no])
		fi
		if ! $compatrdma_found; then
			if test -f "$EXT_O2IBPATH/config.mk"; then
				. "$EXT_O2IBPATH/config.mk"
			elif test -f "$EXT_O2IBPATH/ofed_patch.mk"; then
				. "$EXT_O2IBPATH/ofed_patch.mk"
			fi
		elif test -z "$COMPAT_AUTOCONF"; then
			# Depreciated checks
			if test "x$RHEL_KERNEL" = xyes; then
				RHEL_MAJOR=$(awk '/ RHEL_MAJOR / { print [$]3 }' $LINUX_OBJ/include/$VERSION_HDIR/version.h)
				I=$(awk '/ RHEL_MINOR / { print [$]3 }' $LINUX_OBJ/include/$VERSION_HDIR/version.h)
				while test "$I" -ge 0; do
					EXTRA_OFED_INCLUDE="$EXTRA_OFED_INCLUDE -DCONFIG_COMPAT_RHEL_${RHEL_MAJOR}_$I"
					I=$(($I-1))
				done
			elif test "x$SUSE_KERNEL" = xyes; then
				SP=$(grep PATCHLEVEL /etc/SuSE-release | sed -e 's/.*= *//')
				EXTRA_OFED_INCLUDE="$EXTRA_OFED_INCLUDE -DCONFIG_COMPAT_SLES_11_$SP"
			fi
		fi

		AC_MSG_CHECKING([whether to use any OFED backport headers])
		if test -n "$BACKPORT_INCLUDES"; then
			AC_MSG_RESULT([yes])
			OFED_BACKPORT_PATH="$EXT_O2IBPATH/${BACKPORT_INCLUDES/*\/kernel_addons/kernel_addons}/"
			EXTRA_OFED_INCLUDE="-I$OFED_BACKPORT_PATH $EXTRA_OFED_INCLUDE"
		else
			AC_MSG_RESULT([no])
		fi

		EXT_O2IBLND=""
		EXT_O2IBPATH=$(readlink --canonicalize $EXT_O2IBPATH)
		EXTRA_OFED_INCLUDE="$EXTRA_OFED_INCLUDE -I$EXT_O2IBPATH/include"
		EXTRA_OFED_INCLUDE="$EXTRA_OFED_INCLUDE -I$EXT_O2IBPATH/include/uapi"
		EXTRA_CHECK_INCLUDE="$EXTRA_OFED_CONFIG $EXTRA_OFED_INCLUDE"
		LB_CHECK_COMPILE([whether to enable OpenIB gen2 support],
		openib_gen2_support, [
			#ifdef HAVE_OFED_COMPAT_RDMA
			#undef PACKAGE_NAME
			#undef PACKAGE_TARNAME
			#undef PACKAGE_VERSION
			#undef PACKAGE_STRING
			#undef PACKAGE_BUGREPORT
			#undef PACKAGE_URL
			#include <linux/compat-2.6.h>
			#endif
			#include <linux/version.h>
			#include <linux/pci.h>
			#include <linux/gfp.h>
			#include <rdma/rdma_cm.h>
			#include <rdma/ib_cm.h>
			#include <rdma/ib_verbs.h>
		],[
			struct rdma_cm_id *cm_idi __attribute__ ((unused));
			struct rdma_conn_param conn_param __attribute__ ((unused));
			struct ib_device_attr device_attr __attribute__ ((unused));
			struct ib_qp_attr qp_attr __attribute__ ((unused));
			enum ib_cm_rej_reason rej_reason __attribute__ ((unused));

			rdma_destroy_id(NULL);
		],[
			EXT_O2IBLND="o2iblnd"
			EXT_O2IB_VER="None"
			EXT_OFED_INFO=$(command -v ofed_info)
			if test -n "$EXT_OFED_INFO" ; then
				EXT_O2IB_VER=$(ofed_info -n | tr . -)
			fi
		],[
			case $ENABLEO2IB in
			"yes") AC_MSG_ERROR([cannot compile with OpenIB gen2 headers]) ;;
			"withpath") AC_MSG_ERROR([cannot compile with OpenIB gen2 headers under $EXT_O2IBPATH]) ;;
			*) AC_MSG_ERROR([internal error]) ;;
			esac
		])
		# we know that the found external OFED source+headers are good
		EXT_O2IB_SYMBOLS=""
		CHECK_SYMBOLS=""
		if test -f $EXT_O2IBPATH/Module.symvers ; then
			CHECK_SYMBOLS=$EXT_O2IBPATH/Module.symvers
		fi
		if test -n "$CHECK_SYMBOLS"; then
			if test ! "$CHECK_SYMBOLS" -ef "$LINUX_OBJ/Module.symvers"; then
				AC_MSG_NOTICE([adding $CHECK_SYMBOLS to external o2ib symbols])
				EXT_O2IB_SYMBOLS="${CHECK_SYMBOLS}"
			else
				EXTERNAL_KO2IBLND="no"
			fi
		elif test "x$EXTERNAL_KO2IBLND" != "xno" ; then
			AC_MSG_WARN([
	* Module.symvers for external o2iblnd was not found.
	* Expected: $EXT_O2IBPATH/Module.symvers
	* ko2iblnd.ko for external OFED will not be built.
				    ])
			EXTERNAL_KO2IBLND="no"
		fi
	fi

	# we expect that the found in-kernel OFED source+headers are good
	INT_O2IB_SYMBOLS=""
	CHECK_SYMBOLS=""
	if test -f $LINUX_OBJ/Module.symvers; then
		# Debian symvers is in the arch tree
		# SUSE symvers is in the OBJ tree [KVER-obj/<arch>/<flavor>/]
		CHECK_SYMBOLS=$LINUX_OBJ/Module.symvers
	elif test -f $INT_O2IBPATH/Module.symvers; then
		CHECK_SYMBOLS=$INT_O2IBPATH/Module.symvers
	fi

	if test -n "$CHECK_SYMBOLS"; then
		if test ! "$CHECK_SYMBOLS" -ef "$LINUX_OBJ/Module.symvers"; then
			AC_MSG_NOTICE([adding $CHECK_SYMBOLS to o2ib in-kernel symbols])
			INT_O2IB_SYMBOLS="${CHECK_SYMBOLS}"
		fi
	else
		AC_MSG_WARN([Module.symvers for in-kernel o2iblnd was not found])
	fi

	if test "x$EXTERNAL_KO2IBLND" = "xno" -a "x$BUILT_IN_KO2IBLND" = "xno" ; then
		AC_MSG_WARN([No o2iblnd can be built])
	elif test "x$ENABLE_MULTIPLE_LNDS" = "xno" -a \
		  "x$EXTERNAL_KO2IBLND" != "xno" -a "x$BUILT_IN_KO2IBLND" != "xno"; then
		AC_MSG_WARN([
NOTE: --enable-multiple-lnds is needed to enable both o2iblnd drivers.
* Disabling in-kernel o2iblnd in favor of external o2iblnd driver.
* There can be only one in this configuration
			    ])
		BUILT_IN_KO2IBLND="no"
	fi

	EXTRA_CHECK_INCLUDE=""
])
AC_SUBST(EXT_O2IB_VER)
AC_SUBST(EXTRA_OFED_CONFIG)
AC_SUBST(EXTRA_OFED_INCLUDE)
AC_SUBST(EXT_O2IBLND)
AC_SUBST(EXT_O2IB_SYMBOLS)
AC_SUBST(INT_O2IB_SYMBOLS)

# Passed down to deb packaging via autoMakefile.am
AC_SUBST(EXT_O2IBPATH)
AC_SUBST(ENABLEO2IB)
AC_SUBST(ENABLE_MULTIPLE_LNDS)

AS_IF([test $ENABLEO2IB != "no"], [
	EXTRA_CHECK_INCLUDE="$EXTRA_OFED_CONFIG $EXTRA_OFED_INCLUDE"
	if test ! $EXT_O2IBPATH -ef $LINUX_OBJ; then
		EXTERNAL_KO2IBLND="yes"
	fi

	# MOFED 5.5 fails with:
	#   ERROR: "ib_dma_virt_map_sg" [.../ko2iblnd.ko] undefined!
	# See if we have a broken ib_dma_map_sg()
	AC_DEFUN([LN_SRC_SANE_IB_DMA_MAP_SG], [
		LB2_OFED_TEST_SRC([sane_ib_dma_map_sg], [
			#ifdef HAVE_OFED_COMPAT_RDMA
			#undef PACKAGE_NAME
			#undef PACKAGE_TARNAME
			#undef PACKAGE_VERSION
			#undef PACKAGE_STRING
			#undef PACKAGE_BUGREPORT
			#undef PACKAGE_URL
			#include <linux/compat-2.6.h>
			#endif
			#include <rdma/ib_verbs.h>
		],[
			ib_dma_map_sg((struct ib_device *)NULL,
				      (struct scatterlist *)NULL, 1, 0);
		],[-Werror],[$EXTRA_OFED_CONFIG $EXTRA_OFED_INCLUDE])
	])
	AC_DEFUN([LN_SANE_IB_DMA_MAP_SG], [
		LB2_OFED_TEST_RESULTS(
			[if ib_dma_map_sg() is sane],
			[sane_ib_dma_map_sg],
			[HAVE_OFED_IB_DMA_MAP_SG_SANE],[module])
	])

	#
	# LN_IB_DEVICE_OPS_EXISTS
	#
	# kernel 5.0 commit 521ed0d92ab0db3edd17a5f4716b7f698f4fce61
	# RDMA/core: Introduce ib_device_ops
	# ... introduces the ib_device_ops structure that defines all the
	# InfiniBand device operations in one place ...
	#
	AC_DEFUN([LN_SRC_O2IB_IB_DEVICE_OPS_EXISTS], [
		LB2_OFED_TEST_SRC([ib_device_ops_test], [
			#include <rdma/ib_verbs.h>
		],[
			int x = offsetof(struct ib_device_ops, unmap_fmr);
			x = x;
			(void)x;
		],[-Werror],[$EXTRA_OFED_CONFIG $EXTRA_OFED_INCLUDE])
	])
	AC_DEFUN([LN_O2IB_IB_DEVICE_OPS_EXISTS], [
		LB2_OFED_TEST_RESULTS(
			[struct ib_device_ops is defined],
			[ib_device_ops_test],
			[HAVE_OFED_IB_DEVICE_OPS])
	]) # LN_IB_DEVICE_OPS_EXISTS

	#
	# LN_O2IB_IB_SG_DMA_ADDRESS_EXISTS
	#
	# kernel 5.1 commit a163afc88556e099271a7b423295bc5176fcecce
	# IB/core: Remove ib_sg_dma_address() and ib_sg_dma_len()
	# ... when dma_ops existed (3.6) ib_sg_dma_address() was not trivial ...
	#
	AC_DEFUN([LN_SRC_O2IB_IB_SG_DMA_ADDRESS_EXISTS], [
		LB2_OFED_TEST_SRC([ib_sg_dma_address_test], [
			#include <rdma/ib_verbs.h>
		],[
			u64 x = ib_sg_dma_address(NULL, NULL);
			x = x;
			(void)x;
		],[-Werror],[$EXTRA_OFED_CONFIG $EXTRA_OFED_INCLUDE])
	])
	AC_DEFUN([LN_O2IB_IB_SG_DMA_ADDRESS_EXISTS], [
		LB2_OFED_TEST_RESULTS(
			[ib_sg_dma_address wrapper exists],
			[ib_sg_dma_address_test],
			[HAVE_OFED_IB_SG_DMA_ADDRESS])
	]) # LN_O2IB_IB_SG_DMA_ADDRESS_EXISTS

	#
	# LN_O2IB_RDMA_REJECT
	#
	# A reason argument was added to rdma_reject() in Linux 5.8,
	# commit 8094ba0ace7f6cd1e31ea8b151fba3594cadfa9a
	AC_DEFUN([LN_SRC_O2IB_RDMA_REJECT], [
		LB2_OFED_TEST_SRC([rdma_reject], [
			#ifdef HAVE_OFED_COMPAT_RDMA
			#undef PACKAGE_NAME
			#undef PACKAGE_TARNAME
			#undef PACKAGE_VERSION
			#undef PACKAGE_STRING
			#undef PACKAGE_BUGREPORT
			#undef PACKAGE_URL
			#include <linux/compat-2.6.h>
			#endif
			#include <rdma/ib_verbs.h>
			#include <rdma/ib_cm.h>
			#include <rdma/rdma_cm.h>
		],[
			rdma_reject(NULL, NULL, 0, 0);
		],[],[$EXTRA_OFED_CONFIG $EXTRA_OFED_INCLUDE])
	])
	AC_DEFUN([LN_O2IB_RDMA_REJECT], [
		LB2_OFED_TEST_RESULTS(
			[4arg 'rdma_reject' exists],
			[rdma_reject],
			[HAVE_OFED_RDMA_REJECT_4ARGS])
	]) # LN_O2IB_RDMA_REJECT

	#
	# LN_O2IB_IB_FMR
	#
	# The FMR pool API was removed in Linux 5.8,
	# commit 4e373d5417ecbb4f438a8500f0379a2fc29c2643
	AC_DEFUN([LN_SRC_O2IB_IB_FMR], [
		LB2_OFED_TEST_SRC([ib_fmr], [
			#include <rdma/ib_verbs.h>
		],[
			struct ib_fmr fmr = {};
		],[],[$EXTRA_OFED_CONFIG $EXTRA_OFED_INCLUDE])
	])
	AC_DEFUN([LN_O2IB_IB_FMR], [
		LB2_OFED_TEST_RESULTS(
			[FMR pools API available],
			[ib_fmr],
			[HAVE_OFED_FMR_POOL_API])
	]) # LN_O2IB_IB_FMR

	#
	# LN_O2IB_RDMA_CONNECT_LOCKED
	#
	# rdma_connect_locked() was added in Linux 5.10,
	# commit 071ba4cc559de47160761b9500b72e8fa09d923d
	# and in MOFED-5.2-2. rdma_connect_locked() must
	# be called instead of rdma_connect() in
	# RDMA_CM_EVENT_ROUTE_RESOLVED handler.
	AC_DEFUN([LN_SRC_O2IB_RDMA_CONNECT_LOCKED], [
		LB2_OFED_TEST_SRC([rdma_connect_locked], [
			#include <rdma/rdma_cm.h>
		],[
			rdma_connect_locked(NULL, NULL);
		],[],[$EXTRA_OFED_CONFIG $EXTRA_OFED_INCLUDE])
	])
	AC_DEFUN([LN_O2IB_RDMA_CONNECT_LOCKED], [
		LB2_OFED_TEST_RESULTS(
			['rdma_connect_locked' exists],
			[rdma_connect_locked],
			[HAVE_OFED_RDMA_CONNECT_LOCKED])
	]) # LN_O2IB_RDMA_CONNECT_LOCKED

	#
	# LN_O2IB_IBK_SG_GAPS_REG
	#
	# IB_DEVICE_SG_GAPS_REG was renamed to IBK_SG_GAPS_REG
	# in Linux 5.15 commit e945c653c8e972d.
	AC_DEFUN([LN_SRC_O2IB_IBK_SG_GAPS_REG], [
		LB2_OFED_TEST_SRC([ibk_sg_gaps_reg], [
			#include <rdma/ib_verbs.h>
		],[
			int f = IBK_SG_GAPS_REG;
			(void)f;
		],[],[$EXTRA_OFED_CONFIG $EXTRA_OFED_INCLUDE])
	])
	AC_DEFUN([LN_O2IB_IBK_SG_GAPS_REG], [
		LB2_OFED_TEST_RESULTS(
			['IBK_SG_GAPS_REG' exists],
			[ibk_sg_gaps_reg],
			[HAVE_IBK_SG_GAPS_REG])
	]) # LN_O2IB_IBK_SG_GAPS_REG

	EXTRA_CHECK_INCLUDE=""

	AC_DEFUN([LN_CONFIG_O2IB_SRC], [
		LN_SRC_SANE_IB_DMA_MAP_SG
		LN_SRC_O2IB_IB_DEVICE_OPS_EXISTS
		LN_SRC_O2IB_IB_SG_DMA_ADDRESS_EXISTS
		LN_SRC_O2IB_RDMA_REJECT
		LN_SRC_O2IB_IB_FMR
		LN_SRC_O2IB_RDMA_CONNECT_LOCKED
		LN_SRC_O2IB_IBK_SG_GAPS_REG
	])
	AC_DEFUN([LN_CONFIG_O2IB_RESULTS], [
		LN_SANE_IB_DMA_MAP_SG
		LN_O2IB_IB_DEVICE_OPS_EXISTS
		LN_O2IB_IB_SG_DMA_ADDRESS_EXISTS
		LN_O2IB_RDMA_REJECT
		LN_O2IB_IB_FMR
		LN_O2IB_RDMA_CONNECT_LOCKED
		LN_O2IB_IBK_SG_GAPS_REG
	])
]) # ENABLEO2IB != "no"
]) # LN_CONFIG_O2IB

#
# LN_CONFIG_EFALND
#
# check whether to use the EFA Network Interface lnd
#
AC_DEFUN([LN_CONFIG_EFALND], [
AC_MSG_CHECKING([whether to enable EFA LND])
AC_ARG_ENABLE([efa],
	AS_HELP_STRING([--enable-efa=[yes|no|<path>]],
		       [enable EFA LND]),
	[], [enable_efa="no"])

AS_CASE([$enable_efa],
	[yes],
	[
		AS_IF([test x$uses_dpkg = xyes], [
			LS_PKG="dpkg --listfiles"
		], [
			LS_PKG="rpm -ql"
		])

		EFA_PKG="efa"
		EFA_HEADER="efa_verbs.h"
		EFA_HEADER_PATH=$(eval "$LS_PKG $EFA_PKG" | grep -E "$EFA_HEADER" | head -n1)
		AS_IF([test -n "$EFA_HEADER_PATH"], [
			EFA_INCLUDE_PATH=$(dirname $EFA_HEADER_PATH)
		])

		KERNEL_RDMA_INCLUDE="$LINUX/include/rdma"
		AS_IF([test -z "$EFA_INCLUDE_PATH" && test -f "$KERNEL_RDMA_INCLUDE/$EFA_HEADER"], [
			EFA_INCLUDE_PATH=$KERNEL_RDMA_INCLUDE
		])

		AS_IF([test -z "$EFA_INCLUDE_PATH"], [
			AC_MSG_ERROR([Could not find a supported EFA driver. For custom built driver, the path to header files can be supplied using --enable-efa=<path>.])
		])

		ENABLE_EFA="yes"
	],
	[no],
	[
		ENABLE_EFA="no"
	],
	[
		EFA_INCLUDE_PATH=$enable_efa
		ENABLE_EFA="yes"
	])

AS_IF([test $ENABLE_EFA = "no"], [
	AC_MSG_RESULT([no])
], [
	AC_MSG_RESULT([yes])

	# Check mandatory kernel definitions

	LB_CHECK_COMPILE([if 'ib_device_get_by_name' exists],
	ib_device_get_by_name, [
		#include <rdma/ib_verbs.h>
	],[
		ib_device_get_by_name(NULL, 0);
	],[],[
		AC_MSG_ERROR([EFA LND is not supported with this Linux kerenel])
	])

	LB_CHECK_COMPILE([if 'RDMA_DRIVER_EFA' exists],
	rdma_driver_efa, [
		#include <rdma/ib_verbs.h>
	],[
		int x = RDMA_DRIVER_EFA;
	],[],[
		AC_MSG_ERROR([EFA LND is not supported with this Linux kerenel])
	])

	LB_CHECK_COMPILE([if ib_device 'kverbs_provider' flag exists],
	rdma_driver_efa, [
		#include <rdma/ib_verbs.h>
	],[
		struct ib_device dev = {
			.kverbs_provider = 0,
		};
	],[],[
		AC_MSG_ERROR([EFA LND is not supported with this Linux kerenel])
	])

	# Check optional kernel definitions

	LB_CHECK_COMPILE([if 'ibdev_to_node' exists],
	ibdev_to_node, [
		#include <rdma/ib_verbs.h>
	],[
		ibdev_to_node(NULL);
	],[
		AC_DEFINE(HAVE_IBDEV_TO_NODE, 1,
			[ibdev_to_node() is defined])
	])

	EFALND="efalnd"
	AC_SUBST(EFALND)
	AC_SUBST(EFA_INCLUDE_PATH)
])
]) # LN_CONFIG_EFALND

#
# LN_CONFIG_GNILND
#
# check whether to use the Gemini Network Interface lnd
#
AC_DEFUN([LN_CONFIG_GNILND], [
AC_MSG_CHECKING([whether to enable GNI lnd])
AC_ARG_ENABLE([gni],
	AS_HELP_STRING([--enable-gni],
		[enable GNI lnd]),
	[], [enable_gni="no"])
AC_MSG_RESULT([$enable_gni])

AS_IF([test "x$enable_gni" = xyes], [
	# GNICPPFLAGS and KBUILD_EXTRA_SYMBOLS were set in spec file
	# to include the additional module dependancies of gni kernel driver
	EXTRA_KCFLAGS_save="$EXTRA_KCFLAGS"
	EXTRA_KCFLAGS="$EXTRA_KCFLAGS $GNICPPFLAGS"
	LB_CHECK_COMPILE([if GNI kernel headers are present],
	GNI_header, [
		#include <linux/types.h>
		#include <gni_pub.h>
	],[
		gni_cdm_handle_t kgni_domain;
		gni_return_t	 rc;
		int		 rrc;
		rc = gni_cdm_create(0, 1, 1, 0, &kgni_domain);
		rrc = (rc == GNI_RC_SUCCESS) ? 0 : 1;
		return rrc;
	],[
		GNILND="gnilnd"
	],[
		AC_MSG_ERROR([cannot compile gnilnd with given GNICPPFLAGS: $GNICPPFLAGS])
	])
	# at this point, we have gnilnd basic support,
	# now check for extra features
	LB_CHECK_COMPILE([to use RCA in gnilnd],
	RCA_gnilnd, [
		#include <linux/types.h>
		#include <gni_pub.h>
		#include <krca_lib.h>
	],[
		gni_cdm_handle_t kgni_domain;
		gni_return_t	 rc;
		krca_ticket_t	 ticket = KRCA_NULL_TICKET;
		int		 rrc;
		__u32		 nid = 0, nic_addr;
		rc = gni_cdm_create(0, 1, 1, 0, &kgni_domain);
		rrc = (rc == GNI_RC_SUCCESS) ? 0 : 1;
		rrc += krca_nid_to_nicaddrs(nid, 1, &nic_addr);
		rrc += krca_register(&ticket, RCA_MAKE_SERVICE_INDEX(RCA_IO_CLASS, 9), 99, 0);
		return rrc;
	],[
		GNICPPFLAGS="$GNICPPFLAGS -DGNILND_USE_RCA=1"
	])
	EXTRA_KCFLAGS="$EXTRA_KCFLAGS_save"

	AC_DEFINE(HAVE_GNILND, 1, [support gemini LND])
	AC_SUBST(ENABLE_GNI, yes)
], [
	AC_SUBST(ENABLE_GNI, no)
])
AC_SUBST(GNICPPFLAGS)
AC_SUBST(GNILND)
]) # LN_CONFIG_GNILND

#
# LN_CONFIG_KFILND
#
# check whether to use the kfabric Network Interface lnd
#
AC_DEFUN([LN_CONFIG_KFILND], [
AC_ARG_WITH([kfi],
	AS_HELP_STRING([--with-kfi=<path>], [Kfabric build path for kfilnd]),
	[
		AC_CHECK_FILE([$with_kfi/Module.symvers],
		[
			# KFICPPFLAGS was set in spec file
			KFICPPFLAGS="-I$with_kfi/include"
			EXTRA_KCFLAGS_save="$EXTRA_KCFLAGS"
			EXTRA_KCFLAGS="$EXTRA_KCFLAGS $KFICPPFLAGS"
			KBUILD_EXTRA_SYMBOLS="$KBUILD_EXTRA_SYMBOLS $with_kfi/Module.symvers"
			LB_CHECK_COMPILE([if kfabric headers are present], KFI_header,
			[
				#include <kfi_endpoint.h>
			],[
				struct kfi_info *hints;
				hints = kfi_allocinfo();
			],[
				KFILND="kfilnd"
				AC_MSG_NOTICE([adding $with_kfi/Module.symvers to Symbol Path])
				EXTRA_SYMBOLS="$EXTRA_SYMBOLS $with_kfi/Module.symvers"
			],[
				AC_MSG_ERROR([cannot compile kfilnd with given KFICPPFLAGS: $KFICPPFLAGS])
			])
		],[
			AC_MSG_ERROR(["$with_kfi/Module.symvers does not exist"])
		])
		# at this point, we have kfilnd basic support,
		# now check for extra features
		LB_CHECK_COMPILE([if kfi_cxi domain ops are available],
		KFI_CXI_dom_ops, [
			#include <kfi_endpoint.h>
			#include <kfi_cxi_ext.h>
		],[
			struct kfid *fid;
			struct kfi_cxi_domain_ops *dom_ops;
			kfi_open_ops(fid, KFI_CXI_DOM_OPS_1, 0,
				(void **)&dom_ops, NULL);
		],[
			AC_DEFINE(HAVE_KFI_CXI_DOM_OPS, 1,
				[kfi_cxi domain ops are available])
		])
		LB_CHECK_COMPILE([if KFI_SGL IOV type is supported],
		KFABRIC_KFI_SGL, [
			#include <kfabric.h>
			#include <kfi_rma.h>
		],[
			struct kfi_msg_rma rma = {
				.type = KFI_SGL,
			};
		],[
			AC_DEFINE(HAVE_KFI_SGL, 1,
				  [KFI_SGL IOV type is supported])
		])
	],[])
AC_DEFINE(HAVE_KFILND, 1, [support kfabric LND])
AC_SUBST(KFICPPFLAGS)
AC_SUBST(KFILND)
AC_SUBST(EXTRA_SYMBOLS)
]) # LN_CONFIG_KFILND

#
# LN_HAVE_IN_DEV_FOR_EACH_IFA_RTNL
#
# kernel 5.3 commit ef11db3310e272d3d8dbe8739e0770820dd20e52
# and kernel 4.18.0-193.el8:
# added in_dev_for_each_ifa_rtnl and in_dev_for_each_ifa_rcu
# and removed for_ifa and endfor_ifa.
# Use the _rntl variant as the current locking is rtnl.
#
AC_DEFUN([LN_SRC_HAVE_IN_DEV_FOR_EACH_IFA_RTNL], [
	LB2_LINUX_TEST_SRC([in_dev_for_each_ifa_rtnl_test], [
		#include <linux/inetdevice.h>
	],[
		const struct in_ifaddr *ifa = NULL;
		struct in_device *in_dev = NULL;

		in_dev_for_each_ifa_rtnl(ifa, in_dev) {}
	],[-Werror])
])
AC_DEFUN([LN_HAVE_IN_DEV_FOR_EACH_IFA_RTNL], [
	LB2_MSG_LINUX_TEST_RESULT([if 'in_dev_for_each_ifa_rtnl' is defined],
	[in_dev_for_each_ifa_rtnl_test], [
		AC_DEFINE(HAVE_IN_DEV_FOR_EACH_IFA_RTNL, 1,
			['in_dev_for_each_ifa_rtnl' is defined])
	])
]) # LN_HAVE_IN_DEV_FOR_EACH_IFA_RTNL

#
# LN_CONFIG_SOCK_INUSE_ADD
#
# Linux v5.17-rc1-gd477eb900484 added helper function sock_inuse_add()
# for socket statistics.
#
AC_DEFUN([LN_SRC_CONFIG_SOCK_INUSE_ADD], [
	LB2_LINUX_TEST_SRC([sock_inuse_add], [
		#include <net/sock.h>
	],[
		sock_inuse_add((struct net*)0, 0);
	],[-Werror])
])
AC_DEFUN([LN_CONFIG_SOCK_INUSE_ADD], [
	LB2_MSG_LINUX_TEST_RESULT([if 'sock_inuse_add()' is available],
	[sock_inuse_add], [
		AC_DEFINE(HAVE_SOCK_INUSE_ADD, 1,
			[sock_inuse_add() is available])
	])
]) # LN_CONFIG_SOCK_INUSE_ADD

#
# LN_CONFIG_SOCK_NOT_OWNED_BY_ME
#
# Linux upstream v6.11-rc3-g151c9c724d05d5b0d changes TCP socket orphan
# cleanup, requiring a change in ksocklnd if present. This has been back-ported
# to 4.* and 5.* Linux distributions.
#
# Kernel 6.8 commit 151c9c724d05 added sock_not_owned_by_me()
#
AC_DEFUN([LN_SRC_CONFIG_SOCK_NOT_OWNED_BY_ME], [
	LB2_LINUX_TEST_SRC([sock_not_owned_by_me], [
		#include <net/sock.h>
	],[
		sock_not_owned_by_me((const struct sock *)0);
	],[-Werror])
])
AC_DEFUN([LN_CONFIG_SOCK_NOT_OWNED_BY_ME], [
	LB2_MSG_LINUX_TEST_RESULT([if Linux kernel has 'sock_not_owned_by_me'],
	[sock_not_owned_by_me], [
		AC_DEFINE(HAVE_SOCK_NOT_OWNED_BY_ME, 1,
			[sock_not_owned_by_me is defined in sock.h])
	])
]) # LN_CONFIG_SOCK_NOT_OWNED_BY_ME

#
# LN_SRC_HAVE_NETDEV_LOCK_OPS
#
# netdev_lock_ops() added in v6.14-rc4-1113-gd4c22ec680 to lock ethtool changes
#
AC_DEFUN([LN_SRC_HAVE_NETDEV_LOCK_OPS], [
	LB2_LINUX_TEST_SRC([netdev_lock_ops], [
		#include <net/netdev_lock.h>
	],[
		netdev_lock_ops(NULL);
	],[-Werror])
])
AC_DEFUN([LN_HAVE_NETDEV_LOCK_OPS], [
	LB2_MSG_LINUX_TEST_RESULT([if 'netdev_lock_ops' exist],
	[netdev_lock_ops], [
		AC_DEFINE(HAVE_NETDEV_LOCK_OPS, 1,
			['netdev_lock_ops' is present])
	])
]) # LN_SRC_HAVE_NETDEV_LOCK_OPS

#
# LN_CONFIG_SENDPAGE_OK
#
# kernel commit v5.9-rc6-325-gc381b07941 added sendpage_ok() helper
# check if sendpage_ok() is available
#
AC_DEFUN([LN_SRC_CONFIG_SENDPAGE_OK], [
	LB2_LINUX_TEST_SRC([sendpage_ok], [
		#include <linux/net.h>
	],[
		struct page *page = NULL;
		(void)sendpage_ok(page);
	],[-Werror])
])
AC_DEFUN([LN_CONFIG_SENDPAGE_OK], [
	LB2_MSG_LINUX_TEST_RESULT([if sendpage_ok() is available],
	[sendpage_ok], [
		AC_DEFINE(HAVE_SENDPAGE_OK, 1,
			[sendpage_ok() is available])
	])
]) # LN_CONFIG_SENDPAGE_OK

#
## LN_HAVE_STRUCT_SOCKADDR_UNSIZED
#
# Linux commit v6.18-rc3-603-gbf33247a90d3e
#   net: Add struct sockaddr_unsized for sockaddr of unknown length
#
AC_DEFUN([LN_SRC_HAVE_STRUCT_SOCKADDR_UNSIZED],[
	LB2_LINUX_TEST_SRC([struct_sockaddr_unsized], [
		#include <linux/socket.h>
		#include <linux/net.h>
	],[
		struct sockaddr_unsized *addr = NULL;

		(void)kernel_bind(NULL, addr, 0);
	],[-Werror])
])
AC_DEFUN([LN_HAVE_STRUCT_SOCKADDR_UNSIZED],[
	LB2_MSG_LINUX_TEST_RESULT([if struct sockaddr_unsized exists],
	[struct_sockaddr_unsized], [
		AC_DEFINE(HAVE_STRUCT_SOCKADDR_UNSIZED, 1,
			  [struct sockaddr_unsized exists])
	], [
		AC_DEFINE([sockaddr_unsized], [sockaddr],
			  [struct sockaddr_unsized does not exist])
	])
]) # LN_HAVE_STRUCT_SOCKADDR_UNSIZED

AC_DEFUN([LN_PROG_LINUX_SRC], [
	LN_CONFIG_O2IB_SRC
	# 5.3 and 4.18.0-193.el8
	LN_SRC_HAVE_IN_DEV_FOR_EACH_IFA_RTNL
	# 5.9
	LN_SRC_CONFIG_SENDPAGE_OK
	# 5.17
	LN_SRC_CONFIG_SOCK_INUSE_ADD
	# 6.8
	LN_SRC_CONFIG_SOCK_NOT_OWNED_BY_ME
	# 6.15
	LN_SRC_HAVE_NETDEV_LOCK_OPS
	# 6.19
	LN_SRC_HAVE_STRUCT_SOCKADDR_UNSIZED
])

AC_DEFUN([LN_PROG_LINUX_RESULTS], [
	LN_CONFIG_O2IB_RESULTS
	# 5.3 and 4.18.0-193.el8
	LN_HAVE_IN_DEV_FOR_EACH_IFA_RTNL
	# 5.9
	LN_CONFIG_SENDPAGE_OK
	# 5.17
	LN_CONFIG_SOCK_INUSE_ADD
	# 6.8
	LN_CONFIG_SOCK_NOT_OWNED_BY_ME
	# 6.15
	LN_HAVE_NETDEV_LOCK_OPS
	# 6.19
	LN_HAVE_STRUCT_SOCKADDR_UNSIZED
])

#
# LN_PROG_LINUX
#
# LNet linux kernel checks
#
AC_DEFUN([LN_PROG_LINUX], [
AC_MSG_NOTICE([LNet kernel checks
==============================================================================])

LN_CONFIG_BACKOFF
LN_CONFIG_O2IB
LN_CONFIG_EFALND
LN_CONFIG_GNILND
LN_CONFIG_KFILND
]) # LN_PROG_LINUX

#
# LN_PATH_DEFAULTS
#
# default paths for installed files
#
AC_DEFUN([LN_PATH_DEFAULTS], [
]) # LN_PATH_DEFAULTS

#
# LN_CONFIGURE
#
# other configure checks
#
AC_DEFUN([LN_CONFIGURE], [
AC_MSG_NOTICE([LNet core checks
==============================================================================])

AC_ARG_WITH([cuda],
	AS_HELP_STRING([--with-cuda=path],
			[Path to the CUDA sources.]),
			[cudapath="$withval"],
			[cudapath1=`ls -d1 /usr/src/nvidia-*/nvidia/ 2>/dev/null | tail -1`])

AC_ARG_WITH([gds],
	AS_HELP_STRING([--with-gds=path],
			[Path to the GDS sources.]),
			[gdspath="$withval"],
			[gdspath1=`ls -d1 /usr/src/nvidia-fs*/ 2>/dev/null | tail -1`])

AC_MSG_CHECKING([cuda source directory])
	AS_IF([test -z "${cudapath}"], [
		AS_IF([test -e "${cudapath1}/nv-p2p.h"], [
			cudapath=${cudapath1}
		], [
			cudapath="[Not found]"
		])
	])
AC_MSG_RESULT([$cudapath])

AC_MSG_CHECKING([gds source directory])
	AS_IF([test -z "${gdspath}"], [
		AS_IF([test -e "${gdspath1}/nvfs-dma.h"], [
			gdspath=${gdspath1}
		], [
			gdspath="[Not found]"
		])
	])
AC_MSG_RESULT([$gdspath])

AS_IF([test -e "${cudapath}" && test -e "${gdspath}"],[
	LB_CHECK_FILE([$cudapath/nv-p2p.h], [
		AC_MSG_RESULT([CUDA path is $cudapath])
		[CUDA_PATH=${cudapath}]
		AC_SUBST(CUDA_PATH)
	],[
		AC_MSG_RESULT([CUDA sources not found: nv-p2p.h does not exist])
	])

	LB_CHECK_FILE([$gdspath/nvfs-dma.h], [
		LB_CHECK_FILE([$gdspath/config-host.h], [
			AC_MSG_RESULT([GDS path is ${gdspath}])
			[GDS_PATH=${gdspath}]
			AC_SUBST(GDS_PATH)
			AC_DEFINE(WITH_EXTERNAL_GDS_HEADER, 1, "GDS build enabled")
		], [
		    AC_MSG_RESULT([GDS sources not found: config-host.h does not exist])
        ])
	], [
		AC_MSG_RESULT([GDS sources not found: nvfs-dma.h does not exist])
    ])
],[
	AC_MSG_WARN([CUDA or GDS sources not found. Using embedded GDS headers.])
])

# lnet/utils/lnetconfig/liblnetconfig_netlink.c
AS_IF([test "x$PKGCONF" = "x"],
	[AC_MSG_ERROR([pkg-config package is required to configure Lustre])])

AS_IF([test "x$enable_dist" = xno], [
	PKG_CHECK_MODULES(LIBNL3, [libnl-genl-3.0 >= 3.1])
])

AC_CHECK_LIB([nl-3], [nla_get_s32], [
	AC_DEFINE(HAVE_NLA_GET_S32, 1,
		[libnl3 supports nla_get_s32])
	], [
])

AC_CHECK_LIB([nl-3], [nla_get_s64], [
	AC_DEFINE(HAVE_NLA_GET_S64, 1,
		[libnl3 supports nla_get_s64])
	], [
])

# lnet/utils/portals.c
AC_CHECK_HEADERS([netdb.h])

# lnet/utils/wirecheck.c
AC_CHECK_FUNCS([strnlen])

# --------  Check for required packages  --------------

AC_MSG_CHECKING([whether to enable 'efence' debugging support])
AC_ARG_ENABLE(efence,
	AS_HELP_STRING([--enable-efence],
		[use efence library]),
	[], [enable_efence="no"])
AC_MSG_RESULT([$enable_efence])

LIBEFENCE=""
AS_IF([test "$enable_efence" = yes], [
	LIBEFENCE="-lefence"
	AC_DEFINE(HAVE_LIBEFENCE, 1,
		[libefence support is requested])
	AC_SUBST(ENABLE_EFENCE, yes)
], [
	AC_SUBST(ENABLE_EFENCE, no)
])
AC_SUBST(LIBEFENCE)

LN_CONFIG_DLC
]) # LN_CONFIGURE

#
# LN_CONDITIONALS
#
# AM_CONDITIONAL defines for lnet
#
AC_DEFUN([LN_CONDITIONALS], [
AM_CONDITIONAL(EXTERNAL_KO2IBLND,  test x$EXTERNAL_KO2IBLND = "xyes")
AM_CONDITIONAL(BUILT_IN_KO2IBLND,  test x$BUILT_IN_KO2IBLND = "xyes")
AM_CONDITIONAL(BUILD_EFALND,	   test x$EFALND = "xefalnd")
AM_CONDITIONAL(BUILD_GNILND,       test x$GNILND  = "xgnilnd")
AM_CONDITIONAL(BUILD_KFILND,       test x$KFILND  = "xkfilnd")
]) # LN_CONDITIONALS

#
# LN_CONFIG_FILES
#
# files that should be generated with AC_OUTPUT
#
AC_DEFUN([LN_CONFIG_FILES], [
AC_CONFIG_FILES([
lnet/utils/Makefile
lnet/utils/lnetconfig/Makefile
])
]) # LN_CONFIG_FILES