Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
45 changes: 45 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
name: ci

on:
push:
paths:
- "**.c"
- "**.cmake"
- "**/CMakeLists.txt"
- ".github/workflows/ci.yml"
workflow_dispatch:

# avoid wasted runs
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true


jobs:

unix:

strategy:
matrix:
os: [ubuntu-latest, macos-latest]
intsize: [32, 64]

runs-on: ${{ matrix.os }}
timeout-minutes: 5

steps:
- name: Install MPI (Linux)
if: ${{ runner.os == 'Linux' }}
run: sudo apt install libopenmpi-dev

- name: Install MPI (MacOS)
if: ${{ runner.os == 'macOS' }}
run: brew install open-mpi

- &checkout
uses: actions/checkout@v4

- run: cmake -B build -DIDXTYPEWIDTH=${{ matrix.intsize }}
- run: cmake --build build --parallel

- run: ctest --test-dir build -V
3 changes: 3 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
[submodule "METIS"]
path = METIS
url = https://github.com/scivision/METIS
76 changes: 46 additions & 30 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,43 +1,59 @@
cmake_minimum_required(VERSION 2.8)
project(ParMETIS C)
cmake_minimum_required(VERSION 3.16...4.1)

if(NOT CMAKE_BUILD_TYPE AND NOT DEFINED ENV{CMAKE_BUILD_TYPE})
set(CMAKE_BUILD_TYPE Release CACHE STRING "Debug or Release")
endif()

# Search for MPI.
# GK commented this out as it seems to be creating problems
# include(FindMPI)
# if(NOT MPI_FOUND)
# message(FATAL_ERROR "mpi is not found")
# endif()
# set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${MPI_COMPILE_FLAGS}")
project(parmetis LANGUAGES C VERSION 1.0.0)

# --- need METIS first
include(GNUInstallDirs)
include(cmake/GitSubmodule.cmake)

# Prepare libraries.
if(SHARED)
set(ParMETIS_LIBRARY_TYPE SHARED)
else()
set(ParMETIS_LIBRARY_TYPE STATIC)
if(CMAKE_INSTALL_PREFIX_INITIALIZED_TO_DEFAULT AND parmetis_IS_TOP_LEVEL)
set(CMAKE_INSTALL_PREFIX "${PROJECT_BINARY_DIR}/local" CACHE PATH "install prefix" FORCE)
endif()

message(STATUS "${PROJECT_NAME} ${PROJECT_VERSION} CMake ${CMAKE_VERSION} install prefix ${CMAKE_INSTALL_PREFIX}")

git_submodule(${CMAKE_CURRENT_SOURCE_DIR}/METIS)
add_subdirectory(METIS)

set(CMAKE_C_STANDARD 99)

add_compile_definitions(
"REALTYPEWIDTH=$<IF:$<BOOL:${REALTYPEWIDTH}>,${REALTYPEWIDTH},32>"
"IDXTYPEWIDTH=$<IF:$<BOOL:${IDXTYPEWIDTH}>,${IDXTYPEWIDTH},32>"
)

find_package(MPI REQUIRED)

include(./conf/gkbuild.cmake)

# List of paths that the compiler will search for header files.
# i.e., the -I equivalent
include_directories(include)
include_directories(${MPI_INCLUDE_PATH})
include_directories(${GKLIB_PATH}/include)
include_directories(${METIS_PATH}/include)
include_directories(${CMAKE_INSTALL_PREFIX}/include)

# List of paths that the compiler will search for library files.
# i.e., the -L equivalent
link_directories(${GKLIB_PATH}/lib)
link_directories(${METIS_PATH}/lib)
link_directories(${CMAKE_INSTALL_PREFIX}/lib)

# List of directories that cmake will look for CMakeLists.txt
add_subdirectory(include)
install(FILES include/parmetis.h TYPE INCLUDE)

add_library(parmetis)
target_include_directories(parmetis PUBLIC
"$<BUILD_INTERFACE:${PROJECT_SOURCE_DIR}/include;${PROJECT_SOURCE_DIR}/libparmetis;${PROJECT_SOURCE_DIR}/METIS/include>"
$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>
)
target_link_libraries(parmetis PRIVATE MPI::MPI_C metis::metis)

