cmake_minimum_required(VERSION 3.10)
project(util)

# control where the static and shared libraries are built so that on windows
# we don't need to tinker with the path to run the executable
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY "${PROJECT_BINARY_DIR}")
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY "${PROJECT_BINARY_DIR}")
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY "${PROJECT_BINARY_DIR}")

set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD_REQUIRED True)

#find_package(OpenMP)
#if(OpenMP_CXX_FOUND)
#    target_link_libraries(darc PUBLIC OpenMP::OpenMP_CXX)
#endif()

option(BUILD_SHARED_LIBS "Build using shared libraries" ON)

# the version number.
set(darc_VERSION_MAJOR 3)
set(darc_VERSION_MINOR 2)

if(APPLE)
  set(CMAKE_INSTALL_RPATH "@executable_path/../lib")
elseif(UNIX)
  set(CMAKE_INSTALL_RPATH "$ORIGIN/../lib")
endif()

# configure a header file to pass the version number only
#configure_file(
#  "${PROJECT_SOURCE_DIR}/darcConfig.h.in"
#  "${PROJECT_BINARY_DIR}/darcConfig.h"
#  )

# Note the use of the variable EXTRA_LIBS to collect up any optional libraries
# to later be linked into the executable. The variable EXTRA_INCLUDES is used
# similarly for optional header files. 
get_filename_component(PARENT_DIR ../ ABSOLUTE)
#list(APPEND EXTRA_LIBS Sprs Darc )
list(APPEND EXTRA_LIBS Sprs Sarp Starc Omc Chn Vsi Tools Alex Psed Gsmo
	Hat Aln Gsq Blst Tax Pdb Afn Mgs conjugrad ccmpred Darc 
	Cdht Cmc Gsq Hmm Mgs Pmc Prb Rpm Sprc Tax Twp )

list(APPEND EXTRA_INCLUDES 
	"${PARENT_DIR}/lib/libafn"
	"${PARENT_DIR}/lib/libaln" 
	"${PARENT_DIR}/lib/libblst" 
	"${PARENT_DIR}/lib/libtax" 
	"${PARENT_DIR}/lib/libhat" 
	"${PARENT_DIR}/lib/libalex" 
	"${PARENT_DIR}/lib/libtools" 
	"${PARENT_DIR}/lib/libpdb" 
	"${PARENT_DIR}/lib/libhpt" 
	"${PARENT_DIR}/lib/libchn" 
	"${PARENT_DIR}/lib/libvsi" 
	"${PARENT_DIR}/lib/libsarp" 
	"${PARENT_DIR}/lib/libpsed" 
	"${PARENT_DIR}/lib/libstarc" 
	"${PARENT_DIR}/lib/libgsmo" 
	"${PARENT_DIR}/lib/libomc" 
	"${PARENT_DIR}/lib/libccmpred" 
	"${PARENT_DIR}/lib/libccmpred/libconjugrad" 
	"${PARENT_DIR}/lib/libdarc" 
	"${PARENT_DIR}/lib/libsprs" 
        "${PARENT_DIR}/lib/libcdht "
	"${PARENT_DIR}/lib/libcmc"
        "${PARENT_DIR}/lib/libgsq"
        "${PARENT_DIR}/lib/libhmm"
        "${PARENT_DIR}/lib/libmgs"
        "${PARENT_DIR}/lib/libpmc"
        "${PARENT_DIR}/lib/libprb"
        "${PARENT_DIR}/lib/librpm"
        "${PARENT_DIR}/lib/libsprc"
        "${PARENT_DIR}/lib/libtax"
        "${PARENT_DIR}/lib/libtwp"
	"${PARENT_DIR}/lib/include" 
	)

# add the executable
add_executable(cma2aln cma2aln.cxx)
target_link_libraries(cma2aln ${EXTRA_LIBS} )
include_directories(${PARENT_DIR}/lib/include  ${EXTRA_INCLUDES})

add_executable(matchvsi matchvsi.cxx)
target_link_libraries(matchvsi ${EXTRA_LIBS} )

add_executable(subcma subcma.cxx)
target_link_libraries(subcma ${EXTRA_LIBS} )

add_executable(garma garma.cxx)
target_link_libraries(garma ${EXTRA_LIBS} )

add_executable(cma_recomb cma_recomb_main.cxx)
target_link_libraries(cma_recomb ${EXTRA_LIBS} )

add_executable(exact exact.cxx)
target_link_libraries(exact ${EXTRA_LIBS} )

add_executable(domains domains.cxx)
target_link_libraries(domains ${EXTRA_LIBS} )

add_executable(alphabet alphamain.cxx)
target_link_libraries(alphabet ${EXTRA_LIBS} )

add_executable(msadiff compare_sma.cc run_msadiff.cxx)
target_link_libraries(msadiff ${EXTRA_LIBS} )

add_executable(tweakseq tweakseq.cxx)
target_link_libraries(tweakseq ${EXTRA_LIBS} )

add_executable(msa2clustalw msa2clustalw.cxx)
target_link_libraries(msa2clustalw ${EXTRA_LIBS} )

