Adapting MOD files for C++ with NEURON >= 9.0

Attention

This guide only applies if you have MOD files with VERBATIM blocks that fail to compile with NEURON >= 9.0 but work with older versions of NEURON. If this is not your case, you can skip this guide.

In older versions of NEURON, MOD files containing NMODL code were translated into C code before being compiled and executed by NEURON. Starting with NEURON >= 9.0, NMODL code is translated into C++ code instead.

In most cases, this does not present any issues, as simple C code is typically valid C++, and no changes are required. However, C and C++ are not the same language, and there are cases in which MOD files containing VERBATIM blocks need to be modified in order to build with NEURON >= 9.0.

Before you start, you should decide if you need your MOD files to be compatible simultaneously with NEURON >= 9.0 and older versions, or if you can safely stop supporting older versions. Supporting both is generally possible, but it may be more cumbersome than committing to using C++ features. Considering NEURON has maintained strong backward compatibility and its internal numerical methods haven’t changed with migration to C++, it is likely to be sufficient to adapt MOD files to C++ only and use NEURON >= 9.0. If you do decide to preserve compatibility across versions, the preprocessor macros described in VERBATIM may prove useful.

Note

If you have a model that stopped compiling when you upgraded to or beyond NEURON >= 9.0, the first thing that you should check is whether the relevant MOD files have already been updated in ModelDB or in the GitHub repository of that model. You can check the repository name with the model accession number under https://github.com/ModelDBRepository. An updated version may already be available!

The following models were updated in ModelDB in preparation for NEURON >= 9.0 and may serve as useful references. You can see updated MOD files in the Changed Mod Files column. You can just apply the changes to your MOD files, or you can use the updated MOD files directly from the GitHub repository.

ModelDB Id

Model Name

GitHub Repository

Pull Request

Changed Mod Files

2487

Olfactory Mitral Cell (Davison et al 2000)

ModelDBRepository/2487

pull/1

cadecay.mod

2730

Olfactory Bulb Network (Davison et al 2003)

ModelDBRepository/2730

pull/1

cadecay.mod

2733

Olfactory Mitral Cell (Bhalla, Bower 1993)

ModelDBRepository/2733

pull/1

cadecay.mod

3658

Glutamate diffusion …lar glomerulus (Saftenku 2005)

ModelDBRepository/3658

pull/1

glubbfbm.mod glubes2.mod glubes23.mod glubes3.mod glubes4.mod glubes5.mod glubes6.mod glures23.mod

7399

Feedforward heteroas…with HH dynamics (Lytton 1998)

ModelDBRepository/7399

pull/1

matrix.mod snsarr.inc vecst.mod

7400

Hippocampus temporo-…gram shift model (Lytton 1999)

ModelDBRepository/7400

pull/1

matrix.mod vecst.mod

8284

Febrile seizure-indu…ations to Ih (Chen et al 2001)

ModelDBRepository/8284

pull/1

hyperde1.mod hyperde2.mod hyperde3.mod hyperso.mod ichan.mod

9889

Thalamic quiescence …e seizures (Lytton et al 1997)

ModelDBRepository/9889

pull/1

rand.mod

12631

Computer model of cl…n thalamic slice (Lytton 1997)

ModelDBRepository/12631

pull/2

rand.mod

26997

Gamma oscillations i… networks (Wang, Buzsaki 1996)

ModelDBRepository/26997

pull/1

vecst.mod

35358

CA3 pyramidal cell: …ub model (Pinsky, Rinzel 1994)

ModelDBRepository/35358

pull/2

matrix.mod vecst.mod

37819

Thalamocortical augm…response (Bazhenov et al 1998)

ModelDBRepository/37819

pull/1

matrix.mod pointer.inc ppsav.inc vecst.mod

51781

Dentate gyrus networ…model (Santhakumar et al 2005)

ModelDBRepository/51781

pull/1

hyperde3.mod ichan2.mod

52034

Cortical network mod…leptogenesis (Bush et al 1999)

ModelDBRepository/52034

pull/1

holt_rnd.mod precall.mod snsarr.inc

64229

Parallel network sim…h NEURON (Migliore et al 2006)

ModelDBRepository/64229

pull/1

parbulbNet/cadecay.mod

64296

Dynamical model of o…al cell (Rubin, Cleland 2006)

ModelDBRepository/64296

pull/1

cadecay.mod

87585

Sodium channel mutat…eizures + (Barela et al. 2006)