if(SHARED)
target_link_libraries(parmetis PRIVATE metis GKlib)
endif()

add_library(parmetis::parmetis INTERFACE IMPORTED GLOBAL)
target_link_libraries(parmetis::parmetis INTERFACE parmetis)

install(TARGETS parmetis EXPORT ${PROJECT_NAME}-targets)

add_subdirectory(libparmetis)
add_subdirectory(programs)

# This is for testing during development and is not being distributed
#add_subdirectory(test)

include(cmake/install.cmake)

file(GENERATE OUTPUT .gitignore CONTENT "*")
72 changes: 72 additions & 0 deletions CMakePresets.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
{
"version": 6,

"configurePresets": [
{
"name": "default",
"binaryDir": "${sourceDir}/build",
"cacheVariables": {
"CMAKE_COMPILE_WARNING_AS_ERROR": true
}
}
],
"buildPresets": [
{
"name": "default",
"configurePreset": "default"
},
{
"name": "release",
"configurePreset": "default",
"configuration": "Release"
}
],
"testPresets": [
{
"name": "default",
"configurePreset": "default",
"output": {
"outputOnFailure": true,
"verbosity": "verbose"
},
"execution": {
"noTestsAction": "error",
"scheduleRandom": true,
"stopOnFailure": false,
"timeout": 60
}
},
{
"name": "release", "inherits": "default",
"configuration": "Release"
}
],
"workflowPresets": [
{
"name": "default",
"steps": [
{
"type": "configure",
"name": "default"
},
{
"type": "build",
"name": "default"
}
]
},
{
"name": "release",
"steps": [
{
"type": "configure",
"name": "default"
},
{
"type": "build",
"name": "release"
}
]
}
]
}
1 change: 1 addition & 0 deletions METIS
Submodule METIS added at d4a3aa
78 changes: 10 additions & 68 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,82 +1,26 @@
# ParMETIS
# ParMETIS

