Skip to content

Commit

Permalink
Compile NEURON mechanisms as C++ (#1597)
Browse files Browse the repository at this point in the history
* Make embedded .mod files C++ compatible.
* Generate C++ code from nocmodl instead of C.
* Require C++14, drop references to C++98/C++11.
* Retain C linkage for variables that are still referred to from C code,
  or which are loaded with dlopen().
* Fix deprecation warnings from compatibility wrappers in NEURON build.
* Add C++ mechanism documentation.
* nrnmingwenv: keep GCC toolchain for RxD reactions.
* Update CMake/semantic version to 9.0.0, update CoreNEURON submodule to
  have the same version.
* Update .gitignore.

Co-authored-by: Pramod S Kumbhar <[email protected]>
Co-authored-by: Alexandru Săvulescu <[email protected]>
Co-authored-by: Michael Hines <[email protected]>
  • Loading branch information
4 people authored Jun 20, 2022
1 parent 2c3a21d commit f242cc8
Show file tree
Hide file tree
Showing 89 changed files with 1,205 additions and 931 deletions.
4 changes: 2 additions & 2 deletions .clang-format.changes
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
SortIncludes: false
Standard: c++11
StatementMacros: [MKDLL, MKDLLdec, MKDLLif, MKDLLvp, MKDLLvpf]
Standard: c++14
StatementMacros: [MKDLL, MKDLLdec, MKDLLif, MKDLLvp, MKDLLvpf]
36 changes: 19 additions & 17 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
.clang-format
.cmake-format.yaml
external/tests/
nmodlconf.h.in
nrnconf.h.in
test/ringtest/*.dat
build
.DS_Store
.eggs/
Expand All @@ -21,25 +23,25 @@ virtualenv
# These files are generated at build time
# It would be a good idea to create them in the
# build directory in the future.
src/nrnoc/apcount.c
src/nrnoc/exp2syn.c
src/nrnoc/expsyn.c
src/nrnoc/feature.c
src/nrnoc/hh.c
src/nrnoc/apcount.cpp
src/nrnoc/exp2syn.cpp
src/nrnoc/expsyn.cpp
src/nrnoc/feature.cpp
src/nrnoc/hh.cpp
src/nrnoc/hh.mod.orig
src/nrnoc/hocusr.h
src/nrnoc/intfire1.c
src/nrnoc/intfire2.c
src/nrnoc/intfire4.c
src/nrnoc/netstim.c
src/nrnoc/intfire1.cpp
src/nrnoc/intfire2.cpp
src/nrnoc/intfire4.cpp
src/nrnoc/netstim.cpp
src/nrnoc/nrnversion.
src/nrnoc/nrnversion.h
src/nrnoc/oclmp.c
src/nrnoc/passive.c
src/nrnoc/pattern.c
src/nrnoc/ppmark.c
src/nrnoc/stim.c
src/nrnoc/svclmp.c
src/nrnoc/syn.c
src/nrnoc/vclmp.c
src/nrnoc/oclmp.cpp
src/nrnoc/passive.cpp
src/nrnoc/pattern.cpp
src/nrnoc/ppmark.cpp
src/nrnoc/stim.cpp
src/nrnoc/svclmp.cpp
src/nrnoc/syn.cpp
src/nrnoc/vclmp.cpp
share/lib/python/neuron/help_data.dat
4 changes: 2 additions & 2 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -17,14 +17,14 @@ if(DEFINED ENV{CRAYPE_VERSION})
endif()
project(
NEURON
VERSION 8.2.0
VERSION 9.0.0
LANGUAGES C CXX
HOMEPAGE_URL "https://www.neuron.yale.edu/neuron/")

# =============================================================================
# CMake common project settings
# =============================================================================
set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD 14)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS OFF)

Expand Down
6 changes: 3 additions & 3 deletions bin/nrnivmodl.in
Original file line number Diff line number Diff line change
Expand Up @@ -151,13 +151,13 @@ for i in "${files[@]}" ; do
dir_name="$(dirname "$f")"
# Note: indentation for shell lines in make rules must be a tab
echo "\
./${base_name// /\\ }.c: ${f// /\\ }.mod
./${base_name// /\\ }.cpp: ${f// /\\ }.mod
@printf \" -> \$(C_GREEN)NMODL\$(C_RESET) \$<\\\n\"
(cd \"$dir_name\"; @NRN_NOCMODL_SANITIZER_ENVIRONMENT_STRING@ MODLUNIT=\$(NRNUNITS) \$(NOCMODL) \"$base_name.mod\" -o \"$mdir\")
./${base_name// /\\ }.o: ./${base_name// /\\ }.c
./${base_name// /\\ }.o: ./${base_name// /\\ }.cpp
@printf \" -> \$(C_GREEN)Compiling\$(C_RESET) \$<\\\n\"
\$(COMPILE) -I\"$dir_name\" \$(INCLUDES) @CMAKE_CXX_COMPILE_OPTIONS_PIC@ -c \$< -o \$@
\$(CXXCOMPILE) -I\"$dir_name\" \$(INCLUDES) @CMAKE_CXX_COMPILE_OPTIONS_PIC@ -c \$< -o \$@
" >> "$MODMAKE"
done

Expand Down
14 changes: 5 additions & 9 deletions bin/nrnivmodl_makefile_cmake.in
Original file line number Diff line number Diff line change
Expand Up @@ -61,15 +61,11 @@ ifeq (@NRN_INCLUDE_MPI_HEADERS@, ON)
INCLUDES += $(if @MPI_C_INCLUDE_PATH@, -I$(subst ;, -I,@MPI_C_INCLUDE_PATH@),)
endif

# CC/CXX are always defined. If the definition comes from default change it
ifeq ($(origin CC), default)
CC = @CMAKE_C_COMPILER@
# CXX is always defined. If the definition comes from default change it
ifeq ($(origin CXX), default)
CXX = @CMAKE_CXX_COMPILER@
endif
CFLAGS = @BUILD_TYPE_C_FLAGS@ @CMAKE_C_FLAGS@
CXXFLAGS = @BUILD_TYPE_CXX_FLAGS@ @CMAKE_CXX_FLAGS@ @CXX11_STANDARD_COMPILE_OPTION@

COMPILE = $(CC) $(CFLAGS) @NRN_COMPILE_DEFS_STRING@ @NRN_COMPILE_FLAGS_STRING@
CXXFLAGS = @BUILD_TYPE_CXX_FLAGS@ @CMAKE_CXX_FLAGS@ @CMAKE_CXX14_STANDARD_COMPILE_OPTION@
CXXCOMPILE = $(CXX) $(CXXFLAGS) @NRN_COMPILE_DEFS_STRING@ @NRN_COMPILE_FLAGS_STRING@
CXX_LINK_EXE = $(CXX) $(CXXFLAGS) @CMAKE_EXE_LINKER_FLAGS@ @NRN_LINK_FLAGS_STRING@
CXX_LINK_SHARED = $(CXX) $(CXXFLAGS) @CMAKE_SHARED_LIBRARY_CREATE_CXX_FLAGS@ @CMAKE_SHARED_LIBRARY_CXX_FLAGS@ @CMAKE_SHARED_LINKER_FLAGS@
Expand Down Expand Up @@ -139,12 +135,12 @@ mech_lib_static: mod_func.o $(mod_objs) $(nrn_lib) build_always

mod_func.o: mod_func.cpp
@printf " -> $(C_GREEN)Compiling$(C_RESET) $<\n"
$(COMPILE) $(INCLUDES) @CMAKE_CXX_COMPILE_OPTIONS_PIC@ -c $< -o $@
$(CXXCOMPILE) $(INCLUDES) @CMAKE_CXX_COMPILE_OPTIONS_PIC@ -c $< -o $@

# Generic build c->o. Need PIC for shared lib
$(OBJS_DIR)/%.o: $(MODC_DIR)/%.c | $(OBJS_DIR)
@printf " -> $(C_GREEN)Compiling$(C_RESET) $<\n"
$(COMPILE) $(INCLUDES) @CMAKE_CXX_COMPILE_OPTIONS_PIC@ -c $< -o $@
$(CXXCOMPILE) $(INCLUDES) @CMAKE_CXX_COMPILE_OPTIONS_PIC@ -c $< -o $@


include makemod2c_inc
Expand Down
3 changes: 0 additions & 3 deletions cmake/CMakeListsNrnMech.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -66,9 +66,6 @@ foreach(link_lib ${NRN_LINK_LIBS})
string(APPEND NRN_LINK_DEFS " ${link_flag}")
endforeach()

# PGI add --c++11;-A option for c++11 flag
string(REPLACE ";" " " CXX11_STANDARD_COMPILE_OPTION "${CMAKE_CXX11_STANDARD_COMPILE_OPTION}")

# Compiler flags depending on cmake build type from BUILD_TYPE_<LANG>_FLAGS
string(TOUPPER "${CMAKE_BUILD_TYPE}" _BUILD_TYPE)
set(BUILD_TYPE_C_FLAGS "${CMAKE_C_FLAGS_${_BUILD_TYPE}}")
Expand Down
2 changes: 0 additions & 2 deletions cmake/CompilerHelper.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,5 @@ endif()
if(CMAKE_CXX_COMPILER_ID MATCHES "PGI")
# CMake adds strict standard complaint PGI flag "-A" which breaks compilation of old codes (e.g.
# spdlog, fmt)
set(CMAKE_CXX98_STANDARD_COMPILE_OPTION "")
set(CMAKE_CXX11_STANDARD_COMPILE_OPTION --c++11)
set(CMAKE_CXX14_STANDARD_COMPILE_OPTION --c++14)
endif()
2 changes: 1 addition & 1 deletion cmake/ConfigFileSetting.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -293,7 +293,7 @@ if(MINGW)
nrn_configure_file(nrnsetupmingw.nsi src/mswin)
nrn_configure_file(pre_setup_exe.sh src/mswin)
# Just name and not path since setup.exe user chooses location of install.
set(CC x86_64-w64-mingw32-gcc.exe)
set(CXX x86_64-w64-mingw32-g++.exe)
set(BUILD_MINGW_TRUE "")
set(BUILD_MINGW_FALSE "#")
set(nrnskip_rebase "#")
Expand Down
8 changes: 4 additions & 4 deletions cmake/MacroHelper.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -234,14 +234,14 @@ endmacro()
# =============================================================================
# Run nocmodl to convert NMODL to C
# =============================================================================
macro(nocmodl_mod_to_c modfile_basename)
macro(nocmodl_mod_to_cpp modfile_basename)
add_custom_command(
OUTPUT ${modfile_basename}.c
OUTPUT ${modfile_basename}.cpp
COMMAND
${CMAKE_COMMAND} -E env "MODLUNIT=${PROJECT_BINARY_DIR}/share/nrn/lib/nrnunits.lib"
${NRN_NOCMODL_SANITIZER_ENVIRONMENT} ${PROJECT_BINARY_DIR}/bin/nocmodl ${modfile_basename}.mod
COMMAND sed "'s/_reg()/_reg_()/'" ${modfile_basename}.c > ${modfile_basename}.c.tmp
COMMAND mv ${modfile_basename}.c.tmp ${modfile_basename}.c
COMMAND sed "'s/_reg()/_reg_()/'" ${modfile_basename}.cpp > ${modfile_basename}.cpp.tmp
COMMAND mv ${modfile_basename}.cpp.tmp ${modfile_basename}.cpp
DEPENDS nocmodl ${modfile_basename}.mod
WORKING_DIRECTORY ${PROJECT_BINARY_DIR}/src/nrniv)
endmacro()
Expand Down
4 changes: 3 additions & 1 deletion cmake/NeuronFileLists.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
# Lists of header files to install
# =============================================================================
set(HEADER_FILES_TO_INSTALL
bbsavestate.h
cabvars.h
cspmatrix.h
cspredef.h
Expand Down Expand Up @@ -46,7 +47,8 @@ set(HEADER_FILES_TO_INSTALL
scoplib.h
section.h
spconfig.h
spmatrix.h)
spmatrix.h
treeset.h)

# =============================================================================
# Lists of headers populated using check_include_files
Expand Down
9 changes: 9 additions & 0 deletions docs/guide/how_to_get_started.rst
Original file line number Diff line number Diff line change
Expand Up @@ -31,3 +31,12 @@ Using NMODL to add new mechanisms to NEURON
* NEURON comes with a bunch of mod files that can serve as starting points for "programming by example." Under MSWin the default mechanisms (hh, pas, expsyn etc.) are in `github.com/neuronsimulator/nrn/tree/master/src/nrnoc <https://github.com/neuronsimulator/nrn/tree/master/src/nrnoc>`_. A large collection of mod files is at `github.com/neuronsimulator/nrn/tree/master/share/examples/nrniv/nmodl <https://github.com/neuronsimulator/nrn/tree/master/share/examples/nrniv/nmodl>`_.
* You may also find useful examples in `ModelDB <https://modeldb.yale.edu>`_.

.. include:: ../rst_substitutions.txt

.. note::
Starting in |neuron_with_cpp_mechanisms|, NMODL is translated into C++ code
instead of C.
This change is not fully backwards compatible, and you may find that older
NMODL code needs to be updated to work with |neuron_with_cpp_mechanisms|.
This is principally an issue for MOD files that include ``VERBATIM`` blocks.
For more information, see :ref:`porting-mechanisms-to-cpp`.
1 change: 1 addition & 0 deletions docs/guide/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -13,4 +13,5 @@ Guides
import3d
optimization
randomness
porting_mechanisms_to_cpp
faq
Loading

0 comments on commit f242cc8

Please sign in to comment.