ModelDBRepository/87585

pull/1

ichanR859C1.mod ichanWT2005.mod

93321

Activity dependent c…euron model (Liu et al. 1998)

ModelDBRepository/93321

pull/1

cadecay.mod

97868

NEURON interfaces to…gorithm (Neymotin et al. 2008)

ModelDBRepository/97868

pull/2

MySQL.mod spud.mod vecst.mod

97874

Neural Query System …NEURON Simulator (Lytton 2006)

ModelDBRepository/97874

pull/2

NQS/vecst.mod modeldb/vecst.mod

97917

Cell splitting in ne…ng scaling (Hines et al. 2008)

ModelDBRepository/97917

pull/2

nrntraub/mod/rand.mod nrntraub/mod/ri.mod pardentategyrus/hyperde3.mod pardentategyrus/ichan2.mod

105507

Tonic-clonic transit…tion (Lytton and Omurtag 2007)

ModelDBRepository/105507

pull/2

intf_.mod misc.mod stats.mod vecst.mod

106891

JitCon: Just in time… networks (Lytton et al. 2008)

ModelDBRepository/106891

pull/3

jitcon.mod misc.h misc.mod stats.mod vecst.mod

113732

MEG of Somatosensory Neocortex (Jones et al. 2007)

ModelDBRepository/113732

pull/1

precall.mod presyn.inc

116094

Lateral dendrodendit…ctory Bulb (David et al. 2008)

ModelDBRepository/116094

pull/1

LongDendrite/cadecay.mod ShortDendrite/cadecay.mod

116830

Broadening of activi…tructures (Lytton et al. 2008)

ModelDBRepository/116830

pull/1

intf.mod misc.mod stats.mod vecst.mod

116838

The virtual slice setup (Lytton et al. 2008)

ModelDBRepository/116838

pull/1

intf_.mod misc.h misc.mod stats.mod vecst.mod

116862

Thalamic interneuron…rtment model (Zhu et al. 1999)

ModelDBRepository/116862

pull/1

clampex.mod misc.h vecst.mod

123815

Encoding and retriev…rcuit (Cutsuridis et al. 2009)

ModelDBRepository/123815

pull/1

burststim2.mod ichan2.mod regn_stim.mod

136095

Synaptic information…columns (Neymotin et al. 2010)

ModelDBRepository/136095

pull/1

clampex.mod field.mod infot.mod intf_.mod intfsw.mod misc.h misc.mod netrand.inc pregencv.mod stats.mod updown.mod vecst.mod

136310

Modeling local field…otentials (Bedard et al. 2004)

ModelDBRepository/136310

pull/1

ImpedanceFM.mod

137845

Spike exchange metho…rcomputer (Hines et al., 2011)

ModelDBRepository/137845

pull/1

invlfire.mod

138379

Emergence of physiol…lations (Neymotin et al. 2011)

ModelDBRepository/138379

pull/1

intf6_.mod misc.h misc.mod stats.mod vecst.mod

139421

Ketamine disrupts th…pocampus (Neymotin et al 2011)

ModelDBRepository/139421

pull/1

misc.h misc.mod stats.mod vecst.mod wrap.mod

140881

Computational Surgery (Lytton et al. 2011)

ModelDBRepository/140881

pull/1

intf6_.mod misc.h misc.mod stats.mod vecst.mod

141505

Prosthetic electrost…ortical simulation (Kerr 2012)

ModelDBRepository/141505

pull/1

infot.mod intf6_.mod intfsw.mod misc.h misc.mod staley.mod stats.mod vecst.mod

144538

Reinforcement learni…ement (Chadderdon et al. 2012)

ModelDBRepository/144538

pull/1

infot.mod intf6_.mod intfsw.mod misc.h misc.mod stats.mod updown.mod vecst.mod

144549

Hopfield and Brody m…d, Brody 2000) (NEURON+python)

ModelDBRepository/144549

pull/1

misc.h misc.mod stats.mod vecst.mod

144586

Boolean network-base…sis network (Mai and Liu 2009)

ModelDBRepository/144586

pull/1

bnet.mod misc.h misc.mod stats.mod vecst.mod

146949

Motor cortex microci…pping (Chadderdon et al. 2014)

ModelDBRepository/146949

pull/1

infot.mod intf6.mod intfsw.mod matrix.mod misc.h misc.mod staley.mod stats.mod vecst.mod

149000