ParMETIS is an MPI-based library for partitioning graphs, partitioning finite element meshes,
and producing fill reducing orderings for sparse matrices. The algorithms implemented in
ParMETIS are based on the multilevel recursive-bisection, multilevel k-way, and multi-constraint
[![ci](https://github.com/scivision/ParMETIS/actions/workflows/ci.yml/badge.svg)](https://github.com/scivision/ParMETIS/actions/workflows/ci.yml)

ParMETIS is an MPI-based library for partitioning graphs, partitioning finite element meshes,
and producing fill reducing orderings for sparse matrices. The algorithms implemented in
ParMETIS are based on the multilevel recursive-bisection, multilevel k-way, and multi-constraint
partitioning schemes developed in our lab.

## Downloading ParMETIS
## Downloading ParMETIS

You can download ParMETIS by simply cloning it using the command:
```
git clone https://github.com/KarypisLab/ParMETIS.git
```

## Building the ParMETIS library

To build ParMETIS you can follow the instructions below:

### Dependencies

General dependencies for building ParMETIS are: gcc, cmake, build-essential, and an MPI library.
In Ubuntu systems these can be obtained from the apt package manager (e.g., apt-get install cmake, mpich, etc)

```
sudo apt-get install build-essential
sudo apt-get install cmake
```

In addition, you need to download and install
[GKlib](https://github.com/KarypisLab/GKlib) and
[METIS](https://github.com/KarypisLab/METIS) by following the instructions there.


### Building and installing ParMETIS

ParMETIS is primarily configured by passing options to make config. For example:

```
make config cc=mpicc prefix=~/local
make install
```sh
cmake --workflow --preset default
```

will configure ParMETIS to be built using mpicc and then install the binaries, header files, and libraries at

```
~/local/bin
~/local/include
~/local/lib
```

directories, respectively.

### Common configuration options are:

cc=[compiler] - The C compiler to use [default is determined by CMake]
shared=1 - Build a shared library instead of a static one [off by default]
prefix=[PATH] - Set the installation prefix [~/local by default]
gklib_path=[PATH] - Set the prefix path where GKlib has been installed. You can skip
this if GKlib's installation prefix is the same as that of ParMETIS.
metis_path=[PATH] - Set the prefix path where METIS has been installed. You can skip
this if METIS' installation prefix is the same as that of ParMETIS.

### Advanced debugging related options:

gdb=1 - Build with support for GDB [off by default]
debug=1 - Enable debugging support [off by default]
assert=1 - Enable asserts [off by default]
assert2=1 - Enable very expensive asserts [off by default]

### Other make commands

make uninstall
Removes all files installed by 'make install'.

make clean
Removes all object files but retains the configuration options.

make distclean
Performs clean and completely removes the build directory.


### Definitions of supported data types
Expand All @@ -85,8 +29,6 @@ ParMETIS uses the same data types for integers and floating point numbers (32/64
integers and single/double precision floating point numbers) as used when configuring
and building METIS.


## Copyright & License Notice
Copyright 1998-2020, Regents of the University of Minnesota


Copyright 1998-2020, Regents of the University of Minnesota
69 changes: 69 additions & 0 deletions cmake/GitSubmodule.cmake
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
# get/update Git submodule directory to CMake, assuming the
# Git submodule directory is a CMake project.
# If the submodule directory is not in the same directory, descend level by level with multiple
# git_submodule() calls.
#
# For example, in the MUMPS project, we have submodule directories
# mumps/parmetis/METIS/GKlib
#
# from the mumps/ directory to enable METIS but not ParMETIS if the user desires, we do
# git_submodule(${PROJECT_SOURCE_DIR}/parmetis)
# if(MUMPS_parmetis)
# add_subdirectory(${PROJECT_SOURCE_DIR}/parmetis)
# # ParMETIS project itself handles METIS submodule, then METIS handles GKlib submodule
# else()
# git_submodule(${PROJECT_SOURCE_DIR}/parmetis/METIS)
# add_subdirectory(${PROJECT_SOURCE_DIR}/parmetis/METIS)
# METIS project itself handles GKlib submodule
# endif()


function(git_submodule submod_dir)


if(EXISTS ${submod_dir}/CMakeLists.txt)
return()
endif()

find_package(Git REQUIRED)

set(CMAKE_EXECUTE_PROCESS_COMMAND_ECHO STDOUT)

cmake_path(GET submod_dir PARENT_PATH mod_dir)
# we need to descend level by level

if(IS_DIRECTORY ${mod_dir}/.git)

message(STATUS "${mod_dir} is a Git repository, updating submodule ${submod_dir}")

execute_process(COMMAND ${GIT_EXECUTABLE} submodule update --init --recursive -- ${submod_dir}
WORKING_DIRECTORY ${mod_dir}
COMMAND_ERROR_IS_FATAL ANY
)

else()

cmake_path(GET submod_dir STEM submod_name)
message(STATUS "${PROJECT_SOURCE_DIR} is not a Git repository.")
message(STATUS "Getting ${mod_dir}/.gitmodules info to Git clone ${submod_name} into ${submod_dir}")

execute_process(
COMMAND ${GIT_EXECUTABLE} config
--file ${mod_dir}/.gitmodules
--get submodule.${submod_name}.url
WORKING_DIRECTORY ${mod_dir}
OUTPUT_VARIABLE submod_url
OUTPUT_STRIP_TRAILING_WHITESPACE
COMMAND_ERROR_IS_FATAL ANY
)
# Some platforms like Windows, Git might refuse to clone into a totally empty existing directory
# this is a known technique, to "git clone" from that empty submod_dir directory to make it work.
execute_process(
COMMAND ${GIT_EXECUTABLE} clone ${submod_url} ${submod_dir}
WORKING_DIRECTORY ${submod_dir}
COMMAND_ERROR_IS_FATAL ANY
)

endif()

endfunction()
7 changes: 7 additions & 0 deletions cmake/config.cmake.in
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
@PACKAGE_INIT@

include(${CMAKE_CURRENT_LIST_DIR}/@[email protected])

find_dependency(metis CONFIG)

check_required_components(@PROJECT_NAME@)
Loading