mprausa/epsilon

Compiling epsilon on Fedora 28

Opened this issue · 2 comments

vsht commented

Hi,

in Issue #3, I have already reported some troubles getting epsilon to compile on Fedora 26. Unfortunately, the same happens also on Fedora 28, which raises the question whether one should try to improve the corresponding cmake script. After some fiddling with it I finally managed to compile epsilon without compiling the GiNaC library from the upstream. The main trouble seems to be this check

# Check if the version embedded into the library is the same as the one in the headers.
...

from FindGiNAC.cmake, since for some reason it always fails.

Anyway, for the benefit of other Fedora users here is my recipe to compile Epsilon on our distro

  • Install ginac and cln libraries
sudo dnf install cln cln-devel ginac ginac-devel ginac-utils
  • Clone the libFermat repository
git clone https://github.com/mprausa/libFermat.git
cd libFermat
  • Run cmake. Notice that if libFermat.so doesn't go to /usr/lib64 (which we achieve by setting the
    extra variables INSTALL_LIB_DIR:PATH and CMAKE_INSTALL_PREFIX), then epsilon won't be able to find the library later on.
cmake -DCMAKE_INSTALL_PREFIX=/usr -DINSTALL_LIB_DIR:PATH=lib64

Here is the sample output of this command

-- The C compiler identification is GNU 8.1.1
-- The CXX compiler identification is GNU 8.1.1
-- Check for working C compiler: /usr/bin/cc
-- Check for working C compiler: /usr/bin/cc -- works
-- Detecting C compiler ABI info
-- Detecting C compiler ABI info - done
-- Detecting C compile features
-- Detecting C compile features - done
-- Check for working CXX compiler: /usr/bin/c++
-- Check for working CXX compiler: /usr/bin/c++ -- works
-- Detecting CXX compiler ABI info
-- Detecting CXX compiler ABI info - done
-- Detecting CXX compile features
-- Detecting CXX compile features - done
-- Configuring done
-- Generating done
-- Build files have been written to: /media/Data/Projects/Other/libFermat
  • Run make and install the library.
make && sudo make install

The output:

Scanning dependencies of target Fermat
[ 16%] Building CXX object CMakeFiles/Fermat.dir/src/Fermat.cpp.o
[ 33%] Building CXX object CMakeFiles/Fermat.dir/src/FermatArray.cpp.o
[ 50%] Building CXX object CMakeFiles/Fermat.dir/src/FermatExpression.cpp.o
[ 66%] Linking CXX shared library libFermat.so
[ 66%] Built target Fermat
Scanning dependencies of target fermat_exe
[ 83%] Building CXX object CMakeFiles/fermat_exe.dir/tool/fermat.cpp.o
[100%] Linking CXX executable fermat
[100%] Built target fermat_exe
[ 66%] Built target Fermat
[100%] Built target fermat_exe
Install the project...
-- Install configuration: "Debug"
-- Up-to-date: /usr/include
-- Up-to-date: /usr/include/FermatException.h
-- Up-to-date: /usr/include/FermatExpression.h
-- Up-to-date: /usr/include/FermatArray.h
-- Up-to-date: /usr/include/Fermat.h
-- Up-to-date: /usr/include
-- Up-to-date: /usr/include/lfpstream.h
-- Installing: /usr/lib64/libFermat.so
-- Installing: /usr/bin/fermat
-- Set runtime path of "/usr/bin/fermat" to ""
-- Installing: /usr/lib/cmake/libFermat/libFermatConfig.cmake
-- Up-to-date: /usr/lib/cmake/libFermat/libFermatTargets.cmake
-- Installing: /usr/lib/cmake/libFermat/libFermatTargets-debug.cmake
  • Clone the epsilon repository
git clone https://github.com/mprausa/epsilon.git
cd epsilon
  • Now comes the interesting part: Open cmake/modules/FindGiNaC.cmake, delete the following lines
# Check if the version embedded into the library is the same as the one in the headers.
if (GINAC_INCLUDE_DIRS AND GINAC_LIBRARIES AND NOT CMAKE_CROSSCOMPILING)
	include(CheckCXXSourceRuns)
	set(_save_required_includes ${CMAKE_REQUIRED_INCLUDES})
	set(_save_required_libraries ${CMAKE_REQUIRED_LIBRARIES})
	set(CMAKE_REQUIRED_INCLUDES ${CMAKE_REQUIRED_INCLUDES} ${GINAC_INCLUDE_DIRS})
	set(CMAKE_REQUIRED_LIBRARIES ${CMAKE_REQUIRED_LIBRARIES} ${GINAC_LIBRARIES})
	check_cxx_source_runs("
		#include <ginac/version.h>
		#include <cln/version.h>
		#include <cstdio>
		int main() {
			return (CL_VERSION_MAJOR == cln::version_major) &&
			       (CL_VERSION_MINOR == cln::version_minor) &&
			       (CL_VERSION_PATCHLEVEL == cln::version_patchlevel) &&
			       (GINACLIB_MAJOR_VERSION == GiNaC::version_major) &&
			       (GINACLIB_MINOR_VERSION == GiNaC::version_minor) &&
			       (GINACLIB_MICRO_VERSION == GiNaC::version_micro) ? 0 : 1;
		}
		"
		_ginac_version_matches)
	set(CMAKE_REQUIRED_LIBRARIES ${_save_required_libraries})
	set(CMAKE_REQUIRED_INCLUDES ${_save_required_includes})
	if (NOT _ginac_version_matches)
		if (NOT GINAC_FIND_QUIETLY)
			message(ERROR "header version differs from the library one, "
				      "please check your installation.")
		endif()
		set(GINAC_INCLUDE_DIRS GINAC-NOTFOUND)
		set(GINAC_LIBRARIES GINAC_NOTFOUND)
		set(GINAC_LIBRARY_DIRS)
		set(GINAC_VERSION)
	endif()