Using Strahler`s ana…c models (Marasco et al, 2013)

ModelDBRepository/149000

pull/1

pj.mod

149739

A two-layer biophysi…dulation (Li and Cleland 2013)

ModelDBRepository/149739

pull/1

cadecay.mod cadecay2.mod

150240

A Model Circuit of T…vergence (Behuret et al. 2013)

ModelDBRepository/150240

pull/1

RandomGenerator.mod

150245

Sensorimotor cortex …eaching (Neymotin et al. 2013)

ModelDBRepository/150245

pull/1

infot.mod intf6_.mod misc.h misc.mod stats.mod vecst.mod

150551

Calcium waves and mG…rons (Ashhad & Narayanan 2013)

ModelDBRepository/150551

pull/1

Calamp.mod

150556

Single compartment D…MPA (Biddell and Johnson 2013)

ModelDBRepository/150556

pull/1

KBNetStim.mod

150691

Model of arrhythmias…twork (Casaleggio et al. 2014)

ModelDBRepository/150691

pull/1

Readme halfgapm1.mod halfgapspk.mod

151126

Effects of increasin… network (Bianchi et al. 2014)

ModelDBRepository/151126

pull/1

burststim2.mod ichan2.mod regn_stim.mod

151282

Ih tunes oscillation…3 model (Neymotin et al. 2013)

ModelDBRepository/151282

pull/1

misc.h misc.mod stats.mod vecst.mod

153280

Parvalbumin-positive…amidal cells (Lee et al. 2014)

ModelDBRepository/153280

pull/1

ch_Kdrfast.mod mynetstim.mod repeatconn.mod

154732

Spine head calcium i…ell model (Graham et al. 2014)

ModelDBRepository/154732

pull/1

burststim2.mod

155568

Dentate gyrus network model (Tejada et al 2014)

ModelDBRepository/155568

pull/1

hyperde3.mod ichan2.mod

155601

Basket cell extrasyn…tions (Proddutur et al., 2013)

ModelDBRepository/155601

pull/1

hyperde3.mod ichan2.mod

155602

Status epilepticus a…c inhibition (Yu J et al 2013)

ModelDBRepository/155602

pull/1

hyperde3.mod ichan2.mod

156780

Microcircuits of L5 …midal cells (Hay & Segev 2015)

ModelDBRepository/156780

pull/1

ProbAMPANMDA2.mod ProbUDFsyn2.mod

157157

CA1 pyramidal neuron…cles (Saudargiene et al. 2015)

ModelDBRepository/157157

pull/1

burststim2.mod regn_stim.mod

168874

Neuronal dendrite ca…e model (Neymotin et al, 2015)

ModelDBRepository/168874

pull/4

misc.h misc.mod stats.mod vecst.mod

181967

Long time windows fr…op (Cutsuridis & Poirazi 2015)

ModelDBRepository/181967

pull/1

burststim.mod hyperde3.mod ichan2.mod regn_stim.mod

182129

Computational modeli…signaling (Lupascu et al 2020)

ModelDBRepository/182129

pull/1

ProbGABAAB_EMS_GEPH_g.mod

183300

Mitral cell activity…ory bulb NN (Short et al 2016)

ModelDBRepository/183300

pull/1

cadecay.mod cadecay2.mod thetastim.mod vecstim.mod

185355

Dentate gyrus networ…g in epilepsy (Yim et al 2015)

ModelDBRepository/185355

pull/2

HCN.mod ichan2.mod netstim125.mod netstimbox.mod

185858

Ca+/HCN channel-depe…eocortex (Neymotin et al 2016)

ModelDBRepository/185858

pull/1

misc.h misc.mod vecst.mod

186768

CA3 Network Model of…Activity (Sanjay et. al, 2015)

ModelDBRepository/186768

pull/1

misc.h misc.mod stats.mod vecst.mod wrap.mod

187604

Hippocampal CA1 NN w…ork clamp (Bezaire et al 2016)

ModelDBRepository/187604

pull/2

fastconn.mod mynetstim.mod repeatconn.mod sgate.mod

189154

Multitarget pharmaco…ia in M1 (Neymotin et al 2016)

ModelDBRepository/189154

pull/1

misc.h misc.mod stats.mod vecst.mod

194897

Motor system model w…l arm (Dura-Bernal et al 2017)

ModelDBRepository/194897

pull/2

izhi2007.mod nsloc.mod vecevent.mod

195615

Computer models of c…ynamics (Neymotin et al. 2017)

ModelDBRepository/195615

pull/1

misc.h misc.mod vecst.mod

223031

Interneuron Specific…l (Guet-McCreight et al, 2016)

ModelDBRepository/223031

pull/1

S1/ingauss.mod S2/ingauss.mod SD/ingauss.mod SDprox1/ingauss.mod SDprox2/ingauss.mod

225080

CA1 pyr cell: Inhibi…ssion (Grienberger et al 2017)

ModelDBRepository/225080

pull/1

pr.mod vecevent.mod

231427

Shaping NMDA spikes …on on L5PC (Doron et al. 2017)

ModelDBRepository/231427

pull/2

ProbAMPA.mod ProbUDFsyn2_lark.mod

232097

2D model of olfactor…llations (Li and Cleland 2017)

ModelDBRepository/232097

pull/1

cadecay.mod cadecay2.mod

239177

Phase response theor…(Tikidji-Hamburyan et al 2019)

ModelDBRepository/239177

pull/1

PIR-Inetwork/innp.mod PIR-Inetwork/vecevent.mod

241165

Biophysically realis…imulation (Aberra et al. 2018)

ModelDBRepository/241165

pull/1

mechanisms/ProbAMPANMDA_EMS.mod mechanisms/ProbGABAAB_EMS.mod

241240

Role of afferent-hai…regularity (Holmes et al 2017)

ModelDBRepository/241240

pull/1

afhcsyn_i0.mod hc1.mod random.mod ribbon1.mod

244262

Deconstruction of co…ic DBS (Kumaravelu et al 2018)

ModelDBRepository/244262

pull/1

rand.mod ri.mod

244848

Active dendrites sha…urons (Basak & Narayanan 2018)

ModelDBRepository/244848

pull/2

apamp.mod

247968

Gamma genesis in the…ral amygdala (Feng et al 2019)

ModelDBRepository/247968

pull/1

Gfluct_new_exc.mod Gfluct_new_inh.mod vecevent.mod

249463

Layer V pyramidal ce…cs (Mäki-Marttunen et al 2019)

ModelDBRepository/249463

pull/1

almog/ProbAMPANMDA2.mod almog/ProbUDFsyn2.mod hay/ProbAMPANMDA2.mod hay/ProbUDFsyn2.mod

256388

The APP in C-termina…n firing (Pousinha et al 2019)

ModelDBRepository/256388

pull/1

burststim2.mod ichan2.mod regn_stim.mod

259366

Cycle skipping in IN…dji-Hamburyan & Canavier 2020)

ModelDBRepository/259366

pull/1

innp.mod

Legacy patterns that are invalid C++

This section aims to list some patterns that the NEURON developers have found in pre-NEURON >= 9.0 models that need to be modified to be valid C++.

Implicit pointer type conversions

C++ has stricter rules governing pointer type conversions than C. For example

double* x = (void*)0;   // valid C, invalid C++
double* x = nullptr;    // valid C++, invalid C
double* x = (double*)0; // valid C and C++ (C-style casts discouraged in C++)

Similarly, in C one can pass a void* argument to a function that expects a double*. In C++ this is forbidden.

The same issue may manifest itself in code such as

double* x = malloc(7 * sizeof(double));          // valid C, invalid C++
double* x = new double[7];                       // valid C++, invalid C
double* x = (double*)malloc(7 * sizeof(double)); // valid C and C++ (C-style casts discouraged in C++)

If you choose to move from using C malloc and free to using C++ new and delete then remember that you cannot mix and match new with free and so on.

Note

Explicit memory management with new and delete is discouraged in C++ (R.11: Avoid calling new and delete explicitly). If you do not need to support older versions of NEURON, you may be able to use standard library containers such as std::vector<T>.

Local non-prototype function declarations

In C, the function declaration

void some_function();

is a non-prototype function declaration: it declares that some_function exists, but it does not specify the number of arguments that it takes, or their types. In C++, the same code declares that some_function takes zero arguments (the C equivalent of this is void some_function(void)).

If such a declaration occurs in a top-level VERBATIM block then it is likely to be harmless: it will add a zero-parameter overload of the function, which will never be called. It will, however, cause a problem if the declaration is included inside an NMODL construct

PROCEDURE procedure() {
VERBATIM
  void some_method_taking_an_int(); // problematic in C++
  some_method_taking_an_int(42);
ENDVERBATIM
}

because in this case the local declaration hides the real declaration, which is something like

void some_method_taking_an_int(int);

in a NEURON header that is included when the translated MOD file is compiled. In this case, the problematic local declaration can simply be removed.

Function declarations with incorrect types

In older MOD files and versions of NEURON, API methods were often accessed by declaring them in the MOD file and not by including a correct declaration from NEURON itself. In NEURON 8.2+, more declarations are implicitly included when MOD files are compiled. This can lead to problems if the declaration in the MOD file did not specify the correct argument and return types.

Rand* nrn_random_arg(int); // correct declaration from NEURON header, only in new NEURON
/* ... */
void* nrn_random_arg(int); // incorrect declaration in MOD file, clashes with previous line

The fix here is simply to remove the incorrect declaration from the MOD file.

If the argument types are incorrect, the situation is slightly more nuanced. This is because C++ supports overloading functions by argument type, but not by return type.

void sink(Thing*); // correct declaration from NEURON header, only in new NEURON
/* ... */
void sink(void*); // incorrect declaration in MOD file, adds an overload, not a compilation error
/* ... */
void* void_ptr;
sink(void_ptr);  // probably used to work, now causes a linker error
Thing* thing_ptr;
sink(thing_ptr); // works with both old and new NEURON

Here the incorrect declaration sink(void*) declares a second overload of the sink function, which is not defined anywhere. With NEURON >= 9.0 the sink(void_ptr) line will select the void* second overload, based on the argument type, and this will fail during linking because this overload is not defined (only sink(Thing*) has a definition).

In contrast, sink(thing_ptr) will select the correct overload in NEURON >= 9.0, and it also works in older NEURON versions because Thing* can be implicitly converted to void*.

The fix here is, again, to remove the incorrect declaration from the MOD file.

See also the section below, Deprecated overloads taking void*, for cases where NEURON does provide a (deprecated) definition of the void* overload.

K&R function definitions

C supports (until C23) a legacy (“K&R”) syntax for function declarations. This is not valid C++.

There is no advantage to the legacy syntax. If you have legacy definitions such as

void foo(a, b) int a, b; { /* ... */ }

then simply replace them with

void foo(int a, int b) { /* ... */ }

which is valid in both C and C++.

Legacy patterns that are considered deprecated

As noted above (Local non-prototype function declarations), declarations such as

VERBATIM
extern void vector_resize();
ENDVERBATIM

at the global scope in MOD files declare C++ function overloads that take no parameters. If such declarations appear at the global scope then they do not hide the correct declarations, so this can be harmless, but it is not necessary. In NEURON >= 9.0 the full declarations of the NEURON API methods that can be used in MOD files are implicitly included via the mech_api.h header, so this explicit declaration of a zero-parameter overload is not needed and can safely be removed.

Deprecated overloads taking void*

As noted above (Function declarations with incorrect types), NEURON >= 9.0 provides extra overloads for some API methods that aim to smooth the transition from C to C++. These overloads are provided for widely used methods, and where overloading on return type would not be required.

An example is the vector_capacity function, which in NEURON >= 9.0 has two overloads

int vector_capacity(IvocVect*);
[[deprecated("non-void* overloads are preferred")]] int vector_capacity(void*);

The second one simply casts its argument to IvocVect* and calls the first one. The [[deprecated]] attribute means that MOD files that use the second overload emit compilation warnings when they are compiled using nrnivmodl.

If your MOD files produce these deprecation warnings, make sure that the relevant method (vector_capacity in this example) is being called with an argument of the correct type (IvocVect*), and not a type that is implicitly converted to void*.

Legacy random number generators and API

Various changes have also been done in the API of NEURON functions related to random number generators.

First, in NEURON >= 9.0 parameters passed to the functions need to be of the correct type as it was already mentioned in Function declarations with incorrect types. The most usual consequence of that is that NEURON random API functions that were taking as an argument a void* now need to called with a Rand*. An example of the changes needed to fix this issue is given in 182129.

Another related change is with scop_rand() function that is usually used for defining a URAND FUNCTION in mod files to return a number based on a uniform distribution from 0 to 1. This function now takes no argument anymore. An example of this change can also be found in 182129.

Finally, the preferred random number generator is Random123. You can find more information about that in Random.Random123() and Randomness in NEURON models. An example of the usage of Random123 can be seen in netstim.mod and its corresponding test.` Another important aspect of Random123 is that it’s supported in CoreNEURON as well. For more information about this see Random Number Generators: Random123 vs MCellRan4.