-
Notifications
You must be signed in to change notification settings - Fork 279
Development Workflow
nupic.core is a c++ project comprising the core algorithms of the Numenta Platform for Intelligent Computing (NuPIC) and uses CMake, a cross-platform build system generator, for automating many of the processes surrounding development.
See the README for requirements and developer installation instructions.
CMake is a build configuration tool, and is used in our case to generate the build scripts necessary for building nupic.core
. CMake is invoked on the command line with the cmake
command, but in some cases it may be cmake28
or the like, depending on your OS. The cmake
command requires a path to a directory containing a CMakeLists.txt
file, which is the primary configuration file used to configure a build. An overview describing the format of CMakeLists.txt
can be found at http://www.cmake.org/cmake-tutorial/.
All of the c++ source code can be found in src/
relative to the root of the nupic.core source tree. src/CMakeLists.txt
is the CMake configuration file, which contains all of the instructions for building libnupic_core
, examples, and associated unit tests. Should you need to add a new file to be compiled along with, and linked into libnupic_core
, the file must be included in the list of files in the associated add_library()
function call in src/CMakeLists.txt
. For example:
add_library(${LIB_STATIC_NUPICCORE}
STATIC
nta/algorithms/BitHistory.cpp
nta/algorithms/Cell.cpp
nta/algorithms/Cells4.cpp
...
nta/utils/StringUtils.cpp
nta/utils/TRandom.cpp
nta/utils/Watcher.cpp)
By convention, the files are listed in alphabetical order, including the full path relative to src/
.
Similarly, to add unit tests, add the .cpp
-suffixed c++ files in the call to add_executable()
associated with ${EXECUTABLE_GTESTS}
. For example:
add_executable(${EXECUTABLE_GTESTS}
test/unit/algorithms/CondProbTableTest.cpp
test/unit/algorithms/ConnectionsTest.cpp
test/unit/algorithms/FastCLAClassifierTest.cpp
...
test/unit/UnitTestMain.cpp
test/unit/utils/RandomTest.cpp
test/unit/utils/WatcherTest.cpp)
Also, add the .hpp
-suffixed header files to the ${TEST_HEADERS}
list:
set(TEST_HEADERS
test/unit/algorithms/CondProbTableTest.hpp
test/unit/algorithms/ConnectionsTest.hpp
test/unit/algorithms/FastCLAClassifierTest.hpp
...
test/unit/types/FractionTest.hpp
test/unit/utils/RandomTest.hpp
test/unit/utils/WatcherTest.hpp)
When you make changes to CMakeLists.txt
, or if you need to change any of the arguments to cmake
, you will need to re-run cmake
in order to apply the changes and build the new Makefiles. However, you need not run cmake
between builds. make
will re-build any targets that depend on any files that have changed since the last build. In order to do a completely clean build, remove the contents of the build directory (or completely remove the build directory), and re-run cmake
to generate new Makefiles from scratch.
Should you need to add new definitions, look for add_definitions()
in CMakeLists.txt
and add the definition to the list. For example:
# Compiler `-D*` definitions
add_definitions(-DNTA_PLATFORM_${PLATFORM}${BITNESS}
-DHAVE_CONFIG_H
-DNTA_INTERNAL
-DBOOST_NO_WREGEX
-DNUPIC2
-DNTA_ASSERTIONS_ON
-DNTA_ASM)
Once built, and installed, libnupic_core.a
is the static library, and can be found in lib/
relative to the installation prefix. Meanwhile, the headers can be found in include/
, also relative to the installation prefix. Including libnupic_core
in your project is a matter of ensuring that the headers are available at compile-time (typically in the form of the -I
or -i
compiler flags), and libnupic_core.a
is linked in at link-time (typically in the form of -L<installation prefix>/lib -lnupic_core
link flags). NuPIC, for example, also uses CMake and utilizes the find_library()
function paired with add_library()
to include libnupic_core
in the project:
find_library(LIB_STATIC_NUPICCORE_LOC nupic_core "${NUPIC_CORE}/lib")
add_library(${LIB_STATIC_NUPICCORE_LOC} STATIC IMPORTED GLOBAL)
The above is translated into the proper compiler and linker flags when the nupic build is configured. See https://github.com/numenta/nupic/blob/master/CMakeLists.txt#L237-L240 for context.
Internally, the examples and tests use libnupic_core_solo
, which is libnupic_core
without the externals bundled into the static library.
Using helloregion
as an example, ${COMMON_LIBS}
is a list of libraries to link in, including libnupic_core_solo
, ${COMPILE_FLAGS}
is a set of compiler flags common to the project, ${BITNESS}
is 32
or 64
and ${STDLIB}
is one of -stdlib=libc++
or -stdlib=libstdc++
. For most use-cases, you can copy-and-paste the following, replacing the relevant variable names and source file(s):
set(EXECUTABLE_HELLOREGION helloregion)
add_executable(${EXECUTABLE_HELLOREGION} examples/regions/helloregions.cpp)
target_link_libraries(${EXECUTABLE_HELLOREGION} ${COMMON_LIBS})
set_target_properties(${EXECUTABLE_HELLOREGION}
PROPERTIES COMPILE_FLAGS ${COMPILE_FLAGS})
LINK_FLAGS "-m${BITNESS} ${STDLIB}")
add_dependencies(${EXECUTABLE_HELLOREGION} ${COMMON_LIBS})
add_executable()
above, implicitly adds the helloregion
target. The executable that the above lines produce at build time can be executed with the make helloregion
command. In order to include the binary as part of the installation the target need be included in the install directives. For example:
install(TARGETS
${LIB_STATIC_NUPICCORE}
${LIB_STATIC_GTEST}
${EXECUTABLE_HELLOREGION}
${EXECUTABLE_HTMTEST}
${EXECUTABLE_GTESTS}
RUNTIME DESTINATION bin
LIBRARY DESTINATION lib
ARCHIVE DESTINATION lib)