endif()

and save the file.

  • Run cmake. Here the variables GINAC_INCLUDE_DIRS and GINAC_LIBRARY_DIRS should point the cmake script to the correct (actually standard) location of the GiNaC headers and libraries. The extra flag
    for the compiler (explicit inclusion of the dl library) seems to be related with some weirdness in GCC 8.1, as I definitely did not need that on Fedora 26 (that shipped with GCC 7)
cmake -DCMAKE_INSTALL_PREFIX=/usr/local -DGINAC_INCLUDE_DIRS=/usr/include -DGINAC_LIBRARY_DIRS=/usr/lib64 -DCMAKE_CXX_FLAGS="-ldl"

The output

-- The C compiler identification is GNU 8.1.1
-- The CXX compiler identification is GNU 8.1.1
-- Check for working C compiler: /usr/bin/cc
-- Check for working C compiler: /usr/bin/cc -- works
-- Detecting C compiler ABI info
-- Detecting C compiler ABI info - done
-- Detecting C compile features
-- Detecting C compile features - done
-- Check for working CXX compiler: /usr/bin/c++
-- Check for working CXX compiler: /usr/bin/c++ -- works
-- Detecting CXX compiler ABI info
-- Detecting CXX compiler ABI info - done
-- Detecting CXX compile features
-- Detecting CXX compile features - done
-- Found PkgConfig: /usr/bin/pkg-config (found version "1.4.2") 
-- Checking for module 'cln'
--   Found cln, version 1.3.4
-- found CLN [/usr/include/cln/version.h], version 1.3.4
-- Performing Test _cl_version_matches
-- Performing Test _cl_version_matches - Success
-- Found CLN: /lib64/libcln.so (found suitable version "1.3.4", minimum required is "1.2.2") 
-- Checking for module 'ginac'
--   Found ginac, version 1.7.4
-- Found GiNaC: /lib64/libginac.so;/lib64/libcln.so (found suitable version "1.7.4", minimum required is "1.6.2") 
-- Configuring done
-- Generating done
-- Build files have been written to: /media/Data/Projects/Other/epsilon
  • Run make and install the program.
make && sudo make install

The output

[  6%] Built target functions_fer
Scanning dependencies of target epsilon
[ 13%] Building CXX object epsilon/CMakeFiles/epsilon.dir/src/Dyson.cpp.o
[ 20%] Building CXX object epsilon/CMakeFiles/epsilon.dir/src/Echelon.cpp.o
[ 26%] Building CXX object epsilon/CMakeFiles/epsilon.dir/src/Eigenvalues.cpp.o
[ 33%] Building CXX object epsilon/CMakeFiles/epsilon.dir/src/JordanSystem.cpp.o
[ 40%] Building CXX object epsilon/CMakeFiles/epsilon.dir/src/System.cpp.o
[ 46%] Building CXX object epsilon/CMakeFiles/epsilon.dir/src/TransformationQueue.cpp.o
[ 53%] Building CXX object epsilon/CMakeFiles/epsilon.dir/src/main.cpp.o
[ 60%] Linking CXX executable epsilon
[ 60%] Built target epsilon
[ 66%] Linking CXX executable epsilon-prepare
[100%] Built target epsilon-prepare
[  6%] Built target functions_fer
[ 60%] Built target epsilon
[100%] Built target epsilon-prepare
Install the project...
-- Install configuration: ""
-- Installing: /usr/local/bin/epsilon
-- Installing: /usr/local/bin/epsilon-prepare

That's it! You can run the shipped example

cd example 
./epsilon.sh

to make sure that epsilon is working properly. Hope that helps!

Cheers,
Vladyslav

Hi Vladyslav,

the error message

Check if the version embedded into the library is the same as the one in the headers.

is misleading. It also prints this error message if it fails to compile the example code you deleted from the FindGiNaC.cmake file.

I had a similar problem lately that could be traced back to a missing -ldl flag. I think this might also be the problem in your case.

I will try to fix this issue when I am back from vacation next week.

Cheers,
Mario

vsht commented

Hi Mario,

thanks for the prompt reply. Indeed, if one uses the -ldl flag from the very beginning, it is not necessary to delete the example code in FindGiNaC.cmake. So to compile epsilon on Fedora 28 it is sufficient to use just

cmake -DCMAKE_INSTALL_PREFIX=/usr/local -DGINAC_INCLUDE_DIRS=/usr/include -DGINAC_LIBRARY_DIRS=/usr/lib64 -DCMAKE_CXX_FLAGS="-ldl"

without any additional modifications. I did not notice it, since I first had to find a way to make cmake finish
without errors (which it does also without the flag if one deletes the piece of code I mentioned previously). Then when running make I noticed the problems with the linker and realized that one has to add -ldl to make things work.

In any case, my intention was just to provide a workaround/howto for the benefit of other Fedora users who might be less familiar with compiling from the source. It is of course up to you, whether and how you
might want to fix or improve things.

Cheers,
Vladyslav