From b47853f45164f66a79f8d3432529e71ddd053b32 Mon Sep 17 00:00:00 2001 From: Bentoy13 Date: Tue, 8 Oct 2019 18:10:02 +0200 Subject: [PATCH 1/7] replace 'and' keyword not supported under MSVC --- src/main.cpp | 27 ++++++++++++++------------- 1 file changed, 14 insertions(+), 13 deletions(-) diff --git a/src/main.cpp b/src/main.cpp index e0b3ff3..8927442 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -23,6 +23,7 @@ COPYING for more details. #include #include #include +#include #include "optionsutil.h" #include "pllkmeansfuncs_void.h" @@ -611,7 +612,7 @@ int main(int argc, char* argv[]){ return 1; } - if (!(cout_verbosity > 1) and !(file_verbosity > 0)){ + if (!(cout_verbosity > 1) && !(file_verbosity > 0)){ std::cerr << "problem with options : cmse not requested, thus : valinfn has been set to " << valinfn << " but verbosity is not compatible : cout_verbosity is " << cout_verbosity << " and file_verbosity is " << file_verbosity << " . It is required that cout_verbosity > 1 or file_verbosirt > 0" << std::endl; return 1; } @@ -628,62 +629,62 @@ int main(int argc, char* argv[]){ return 1; } - if (uopts.options["cinfn"].isset and uopts.options["ioutfn"].isset){ + if (uopts.options["cinfn"].isset && uopts.options["ioutfn"].isset){ std::cerr << "problem with options : cannot set both cinfn and ioutfn" << std::endl; return 1; } - if ((uopts.options["soutfn"].isset and (file_verbosity != 2 and file_verbosity != 3) )){ + if ((uopts.options["soutfn"].isset && (file_verbosity != 2 && file_verbosity != 3) )){ std::cerr << "problem with options : soutfn is set, but file_verbosity is set to " << file_verbosity << ", either unset soutfn or set file_verbosity to 2 (or 3, but then include voutfn as well)" << std::endl; return 1; } - if ((uopts.options["voutfn"].isset and file_verbosity != 3)){ + if ((uopts.options["voutfn"].isset && file_verbosity != 3)){ std::cerr << "problem with options : voutfn is set, but file_verbosity is set to " << file_verbosity << ", either unset voutfn or set file_verbosity to 3" << std::endl; return 1; } - if ((uopts.options["moutfn"].isset and nruns == 1)){ + if ((uopts.options["moutfn"].isset && nruns == 1)){ std::cerr << "problem with options : moutfn is set, nruns is 1, either unset moutfn or set nruns to be greater than 1" << std::endl; return 1; } - if ((uopts.options["moutdir"].isset and nruns == 1)){ + if ((uopts.options["moutdir"].isset && nruns == 1)){ std::cerr << "problem with options : moutdir is set, nruns is 1, either unset moutdir or set nruns to be greater than 1" << std::endl; return 1; } - if ((uopts.options["voutfn"].isset and nruns != 1)){ + if ((uopts.options["voutfn"].isset && nruns != 1)){ std::cerr << "problem with options : voutfn is set, nruns is " << nruns << ", either unset voutfn or set nruns to 1" << std::endl; return 1; } - if ((uopts.options["soutfn"].isset and nruns != 1)){ + if ((uopts.options["soutfn"].isset && nruns != 1)){ std::cerr << "problem with options : soutfn is set, nruns is " << nruns << ", this combination is currently not supported, either unset soutfn or set nruns to 1" << std::endl; return 1; } - if ((uopts.options["voutfn"].isset == false and file_verbosity == 3)){ + if ((uopts.options["voutfn"].isset == false && file_verbosity == 3)){ std::cerr << "problem with options : voutfn is not set, but file_verbosity is set to 3, either lower file_verbosity to 0 or 2, or set voutfn" << std::endl; return 1; } - if (nruns != 1 and (uopts.options["cinfn"].isset || uopts.options["ind0fn"].isset )){ + if (nruns != 1 && (uopts.options["cinfn"].isset || uopts.options["ind0fn"].isset )){ std::cerr << "problem with options : nruns is set to " << nruns << ", but either cinfn or ind0fn is set. For nruns > 1, it is currently not possible to initialise from prespecified centroids or indices. Either reduce nruns to 1, or make sure neither cinfn nor indofn are set. With nruns > 1, init0 may be set. " << std::endl; return 1; } int ninitflags = uopts.options["cinfn"].isset + uopts.options["ind0fn"].isset + uopts.options["init0"].isset; if (ninitflags > 1){ - std::cerr << "at most one 1 of cinfn, ind0fn and init0 can be set" << std::endl; + std::cerr << "at most one 1 of cinfn, ind0fn && init0 can be set" << std::endl; return 1; } if ( - (uopts.options["cmsewritefn"].isset and !(uopts.options["cmserate"].isset)) || - (!(uopts.options["cmsewritefn"].isset) and uopts.options["cmserate"].isset)) + (uopts.options["cmsewritefn"].isset && !(uopts.options["cmserate"].isset)) || + (!(uopts.options["cmsewritefn"].isset) && uopts.options["cmserate"].isset)) { std::cerr << "problem with options : either 0 or 2 of cmsewritefn and cmserate need to be set\n"; return 1; From 4104ab1babd57499ef06d6b846dd2afd57a1aed2 Mon Sep 17 00:00:00 2001 From: Bentoy13 Date: Tue, 8 Oct 2019 18:11:34 +0200 Subject: [PATCH 2/7] add setenv function for windows support --- src/arrutilv2l0.h | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/src/arrutilv2l0.h b/src/arrutilv2l0.h index 7070700..eefefce 100644 --- a/src/arrutilv2l0.h +++ b/src/arrutilv2l0.h @@ -54,5 +54,19 @@ COPYING for more details. #include "arrutilv2l0blasless.h" #endif +#ifdef _MSC_VER +// add setenv undeer Windows +int setenv(const char *name, const char *value, int overwrite) +{ + int errcode = 0; + if (!overwrite) { + size_t envsize = 0; + errcode = getenv_s(&envsize, NULL, 0, name); + if (errcode || envsize) return errcode; + } + return _putenv_s(name, value); +} +#endif // _MSC_VER + #endif From 7744e226f6c3e0e39f152ce96c7c127dcd51a859 Mon Sep 17 00:00:00 2001 From: Bentoy13 Date: Tue, 8 Oct 2019 18:12:59 +0200 Subject: [PATCH 3/7] add for std::max --- src/barrierutil.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/barrierutil.cpp b/src/barrierutil.cpp index 13ba3ba..e6ddb7a 100644 --- a/src/barrierutil.cpp +++ b/src/barrierutil.cpp @@ -20,6 +20,7 @@ COPYING for more details. #include "barrierutil.h" #include +#include namespace stdthreadutil{ From ad640ec90646a4b13a9d167c7d8eb2b12229d906 Mon Sep 17 00:00:00 2001 From: Bentoy13 Date: Wed, 9 Oct 2019 09:15:34 +0200 Subject: [PATCH 4/7] force forwarding under MSVC --- src/initialise2.h | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/initialise2.h b/src/initialise2.h index 888aa4d..d97102a 100644 --- a/src/initialise2.h +++ b/src/initialise2.h @@ -156,7 +156,11 @@ std::tuple, std::unique_ptr, std::unique_p std::unique_ptr, std::unique_ptr, TFloat > - (std::move(C_uptr), std::move(C_l22s_uptr), std::move(ind0), TFloat(mse2)); +#ifdef _MSC_VER + (std::move(C_uptr), std::move(C_l22s_uptr), std::move(ind0), std::move(TFloat(mse2))); //force forwarding +#else + (std::move(C_uptr), std::move(C_l22s_uptr), std::move(ind0), TFloat(mse2)); +#endif } From 1963cd5c7c78bf2d81f95e85a76c234c80b106ca Mon Sep 17 00:00:00 2001 From: Bentoy13 Date: Wed, 9 Oct 2019 09:22:46 +0200 Subject: [PATCH 5/7] change and to && --- src/stringutilbase.cpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/stringutilbase.cpp b/src/stringutilbase.cpp index 54c562a..9b9186b 100644 --- a/src/stringutilbase.cpp +++ b/src/stringutilbase.cpp @@ -21,6 +21,8 @@ COPYING for more details. #include "stringutilbase.h" #include #include +#include + namespace stringutil{ //split the string tosplit by delim. With x appearances of delim in tosplit, the returned vector will have length x + 1 (even if appearances at the start, end, contiguous. std::vector split(const std::string & tosplit, const std::string & delim){ @@ -63,12 +65,12 @@ std::vector split(const std::string & tosplit){ unsigned it = 0; while (it != tosplit.size()){ - while (isws(tosplit[it]) and it != tosplit.size()){ + while (isws(tosplit[it]) && it != tosplit.size()){ ++it; } unsigned start = it; - while (!isws(tosplit[it]) and it != tosplit.size()){ + while (!isws(tosplit[it]) && it != tosplit.size()){ ++it; } unsigned end = it; From 88ad9ee58fbf65b5e8f2dbf0d7a2bf3b4c9727ea Mon Sep 17 00:00:00 2001 From: Bentoy13 Date: Wed, 9 Oct 2019 09:23:47 +0200 Subject: [PATCH 6/7] change and to && --- src/stringutilfile.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/stringutilfile.cpp b/src/stringutilfile.cpp index a6c92b5..0deaceb 100644 --- a/src/stringutilfile.cpp +++ b/src/stringutilfile.cpp @@ -63,7 +63,7 @@ bool file_has_2int_header(const std::string & filename){ return false; } /* next test that they are indeed integers */ - if (is_integer(bob[0]) and is_integer(bob[1])){ + if (is_integer(bob[0]) && is_integer(bob[1])){ return true; } From 9d409bab5837ad71d1589f9515388ef394d9b0c6 Mon Sep 17 00:00:00 2001 From: Bentoy13 Date: Wed, 9 Oct 2019 16:16:16 +0200 Subject: [PATCH 7/7] add draft for CMake Cmake files comprise two files, one for the lib placed in src, the other at the root for the test program --- CMakeLists.txt | 33 +++++++++++++++++++++++++++++++++ src/CMakeLists.txt | 34 ++++++++++++++++++++++++++++++++++ src/arrutilv2l0.h | 2 +- src/initialise2.h | 2 +- src/main.cpp | 2 +- 5 files changed, 70 insertions(+), 3 deletions(-) create mode 100644 CMakeLists.txt create mode 100644 src/CMakeLists.txt diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 0000000..7738f52 --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,33 @@ +cmake_minimum_required(VERSION 3.6.2) + +project(eakmeans) + +option(STATIC_LIBRARY "Build static library instead of shared library" OFF) +if(STATIC_LIBRARY) + set(LIB_TYPE "STATIC") +else() + set(LIB_TYPE "SHARED") +endif() +add_subdirectory(src) + +option(BUILD_MAIN "Build test executable" ON) +if(BUILD_MAIN) + set(EXE_SRC "${CMAKE_CURRENT_SOURCE_DIR}/src/main.cpp") + include_directories("${CMAKE_CURRENT_SOURCE_DIR}/src") + link_directories("${CMAKE_ARCHIVE_OUTPUT_DIRECTORY}" "${BLAS_FOLDER}/dll") + add_executable(${PROJECT_NAME} ${EXE_SRC}) + target_link_libraries(${PROJECT_NAME} PUBLIC ${LIB_EAKMEANS} ${BLAS}) + add_dependencies(${PROJECT_NAME} libeakmeans) + if(WIN32) + set_target_properties(${PROJECT_NAME} PROPERTIES LINK_FLAGS "/WHOLEARCHIVE:libeakmeans") + endif() +endif() + +option(PYTHON_KMEANS "Build Python integration of eakmeans." OFF) +if(PYTHON_KMEANS) + execute_process( + COMMAND python "${PROJECT_SOURCE_DIR}/setup.py" build_ext -b lib + WORKING_DIRECTORY ${PROJECT_SOURCE_DIR} + RESULT_VARIABLE py_result + ) +endif() diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt new file mode 100644 index 0000000..da0354b --- /dev/null +++ b/src/CMakeLists.txt @@ -0,0 +1,34 @@ +cmake_minimum_required(VERSION 3.6.2) + +project(libeakmeans) + +# We enable C++11 +set(CMAKE_CXX_STANDARD 11) + +set(TARGET_ARCHI "x64") +set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${TARGET_ARCHI}" CACHE PATH "Output library (lib) directory") +set(LIBEAKMEANS_OUTPUT_DIR ${CMAKE_ARCHIVE_OUTPUT_DIRECTORY}) + +option(USEBLAS "Use external BLAS library" OFF) +if(USEBLAS) + set(BLAS_FOLDER "${CMAKE_CURRENT_SOURCE_DIR}/../../OpenBLAS/build" CACHE PATH "Folder where to find BLAS distribution") + set(BLAS_NAME "libopenblas" CACHE STRING "Name of BLAS implementation") +endif() + +file(GLOB LIB_SRC *.cpp *.hpp *.h) +get_filename_component(main_cpp ${CMAKE_CURRENT_SOURCE_DIR}/main.cpp ABSOLUTE) +list(REMOVE_ITEM LIB_SRC "${main_cpp}") + +if(USEBLAS) + include_directories("${BLAS_FOLDER}/include") + find_library(BLAS ${BLAS_NAME} PATHS "${BLAS_FOLDER}" PATH_SUFFIXES lib;dll) +endif() + +add_library(${PROJECT_NAME} ${LIB_TYPE} ${LIB_SRC}) +set_target_properties(${PROJECT_NAME} PROPERTIES LINKER_LANGUAGE CXX) +target_include_directories (${PROJECT_NAME} PUBLIC {CMAKE_CURRENT_SOURCE_DIR}/src) + +if(USEBLAS) + target_link_libraries(${PROJECT_NAME} PRIVATE ${BLAS}) + target_compile_definitions(${PROJECT_NAME} PUBLIC "WITHBLAS") +endif() diff --git a/src/arrutilv2l0.h b/src/arrutilv2l0.h index eefefce..660bba4 100644 --- a/src/arrutilv2l0.h +++ b/src/arrutilv2l0.h @@ -55,7 +55,7 @@ COPYING for more details. #endif #ifdef _MSC_VER -// add setenv undeer Windows +// add setenv under Windows int setenv(const char *name, const char *value, int overwrite) { int errcode = 0; diff --git a/src/initialise2.h b/src/initialise2.h index d97102a..d301fef 100644 --- a/src/initialise2.h +++ b/src/initialise2.h @@ -160,7 +160,7 @@ std::tuple, std::unique_ptr, std::unique_p (std::move(C_uptr), std::move(C_l22s_uptr), std::move(ind0), std::move(TFloat(mse2))); //force forwarding #else (std::move(C_uptr), std::move(C_l22s_uptr), std::move(ind0), TFloat(mse2)); -#endif +#endif } diff --git a/src/main.cpp b/src/main.cpp index 8927442..e913642 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -677,7 +677,7 @@ int main(int argc, char* argv[]){ int ninitflags = uopts.options["cinfn"].isset + uopts.options["ind0fn"].isset + uopts.options["init0"].isset; if (ninitflags > 1){ - std::cerr << "at most one 1 of cinfn, ind0fn && init0 can be set" << std::endl; + std::cerr << "at most one 1 of cinfn, ind0fn and init0 can be set" << std::endl; return 1; }