<!---
CMake build script for ACM Collected Algorithms: DCUHRE and DQUAD
Copyright (C) 2025  Tim Kaune

This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Lesser General Public License as
published by the Free Software Foundation, either version 3 of the
License, or (at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU Lesser General Public License for more details.

You should have received a copy of the GNU Lesser General Public
License along with this program.  If not, see
<https://www.gnu.org/licenses/>.
--->

# ACM Collected Algorithms: DCUHRE and DQUAD #

This project provides a CMake framework, that automatically downloads the two
Fortran integrator libraries DCUHRE and DQUAD from the ACM Collected Algorithms
(<https://calgo.acm.org/>), converts them to C and builds them.

## Prerequisites ##

What you need:

- [Git](https://git-scm.com/) (optional) for getting the code and contributing
  to the project
- [CMake](https://cmake.org/) and [Ninja](https://ninja-build.org/) for building
  the project
- C compiler
  - GCC for Linux (<https://gcc.gnu.org/>)
  - Clang for Mac OS X (<https://clang.llvm.org/>)
  - Cygwin + GCC for Windows (<https://www.cygwin.com/>)
- NetlibF2C (<https://gitlab.aei.uni-hannover.de/netlib/netlib-f2c>)
- LoadStaticSharedTargets (<https://gitlab.aei.uni-hannover.de/cmake/loadstaticsharedtargets>)

### Linux (Ubuntu) ###

Use your distribution's package manager to install the necessary packages:

```shell
$ sudo apt-get install cmake ninja-build gcc
```

### Mac OS X ###

You will need one of the community package managers for Mac OS X:
[Homebrew](https://brew.sh/) or
[MacPorts](https://www.macports.org/install.php). For installing one of these,
please refer to their respective installation instructions.

#### Homebrew ####

```shell
$ brew install cmake ninja llvm
```

#### MacPorts ####

```shell
$ sudo port -v install cmake ninja clang-<XX>
```

where you have to replace `<XX>` with the latest stable version of Clang.
You can discover all available versions of Clang like this:

```shell
$ port search --name --line --regex '^clang-?\d*\.?\d*$'
```

### Windows ###

The easiest thing to do is using the [Windows Subsystem for Linux
(WSL)](https://learn.microsoft.com/en-us/windows/wsl/install) and follow the
Linux instructions above.

Otherwise, install [Git for Windows](https://gitforwindows.org/) for version
control and [cygwin](https://cygwin.com/install.html), which is a large
collection of GNU and Open Source tools which provide functionality similar to a
Linux distribution on Windows. During the `cygwin` installation you'll be
prompted to add additional packages. Search and select the following:

- `cmake`, `ninja` and `gcc-core` for the compiler and the build system

After `cygwin` finishes installing, use the cygwin terminal to start the build
process.

## How to compile ##

1. Clone this git repository or download the source code archive and unpack it
   to an arbitrary directory (e.g. `calgo-integrators`).
2. Go to this directory and type `cp ./CMakeUserPresets.template.json
   ./CMakeUserPresets.json`.
3. Next, type `cmake --workflow --list-presets`. A list of available build
   workflows will be shown to you.
4. For configuring, building and installing the project, type `cmake --workflow
   --preset user-shared-release-install`. This will try to populate the
   `./build` directory with a CMake configuration tree, execute the build and
   install the project. By default, the configured installation directory is
   `./install`.

   But it will __fail__ due to unaccepted licenses. Study the license text and
   proceed to the next step.
5. Open `./CMakeUserPresets.json` in your favorite editor and set
   `"NetlibF2C_LICENSE_ACCEPTED": true` in the first configure preset
   `"user-config"`. Repeat step 4. It'll fail again with the next license. Study
   the license text and proceed to set `"CalgoIntegrators_LICENSE_ACCEPTED":
   true`.
6. Repeat step 4. Configuring, building and installing should be successful now.
7. Repeat step 6. for the other user workflow presets
   `user-shared-debug-install`, `user-static-release-install` and
   `user-static-debug-install` as needed.

## How to use ##

Now, the integrator code is compiled and you can use it in other projects. The
installed integrator package is discoverable by CMake as __CalgoIntegrators__.
In the `CMakeLists.txt` of the other project, call:

```cmake
include(FetchContent)

FetchContent_Declare(
    CalgoIntegrators
    GIT_REPOSITORY "https://gitlab.aei.uni-hannover.de/netlib/calgo-integrators.git"
    GIT_TAG v1.11.0
    SYSTEM
    FIND_PACKAGE_ARGS 1.11.0 CONFIG NAMES CalgoIntegrators
)
set(CalgoIntegrators_INCLUDE_PACKAGING TRUE)
FetchContent_MakeAvailable(CalgoIntegrators)
```

This discovers an installed version of the CalgoIntegrators package or adds it
to the other project's install targets. To help CMake discover the
CalgoIntegrators package, call CMake for the other project like this:

```shell
$ cmake -B ./build -D "CMAKE_PREFIX_PATH=/path/to/CalgoIntegrators/install/prefix"
```

Replace the path to the CalgoIntegrators install prefix with the actual path on
your system! If CalgoIntegrators is installed in a proper system-wide location,
the `CMAKE_PREFIX_PATH` shouldn't be necessary.

This makes two CMake targets available to you, the `Netlib::DCUHRE` and the
`Netlib::DQUAD` library targets (static or shared depends on the value of
`BUILD_SHARED_LIBS` in the other project). The `Netlib::libf2c` is already
contained in these targets.

For more information read the two papers referenced below.

## References ##

Paola Favati, Grazia Lotti, and Francesco Romani. 1991. Algorithm 691: Improving
QUADPACK automatic integration routines. ACM Trans. Math. Softw. 17, 2 (June
1991), 218–232. DOI:<https://dl.acm.org/doi/10.1145/108556.108580>

Jarle Berntsen, Terje O. Espelid, and Alan Genz. 1991. Algorithm 698: DCUHRE: an
adaptive multidemensional integration routine for a vector of integrals. ACM
Trans. Math. Softw. 17, 4 (Dec. 1991), 452–456.
DOI:<https://dl.acm.org/doi/10.1145/210232.210234>