Skip to content

Spack CPU Build Fix. Add spack built libCEED support. #1734

Spack CPU Build Fix. Add spack built libCEED support.

Spack CPU Build Fix. Add spack built libCEED support. #1734

name: Build and Test (Linux)
on:
push:
branches:
- main
pull_request:
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true
jobs:
build-and-test-linux:
strategy:
fail-fast: false
matrix:
include: # Pairwise testing (from allpairspy)
# Bug in MPICH on Ubuntu 24 means we disable Ubuntu24 builds.
# https://stackoverflow.com/questions/78815680/mpi-comm-size-always-returns-1-again
- arch: x86
compiler: intel
mpi: intelmpi
math-libs: intelmkl
build-shared: shared
with-64bit-int: int64
with-openmp: openmp
with-eigensolver: slepc
with-solver: superlu
# - arch: x86
# compiler: gcc
# mpi: mpich
# math-libs: openblas
# build-shared: static
# with-64bit-int: int32
# with-openmp: serial
# with-eigensolver: arpack
# with-solver: strumpack
- arch: x86
compiler: clang
mpi: openmpi
math-libs: aocl
build-shared: static
with-64bit-int: int64
with-openmp: serial
with-eigensolver: slepc
with-solver: mumps
# - arch: x86
# compiler: clang
# mpi: mpich
# math-libs: aocl
# build-shared: shared
# with-64bit-int: int32
# with-openmp: openmp
# with-eigensolver: arpack
# with-solver: mumps
- arch: x86
compiler: gcc
mpi: openmpi
math-libs: openblas
build-shared: shared
with-64bit-int: int64
with-openmp: openmp
with-eigensolver: slepc
with-solver: strumpack
- arch: x86
compiler: intel
mpi: intelmpi
math-libs: intelmkl
build-shared: static
with-64bit-int: int32
with-openmp: serial
with-eigensolver: arpack
with-solver: superlu
- arch: x86
compiler: intel
mpi: intelmpi
math-libs: intelmkl
build-shared: static
with-64bit-int: int32
with-openmp: openmp
with-eigensolver: slepc
with-solver: strumpack
- arch: x86
compiler: intel
mpi: intelmpi
math-libs: intelmkl
build-shared: shared
with-64bit-int: int64
with-openmp: serial
with-eigensolver: arpack
with-solver: mumps
- arch: x86
compiler: gcc
mpi: openmpi
math-libs: aocl
build-shared: shared
with-64bit-int: int32
with-openmp: serial
with-eigensolver: arpack
with-solver: superlu
# - arch: x86
# compiler: clang
# mpi: mpich
# math-libs: openblas
# build-shared: shared
# with-64bit-int: int64
# with-openmp: serial
# with-eigensolver: slepc
# with-solver: superlu
- arch: arm
compiler: gcc
mpi: mpich
math-libs: openblas
build-shared: shared
with-64bit-int: int64
with-openmp: openmp
with-eigensolver: slepc
with-solver: superlu
- arch: arm
compiler: clang
mpi: openmpi
math-libs: armpl
build-shared: static
with-64bit-int: int32
with-openmp: serial
with-eigensolver: arpack
with-solver: strumpack
- arch: arm
compiler: clang
mpi: mpich
math-libs: armpl
build-shared: shared
with-64bit-int: int32
with-openmp: openmp
with-eigensolver: arpack
with-solver: mumps
- arch: arm
compiler: gcc
mpi: openmpi
math-libs: openblas
build-shared: static
with-64bit-int: int64
with-openmp: serial
with-eigensolver: slepc
with-solver: mumps
- arch: arm
compiler: gcc
mpi: openmpi
math-libs: armpl
build-shared: shared
with-64bit-int: int64
with-openmp: serial
with-eigensolver: arpack
with-solver: superlu
- arch: arm
compiler: clang
mpi: mpich
math-libs: openblas
build-shared: static
with-64bit-int: int32
with-openmp: openmp
with-eigensolver: slepc
with-solver: strumpack
- arch: arm
compiler: clang
mpi: mpich
math-libs: openblas
build-shared: static
with-64bit-int: int64
with-openmp: serial
with-eigensolver: arpack
with-solver: superlu
- arch: arm
compiler: gcc
mpi: openmpi
math-libs: armpl
build-shared: shared
with-64bit-int: int32
with-openmp: openmp
with-eigensolver: slepc
with-solver: strumpack
- arch: arm
compiler: gcc
mpi: openmpi
math-libs: armpl
build-shared: shared
with-64bit-int: int32
with-openmp: openmp
with-eigensolver: slepc
with-solver: superlu
- arch: arm
compiler: gcc
mpi: openmpi
math-libs: armpl
build-shared: shared
with-64bit-int: int64
with-openmp: openmp
with-eigensolver: slepc
with-solver: strumpack
# Flaky arm builds with ubuntu 24 means we pin to ubuntu 22
runs-on: ${{ matrix.arch == 'x86' && 'palace_ubuntu-latest_16-core' || 'ubuntu-22.04-arm' }}
steps:
- uses: actions/checkout@v4
with:
submodules: 'recursive'
- name: Update package lists
run: |
sudo apt-get update
- name: Configure GNU compilers
run: |
# Find latest gnu compiler versions
LATEST_GFORTRAN=$(apt-cache search '^gfortran-[0-9]+$' | sort -V | tail -n1 | cut -d' ' -f1)
LATEST_GCC=$(apt-cache search '^gcc-[0-9]+$' | sort -V | tail -n1 | cut -d' ' -f1)
LATEST_GPP=$(apt-cache search '^g\+\+-[0-9]+$' | sort -V | tail -n1 | cut -d' ' -f1)
GFORT_VERSION=$(echo $LATEST_GFORTRAN | cut -d'-' -f2)
GCC_VERSION=$(echo $LATEST_GCC | cut -d'-' -f2)
sudo apt-get install -y $LATEST_GFORTRAN $LATEST_GCC $LATEST_GPP
sudo update-alternatives --install $(which gfortran) gfortran $(which gfortran-$GFORT_VERSION) ${GFORT_VERSION}0
sudo update-alternatives --set gfortran $(which gfortran-$GFORT_VERSION)
sudo update-alternatives --install $(which gcc) gcc $(which gcc-$GCC_VERSION) ${GCC_VERSION}0 \
--slave $(which g++) g++ $(which g++-$GCC_VERSION)
sudo update-alternatives --set gcc $(which gcc-$GCC_VERSION)
gfortran --version
gcc --version
g++ --version
- name: Configure Open MPI
if: matrix.mpi == 'openmpi'
run: |
sudo apt-get install -y openmpi-bin libopenmpi-dev
- name: Configure MPICH
if: matrix.mpi == 'mpich'
run: |
sudo apt-get install -y mpich libmpich-dev
- name: Configure Intel MPI
if: matrix.mpi == 'intelmpi'
uses: mpi4py/setup-mpi@v1
with:
mpi: ${{ matrix.mpi }}
- name: Configure Clang compiler
if: matrix.compiler == 'clang'
run: |
sudo apt-get install -y clang lld
if [[ "${{ matrix.with-openmp }}" == 'openmp' ]]; then
sudo apt-get install -y libomp-dev
fi
- name: Configure Intel oneAPI compiler
if: matrix.compiler == 'intel'
run: |
sudo apt-get install -y intel-oneapi-compiler-dpcpp-cpp=2024.2.1-1079 \
intel-oneapi-compiler-fortran=2024.2.1-1079
- name: Install math libraries (OpenBLAS)
if: matrix.math-libs == 'openblas'
run: |
if [[ "${{ matrix.with-openmp }}" == 'openmp' ]]; then
sudo apt-get install -y libopenblas-openmp-dev
else
sudo apt-get install -y libopenblas-serial-dev
fi
- name: Install GCC OpenMP runtime
if: matrix.with-openmp == 'openmp'
run: |
sudo apt-get install -y libgomp1
- name: Install math libraries (Intel oneAPI MKL)
if: matrix.math-libs == 'intelmkl'
run: |
sudo apt-get install -y intel-oneapi-mkl=2024.2.2-15 intel-oneapi-mkl-devel=2024.2.2-15
- name: Install math libraries (AOCL)
if: matrix.math-libs == 'aocl'
run: |
wget -q https://download.amd.com/developer/eula/aocl/aocl-4-1/aocl-linux-gcc-4.1.0_1_amd64.deb
sudo apt-get install -y ./aocl-linux-gcc-4.1.0_1_amd64.deb
rm aocl-linux-gcc-*.deb
echo "AOCLROOT=/opt/AMD/aocl/aocl-linux-gcc-4.1.0/gcc" >> $GITHUB_ENV
- name: Install math libraries (ARMPL)
if: matrix.math-libs == 'armpl'
run: |
wget -q https://developer.arm.com/-/cdn-downloads/permalink/Arm-Performance-Libraries/Version_24.10/arm-performance-libraries_24.10_deb_gcc.tar
tar -xf arm-performance-libraries* && rm -rf arm-performance-libraries*.tar
sudo ./arm-performance-libraries*/arm-performance-libraries*.sh -a -f -i /opt/arm
echo "ARMPL_DIR=/opt/arm/armpl_24.10_gcc" >> $GITHUB_ENV
- name: Test MPI installation
run: |
# Create test program
cat > mpi_test.c << 'EOF'
#include <stdio.h>
#include <mpi.h>
int main(int argc, char *argv[]) {
int rank, size;
MPI_Init(&argc, &argv);
MPI_Comm_rank(MPI_COMM_WORLD, &rank);
MPI_Comm_size(MPI_COMM_WORLD, &size);
printf("Process %d of %d\n", rank, size);
if (rank == 0) {
if (size == 1) {
printf("ERROR: MPI_Comm_size reports only 1 process\n");
return 1;
} else {
printf("SUCCESS: MPI running with %d processes\n", size);
}
}
MPI_Finalize();
return 0;
}
EOF
# Select correct compiler wrapper
if [[ "${{ matrix.mpi }}" == "mpich" ]]; then
MPICC="mpicc"
elif [[ "${{ matrix.mpi }}" == "openmpi" ]]; then
MPICC="mpicc"
elif [[ "${{ matrix.mpi }}" == "intelmpi" ]]; then
source /opt/intel/oneapi/setvars.sh
MPICC="mpiicx"
fi
$MPICC mpi_test.c -o mpi_test
mpirun -np 2 ./mpi_test
- uses: julia-actions/setup-julia@v2
with:
version: '1'
- name: Build Palace
env:
CMAKE_BUILD_TYPE: Release
NUM_PROC_BUILD_MAX: '32'
run: |
# Configure environment
if [[ "${{ matrix.compiler }}" == 'intel' ]] || \
[[ "${{ matrix.mpi }}" == 'intelmpi' ]] || \
[[ "${{ matrix.math-libs }}" == 'intelmkl' ]]; then
source /opt/intel/oneapi/setvars.sh # Sets PATH, MKLROOT
if [[ "${{ matrix.compiler }}" == 'intel' ]]; then
export CC=icx
export CXX=icpx
export FC=ifx
fi
elif [[ "${{ matrix.compiler }}" == 'clang' ]]; then
export CC=clang
export CXX=clang++
export FC=gfortran
export LDFLAGS='-fuse-ld=lld'
elif [[ "${{ matrix.compiler }}" == 'gcc' ]]; then
export CC=gcc
export CXX=g++
export FC=gfortran
fi
export NUM_PROC_BUILD=$(nproc 2> /dev/null || sysctl -n hw.ncpu)
if [[ "$NUM_PROC_BUILD" -gt "$NUM_PROC_BUILD_MAX" ]]; then
NUM_PROC_BUILD=$NUM_PROC_BUILD_MAX
fi
if [[ "${{ matrix.math-libs }}" == 'aocl' ]]; then
export AOCLROOT="$AOCLROOT"
export LD_LIBRARY_PATH="$AOCLROOT/lib:$LD_LIBRARY_PATH"
fi
if [[ "${{ matrix.math-libs }}" == 'armpl' ]]; then
export ARMPL_DIR="$ARMPL_DIR"
export LD_LIBRARY_PATH="$ARMPL_DIR/lib:$LD_LIBRARY_PATH"
fi
[[ "${{ matrix.build-shared }}" == 'shared' ]] && BUILD_SHARED='ON' || BUILD_SHARED='OFF'
[[ "${{ matrix.with-64bit-int }}" == 'int64' ]] && WITH_INT64='ON' || WITH_INT64='OFF'
[[ "${{ matrix.with-openmp }}" == 'openmp' ]] && WITH_OPENMP='ON' || WITH_OPENMP='OFF'
[[ "${{ matrix.with-solver }}" == 'superlu' ]] && WITH_SUPERLU='ON' || WITH_SUPERLU='OFF'
[[ "${{ matrix.with-solver }}" == 'strumpack' ]] && WITH_STRUMPACK='ON' || WITH_STRUMPACK='OFF'
[[ "${{ matrix.with-solver }}" == 'mumps' ]] && WITH_MUMPS='ON' || WITH_MUMPS='OFF'
[[ "${{ matrix.with-eigensolver }}" == 'slepc' ]] && WITH_SLEPC='ON' || WITH_SLEPC='OFF'
[[ "${{ matrix.with-eigensolver }}" == 'arpack' ]] && WITH_ARPACK='ON' || WITH_ARPACK='OFF'
# Build and install (with unit tests)
# Compile so that MFEM throws exceptions rather then aborts for unit-tests
mkdir palace-build && cd palace-build
cmake .. \
-DCMAKE_INSTALL_PREFIX=$(pwd)/../palace-install \
-DBUILD_SHARED_LIBS=$BUILD_SHARED \
-DPALACE_WITH_64BIT_INT=$WITH_INT64 \
-DPALACE_WITH_OPENMP=$WITH_OPENMP \
-DPALACE_WITH_SUPERLU=$WITH_SUPERLU \
-DPALACE_WITH_STRUMPACK=$WITH_STRUMPACK \
-DPALACE_WITH_MUMPS=$WITH_MUMPS \
-DPALACE_WITH_SLEPC=$WITH_SLEPC \
-DPALACE_WITH_ARPACK=$WITH_ARPACK \
-DPALACE_MFEM_USE_EXCEPTIONS=ON
make -j$NUM_PROC_BUILD palace-tests
- name: Run unit tests
timeout-minutes: 5
env:
NUM_PROC_TEST_MAX: '2'
run: |
# Configure environment
if [[ "${{ matrix.compiler }}" == 'intel' ]] || \
[[ "${{ matrix.mpi }}" == 'intelmpi' ]] || \
[[ "${{ matrix.math-libs }}" == 'intelmkl' ]]; then
source /opt/intel/oneapi/setvars.sh # Sets PATH, MKLROOT
fi
if [[ "${{ matrix.with-openmp }}" == 'true' ]]; then
export OMP_NUM_THREADS=2
else
export OMP_NUM_THREADS=1
fi
export LD_LIBRARY_PATH=$(pwd)/palace-install/lib:$LD_LIBRARY_PATH
export LD_LIBRARY_PATH=$(pwd)/palace-install/lib64:$LD_LIBRARY_PATH
if [[ "${{ matrix.math-libs }}" == 'aocl' ]]; then
export LD_LIBRARY_PATH="$AOCLROOT/lib:$LD_LIBRARY_PATH"
fi
cd $(pwd)/palace-build/palace-build/test/unit
# Run tests
mpirun -np $NUM_PROC_TEST_MAX ./unit-tests --skip-benchmarks
- name: Run regression tests for examples/
timeout-minutes: 60
env:
NUM_PROC_TEST_MAX: '8'
run: |
# Configure environment
if [[ "${{ matrix.compiler }}" == 'intel' ]] || \
[[ "${{ matrix.mpi }}" == 'intelmpi' ]] || \
[[ "${{ matrix.math-libs }}" == 'intelmkl' ]]; then
source /opt/intel/oneapi/setvars.sh # Sets PATH, MKLROOT
fi
if [[ "${{ matrix.math-libs }}" == 'aocl' ]]; then
export AOCLROOT=/opt/AMD/aocl/aocl-linux-gcc-4.1.0/gcc
export LD_LIBRARY_PATH=$AOCLROOT/lib:$LD_LIBRARY_PATH
fi
export NUM_PROC_TEST=$(nproc 2> /dev/null || sysctl -n hw.ncpu)
if [[ "$NUM_PROC_TEST" -gt "$NUM_PROC_TEST_MAX" ]]; then
NUM_PROC_TEST=$NUM_PROC_TEST_MAX
fi
if [[ "${{ matrix.with-openmp }}" == 'true' ]]; then
NUM_PROC_TEST=$(( NUM_PROC_TEST / 2 ))
export OMP_NUM_THREADS=2
else
export OMP_NUM_THREADS=1
fi
export PATH=$(pwd)/palace-install/bin:$PATH
# Run tests
julia --project=test/examples -e 'using Pkg; Pkg.instantiate()'
julia --project=test/examples --color=yes test/examples/runtests.jl