1 #include <../../nrnconf.h>
48 if (blocktype == BREAKPOINT) {
65 diag(
"The SOLVE statement must be before the DERIVATIVE block for ",
SYM(lq)->
name);
78 if (strcmp(
SYM(qMethod)->
name,
"derivimplicit") == 0) {
81 if (strcmp(
SYM(qMethod)->
name,
"cnexp") == 0) {
98 " std_cerr_stream << \"%s\\n\";\n"
99 " std_cerr_stream << _ml << ' ' << _iml << '\\n';\n"
100 " abort_run(error);\n"
111 int numeqn, listnum, btype, steadystate;
129 if (method && strcmp(method->
name,
"after_cvode") == 0) {
134 if (method && strcmp(method->
name,
"cvode_t") == 0) {
139 if (method && strcmp(method->
name,
"cvode_v") == 0) {
163 if (method ==
SYM0) {
164 method =
lookup(
"derivimplicit");
166 if (btype == BREAKPOINT && !steadystate) {
168 if (strcmp(method->
name,
"cnexp") != 0 &&
169 strcmp(method->
name,
"derivimplicit") != 0 &&
170 strcmp(method->
name,
"euler") != 0) {
172 "Notice: %s is not thread safe. Complain to Hines\n",
180 if (btype == BREAKPOINT)
182 solv_diffeq(qsol, fun, method, numeqn, listnum, steadystate, btype);
185 if (method ==
SYM0) {
186 method =
lookup(
"_advance");
188 if (btype == BREAKPOINT && (method->
subtype &
DERF)) {
191 "Notice: KINETIC is thread safe only with METHOD sparse. Complain to Hines\n");
197 if (btype == BREAKPOINT) {
199 if (strcmp(method->
name,
"sparse") == 0) {
204 solv_diffeq(qsol, fun, method, numeqn, listnum, steadystate, btype);
207 fprintf(stderr,
"Notice: NONLINEAR is not thread safe.\n");
209 if (method ==
SYM0) {
210 method =
lookup(
"newton");
215 fprintf(stderr,
"Notice: LINEAR is not thread safe.\n");
217 if (method ==
SYM0) {
220 solv_lineq(qsol, fun, method, numeqn, listnum);
223 fprintf(stderr,
"Notice: DISCRETE is not thread safe.\n");
225 if (btype == BREAKPOINT)
232 if (btype == BREAKPOINT) {
234 if (cvodemethod_ == 1) {
237 if (cvodemethod_ == 2) {
243 if (cvodemethod_ == 3) {
257 diag(
"Illegal or unimplemented SOLVE type: ", fun->
name);
260 if (btype == BREAKPOINT) {
266 if (errstmt->
next == errstmt->
prev) {
270 fprintf(stderr,
"Notice: SOLVE with ERROR is not thread safe.\n");
316 static int called = 0, firstderf = 1;
331 Sprintf(sval,
"%g", (d[1] - d[0]) / d[2]);
332 }
else if (
type == DISCRETE) {
349 "Warning: More than one integrating SOLVE statement in an \
350 BREAKPOINT block.\nThe simulation will be incorrect if more than one is used \
377 if (fun ==
SYM(qchk)) {
378 method =
SYM(
q->next);
379 switch (
q->itemtype) {
381 if (!method || strcmp(
"derivimplicit", method->
name) != 0) {
383 "STEADYSTATE requires all SOLVE's of this DERIVATIVE block to use the\n\
384 `derivimplicit' method:",
389 if (
SYM(qchk->
next) != method || (method && strcmp(
"sparse", method->
name) != 0)) {
391 "STEADYSTATE requires all SOLVE's of this KINETIC block to use the\n\
392 same method (`advance' or `sparse'). :",
397 diag(
"STEADYSTATE only valid for SOLVEing a KINETIC or DERIVATIVE block:",
void solv_diffeq(Item *qsol, Symbol *fun, Symbol *method, int numeqn, int listnum, int steadystate, int btype)
void add_deriv_imp_list(char *name)
Symbol * ifnew_parminstall(const char *name, const char *num, const char *units, const char *limits)
static int follow(int expect, int ifyes, int ifno)
void cvode_kinetic(Item *qsol, Symbol *fun, int numeqn, int listnum)
#define ITERATE(itm, lst)
Symbol * lookup(const char *)
char * stralloc(const char *buf, char *rel)
void movelist(Item *q1, Item *q2, List *s)
void move(Item *q1, Item *q2, Item *q3)
Item * linsertstr(List *list, const char *str)
void replacstr(Item *q, const char *s)
Item * insertstr(Item *item, const char *str)
Item * lappendsym(List *list, Symbol *sym)
void freelist(List *list)
List * newlist()
The following routines support the concept of a list.
int Sprintf(char(&buf)[N], const char *fmt, Args &&... args)
Redirect sprintf to snprintf if the buffer size can be deduced.
void cvode_interface(Symbol *fun, int num, int neq)
void solv_lineq(Item *qsol, Symbol *fun, Symbol *method, int numeqn, int listnum)
void solv_nonlin(Item *qsol, Symbol *fun, Symbol *method, int numeqn, int listnum)
void vectorize_substitute(Item *q, const char *str)
NMODL parser global flags / functions.
Symbol * cvode_nrn_current_solve_
Symbol * cvode_nrn_cur_solve_
void check_ss_consist(Item *)
void whileloop(Item *, long, int)
void solvequeue(Item *qName, Item *qMethod, int blocktype)
static double remove(void *v)
int Fprintf(FILE *stream, const char *fmt, Args... args)