#
# This is a CMake makefile.  You can find the cmake utility and
# information about it at http://www.cmake.org
#
#
# This cmake file tries to find installed BLAS and LAPACK libraries.  
# It looks for an installed copy of the Intel MKL library first and then
# attempts to find some other BLAS and LAPACK libraries if you don't have 
# the Intel MKL.
#
#  blas_found        - True if BLAS is available
#  lapack_found      - True if LAPACK is available
#  blas_libraries    - link against these to use BLAS library 
#  lapack_libraries  - link against these to use LAPACK library 

# setting this makes CMake allow normal looking if else statements
SET(CMAKE_ALLOW_LOOSE_LOOP_CONSTRUCTS true)

SET(blas_found 0)
SET(lapack_found 0)


if (UNIX)
    message(STATUS "Searching for BLAS and LAPACK")

    include(CheckTypeSize)
    check_type_size( "void*" SIZE_OF_VOID_PTR)

    if (SIZE_OF_VOID_PTR EQUAL 8)
        set( mkl_search_path
            /opt/intel/mkl/*/lib/em64t
            /opt/intel/mkl/lib/intel64
            /opt/intel/lib/intel64
            )

        find_library(mkl_intel mkl_intel_lp64 ${mkl_search_path})
    else()
        set( mkl_search_path
            /opt/intel/mkl/*/lib/32
            /opt/intel/mkl/lib/ia32
            /opt/intel/lib/ia32
            )

        find_library(mkl_intel mkl_intel ${mkl_search_path})
    endif()

   include(CheckLibraryExists)


   # Search for the needed libraries from the MKL.  We will try to link against the mkl_rt
   # file first since this way avoids linking bugs in some cases.
   find_library(mkl_rt mkl_rt ${mkl_search_path})
   mark_as_advanced(  mkl_rt )
   # if we found the MKL 
   if ( mkl_rt)
      set(blas_libraries  ${mkl_rt} )
      set(lapack_libraries  ${mkl_rt} )
      set(blas_found 1)
      set(lapack_found 1)
      set(found_intel_mkl 1)
      message(STATUS "Found Intel MKL BLAS/LAPACK library")
   endif()



   if (NOT found_intel_mkl)
      # Search for the needed libraries from the MKL.  This time try looking for a different
      # set of MKL files and try to link against those.
      find_library(mkl_core mkl_core ${mkl_search_path})
      find_library(mkl_thread mkl_intel_thread ${mkl_search_path})
      find_library(mkl_iomp iomp5 ${mkl_search_path})
      find_library(mkl_pthread pthread ${mkl_search_path})

      mark_as_advanced( mkl_intel mkl_core mkl_thread mkl_iomp mkl_pthread)
      # If we found the MKL 
      if (mkl_intel AND mkl_core AND mkl_thread AND mkl_iomp AND mkl_pthread)
         set(blas_libraries ${mkl_intel} ${mkl_core} ${mkl_thread} ${mkl_iomp} ${mkl_pthread})
         set(lapack_libraries ${mkl_intel} ${mkl_core} ${mkl_thread} ${mkl_iomp} ${mkl_pthread})
         set(blas_found 1)
         set(lapack_found 1)
         set(found_intel_mkl 1)
         message(STATUS "Found Intel MKL BLAS/LAPACK library")
      endif()
   endif()


   # try to find some other LAPACK libraries if we didn't find the MKL
   set(extra_paths
        /usr/lib64
        /usr/lib64/atlas-sse3
        /usr/lib64/atlas-sse2
        /usr/lib64/atlas
        /usr/lib
        /usr/lib/atlas-sse3
        /usr/lib/atlas-sse2
        /usr/lib/atlas)


   if (NOT lapack_found)
      find_library(lapack_lib NAMES lapack lapack-3 PATHS ${extra_paths})
      if (lapack_lib)
         set(lapack_libraries ${lapack_lib})
         set(lapack_found 1)
         message(STATUS "Found LAPACK library")
      endif()
      mark_as_advanced( lapack_lib)
   endif()

   
   # try to find some other BLAS libraries if we didn't find the MKL
   
   if (NOT blas_found)
      find_library(atlas_lib atlas PATHS ${extra_paths})
      find_library(cblas_lib cblas PATHS ${extra_paths})
      if (atlas_lib AND cblas_lib)
         set(blas_libraries ${atlas_lib} ${cblas_lib})
         set(blas_found 1)
         message(STATUS "Found ATLAS BLAS library")
      endif()
      mark_as_advanced( atlas_lib cblas_lib)
   endif()


   if (NOT blas_found)
      find_library(cblas_lib cblas PATHS ${extra_paths})
      if (cblas_lib)
         set(blas_libraries ${cblas_lib})
         set(blas_found 1)
         message(STATUS "Found CBLAS library")
      endif()
      mark_as_advanced( cblas_lib)
   endif()

   
   if (NOT blas_found)
      find_library(generic_blas blas PATHS ${extra_paths})
      if (generic_blas)
         set(blas_libraries ${generic_blas})
         set(blas_found 1)
         message(STATUS "Found BLAS library")
      endif()
      mark_as_advanced( generic_blas)
   endif()




   # Make sure we really found a CBLAS library.  That is, it needs to expose
   # the proper cblas link symbols.  So here we test if one of them is present
   # and assume everything is good if it is. Note that we don't do this check if
   # we found the Intel MKL since for some reason CHECK_FUNCTION_EXISTS doesn't work
   # with it.  But it's fine since the MKL should always have cblas.
   if (blas_found AND NOT found_intel_mkl)
      INCLUDE (CheckFunctionExists)
      set(CMAKE_REQUIRED_LIBRARIES ${blas_libraries})
      CHECK_FUNCTION_EXISTS(cblas_ddot HAVE_CBLAS)
      if (NOT HAVE_CBLAS)
         message(STATUS "BLAS library does not have cblas symbols, so dlib will not use BLAS or LAPACK")
         set(blas_found 0)
         set(lapack_found 0)
      endif()
   endif()


   if (NOT blas_found)
      message(STATUS "***** No BLAS library found *****")
   endif()

endif()