add_executable(msa2selex msa2selex.cxx)
target_link_libraries(msa2selex ${EXTRA_LIBS} )

add_executable(selex2cma selex2cma.cxx)
target_link_libraries(selex2cma ${EXTRA_LIBS} )

add_executable(recombine_msa recombine_msa.cxx)
target_link_libraries(recombine_msa ${EXTRA_LIBS} )

add_executable(superimpose superimpose.cxx)
target_link_libraries(superimpose ${EXTRA_LIBS} )

add_executable(tree2hpt tree2hpt.cxx)
target_link_libraries(tree2hpt ${EXTRA_LIBS} )

add_executable(chn_see chn_see.cxx)
target_link_libraries(chn_see ${EXTRA_LIBS} )

add_executable(chn_pps chn_pps.cxx)
target_link_libraries(chn_pps ${EXTRA_LIBS} )

add_executable(chn_aln chn_aln.cxx)
target_link_libraries(chn_aln ${EXTRA_LIBS} )

add_executable(gblastpgp gblastpgp.cxx)
target_link_libraries(gblastpgp ${EXTRA_LIBS} )

add_executable(SP_score SP_score.cxx)
target_link_libraries(SP_score ${EXTRA_LIBS} )

add_executable(chn_vsi chn_vsi.cxx)
target_link_libraries(chn_vsi ${EXTRA_LIBS} )

add_executable(findfullsq findfullsq.cxx)
target_link_libraries(findfullsq ${EXTRA_LIBS} )

add_executable(unrelatedseq unrelatedseq.cxx)
target_link_libraries(unrelatedseq ${EXTRA_LIBS} )

add_executable(gor_driver gor_driver_main.cxx)
target_link_libraries(gor_driver ${EXTRA_LIBS} )

add_executable(histogram histogram.cxx)
target_link_libraries(histogram ${EXTRA_LIBS} )

add_executable(hypergeo hypergeo.cxx)
target_link_libraries(hypergeo ${EXTRA_LIBS} )

add_executable(convert_hpt ConvertHptViaTemplate.cc convert_hpt.cxx)
target_link_libraries(convert_hpt ${EXTRA_LIBS} )

add_executable(hist_test hist_main.cxx)
target_link_libraries(hist_test ${EXTRA_LIBS} )

add_executable(bp2dc bp2dc_typ.cxx run_bp2dc.cxx)
target_link_libraries(bp2dc ${EXTRA_LIBS} )

#add_executable(surface surface.cxx)
#target_link_libraries(surface ${EXTRA_LIBS} )

add_executable(find_triad find_triad.cxx)
target_link_libraries(find_triad ${EXTRA_LIBS} )

add_executable(asset asset.cxx)
target_link_libraries(asset ${EXTRA_LIBS} )

add_executable(seqset seqset.cxx)
target_link_libraries(seqset ${EXTRA_LIBS} )

# add the binary tree to the search path for include files
# so that we will find darcConfig.h
#target_include_directories(darc PRIVATE "${PROJECT_BINARY_DIR}" ${EXTRA_INCLUDES} )
target_include_directories(darc PUBLIC "${PROJECT_BINARY_DIR}" ${EXTRA_INCLUDES} )

# add the install targets
#install(TARGETS darc DESTINATION bin)
#install(FILES "${PROJECT_BINARY_DIR}/darcConfig.h"
#  DESTINATION include
#  )

# Compile with OpenMP if available
if(WITH_OMP)
        find_package(OpenMP)
endif(WITH_OMP)
if(OPENMP_FOUND)
#        list(APPEND SOURCES evaluate_cpu_omp.c)
        add_definitions("-DOPENMP")
endif(OPENMP_FOUND)

if(OPENMP_FOUND)
        target_link_libraries(darc OpenMP::OpenMP_CXX)
endif(OPENMP_FOUND)

# OpenMP=on by default. Disable compiling with OpenMP using cmake -DWITH_OMP=OFF
if(NOT DEFINED WITH_OMP)
        set(WITH_OMP ON)
endif(NOT DEFINED WITH_OMP)

# CUDA on by default. Disable compiling with cuda using cmake -DWITH_CUDA=OFF
if(NOT DEFINED WITH_CUDA)
        set(WITH_CUDA ON)
endif(NOT DEFINED WITH_CUDA)

# Compile with CUDA if we can find the SDK
if(WITH_CUDA)
	find_package(CUDA)
endif(WITH_CUDA)
if(CUDA_FOUND)
        check_language(CUDA)
        enable_language(CUDA)
        add_definitions(-DCUDA)
        include_directories(${CMAKE_CUDA_TOOLKIT_INCLUDE_DIRECTORIES})
        list(APPEND SOURCES evaluate_cuda.c evaluate_cuda_kernels.cu)
	set(CMAKE_CUDA_FLAGS ${CMAKE_NVCC_FLAGS} --ccbin $(CMAKE_CXX_COMPILER))
        set_target_properties(darc PROPERTIES CUDA_SEPERABLE_COMPILATION ON)
endif(CUDA_FOUND)

