NEURON
grids.h
Go to the documentation of this file.
1 /******************************************************************
2 Author: Austin Lachance
3 Date: 10/28/16
4 Description: Header File for grids.cpp. Allows access to Grid_node
5 and Flux_pair structs and their respective functions
6 ******************************************************************/
7 #include <stdio.h>
8 #include <assert.h>
9 #include <nrnmpi.h>
10 
11 #include "nrn_pyhocobject.h"
12 #include "nrnwrap_Python.h"
13 
14 #define IDX(x, y, z) ((z) + (y) *g->size_z + (x) *g->size_z * g->size_y)
15 #define INDEX(x, y, z) ((z) + (y) *grid->size_z + (x) *grid->size_z * grid->size_y)
16 #define ALPHA(x, y, z) (g->get_alpha(g->alpha, IDX(x, y, z)))
17 #define VOLFRAC(idx) (g->get_alpha(g->alpha, idx))
18 #define TORT(idx) (g->get_permeability(g->permeability, idx))
19 #define PERM(x, y, z) (g->get_permeability(g->permeability, IDX(x, y, z)))
20 #define SQ(x) ((x) * (x))
21 #define CU(x) ((x) * (x) * (x))
22 #define TRUE 1
23 #define FALSE 0
24 #define TORTUOSITY 2
25 #define VOLUME_FRACTION 3
26 #define ICS_ALPHA 4
27 
28 #define NEUMANN 0
29 #define DIRICHLET 1
30 
31 #define MAX(a, b) ((a) > (b) ? (a) : (b))
32 #define MIN(a, b) ((a) < (b) ? (a) : (b))
33 
34 struct Hybrid_data {
36  long* indices1d;
38  long* indices3d;
39  double* rates;
40  double* volumes1d;
41  double* volumes3d;
42 };
43 
45  neuron::container::data_handle<double> destination; /* memory loc to transfer concentration to
46  */
47  long source; /* index in grid for source */
48 };
49 
51  long destination; /* index in grid */
52  neuron::container::data_handle<double> source; /* memory loc of e.g. ica */
53  double scale_factor;
54 };
55 
56 using ReactionRate =
57  void(double**, double**, double**, double*, double*, double*, double*, double**, double);
58 using ECSReactionRate = void(double*, double*, double*, double*);
59 struct Reaction {
62  unsigned int num_species_involved;
63  unsigned int num_params_involved;
64  double** species_states;
65  unsigned char* subregion;
66  unsigned int region_size;
68  double** mc3d_mults;
69 };
70 
71 struct AdiLineData {
72  double* copyFrom;
73  long copyTo;
74 };
75 
77  /*TODO: Support for mixed boundaries and by edge (maybe even by voxel)*/
78  unsigned char type;
79  double value;
80 };
81 
82 class Grid_node {
83  public:
85 
86  double* states; // Array of doubles representing Grid space
87  double* states_x;
88  double* states_y;
89  double* states_z; // TODO: This is only used by ICS, is it necessary?
90  double* states_cur;
91  int size_x; // Size of X dimension
92  int size_y; // Size of Y dimension
93  int size_z; // Size of Z dimension
94  double dc_x; // X diffusion constant
95  double dc_y; // Y diffusion constant
96  double dc_z; // Z diffusion constant
97  double dx; // ∆X
98  double dy; // ∆Y
99  double dz; // ∆Z
101  bool hybrid;
107 
108  /*used for MPI implementation*/
115  double* all_currents;
116 
117  /*Extension to handle a variable diffusion characteristics of a grid*/
118  unsigned char VARIABLE_ECS_VOLUME; /*FLAG which variable volume fraction
119  methods should be used*/
120  /*diffusion characteristics are arrays of a single value or
121  * the number of voxels (size_x*size_y*size_z)*/
122  double* permeability; /* 1/tortuosities^2 squared
123  D_eff = D_free*permeability */
124  double* alpha; /* volume fractions */
125  /*Function that will be assigned when the grid is created to either return
126  * the single value or the value at a given index*/
127  double (*get_alpha)(double*, int);
128  double (*get_permeability)(double*, int);
129  double atolscale;
130 
133  std::vector<neuron::container::data_handle<double>> ics_concentration_seg_handles;
136 
137  int insert(int grid_list_index);
142 
143 
144  virtual ~Grid_node() {}
145  virtual void set_diffusion(double*, int) = 0;
146  virtual void set_num_threads(const int n) = 0;
147  virtual void do_grid_currents(double*, double, int) = 0;
148  virtual void apply_node_flux3D(double dt, double* states) = 0;
149  virtual void volume_setup() = 0;
150  virtual int dg_adi() = 0;
151  virtual void variable_step_diffusion(const double* states, double* ydot) = 0;
152  virtual void variable_step_ode_solve(double* RHS, double dt) = 0;
153  virtual void scatter_grid_concentrations() = 0;
154  virtual void hybrid_connections() = 0;
155  virtual void variable_step_hybrid_connections(const double* cvode_states_3d,
156  double* const ydot_3d,
157  const double* cvode_states_1d,
158  double* const ydot_1d) = 0;
159 };
160 
161 class ECS_Grid_node: public Grid_node {
162  public:
163  // Data for DG-ADI
164  ECS_Grid_node();
166  int,
167  int,
168  int,
169  double,
170  double,
171  double,
172  double,
173  double,
174  double,
175  PyHocObject*,
176  PyHocObject*,
177  int,
178  double,
179  double);
180  ~ECS_Grid_node();
185 
186  // Data for multicompartment reactions
204 
205  void set_num_threads(const int n);
206  void do_grid_currents(double*, double, int);
207  void apply_node_flux3D(double dt, double* states);
208  void volume_setup();
209  int dg_adi();
210  void variable_step_diffusion(const double* states, double* ydot);
211  void variable_step_ode_solve(double* RHS, double dt);
212  void variable_step_hybrid_connections(const double* cvode_states_3d,
213  double* const ydot_3d,
214  const double* cvode_states_1d,
215  double* const ydot_1d);
217  void hybrid_connections();
218  void set_diffusion(double*, int);
221  void do_multicompartment_reactions(double*);
224  int add_multicompartment_reaction(int, int*, int);
225  double* set_rxd_currents(int, int*, PyHocObject**);
226 };
227 
230  const double,
231  const int,
232  const int,
233  double const* const,
234  double* const,
235  double* const);
236  double* states_in;
237  double* states_out;
239 };
240 
242  int start, stop;
243  double* state;
245  int sizej;
247  double* scratchpad;
248 };
249 
250 class ICS_Grid_node: public Grid_node {
251  public:
252  ICS_Grid_node();
253  ~ICS_Grid_node();
254  // fractional volumes
255  double* _ics_alphas;
256  // stores the positive x,y, and z neighbors for each node. [node0_x, node0_y, node0_z, node1_x
257  // ...]
258  long* _neighbors;
259 
260  /*Line definitions from Python. In pattern of [line_start_node, line_length, ...]
261  Array is sorted from longest to shortest line */
265 
266  // Lengths of _sorted_lines arrays. Used to find thread start and stop indices
270 
271  // maximum line length for scratchpad memory allocation
273 
274  // total number of nodes for this grid
276 
277  // indices for thread start and stop positions
279 
280  // Data for DG-ADI
285 
287  long,
288  long*,
289  long*,
290  long,
291  long*,
292  long,
293  long*,
294  long,
295  double*,
296  double*,
297  double,
298  bool,
299  double,
300  double*);
301  void divide_x_work(const int nthreads);
302  void divide_y_work(const int nthreads);
303  void divide_z_work(const int nthreads);
304  void set_num_threads(const int n);
305  void do_grid_currents(double*, double, int);
306  void apply_node_flux3D(double dt, double* states);
307  void volume_setup();
308  int dg_adi();
309  void variable_step_diffusion(const double* states, double* ydot);
310  void variable_step_ode_solve(double* RHS, double dt);
311  void hybrid_connections();
312  void variable_step_hybrid_connections(const double* cvode_states_3d,
313  double* const ydot_3d,
314  const double* cvode_states_1d,
315  double* const ydot_1d);
318  void set_diffusion(double*, int);
322  int add_multicompartment_reaction(int, int*, int);
323  double* set_rxd_currents(int, int*, PyHocObject**);
324 };
325 
328  int,
329  int,
330  int,
331  double,
332  double*,
333  double*,
334  double*,
335  double*,
336  double*,
337  double*);
338  double* states_in;
339  double* states_out;
340  double* deltas;
345  double dc;
346  double* dcgrid;
347  double d;
348 };
349 
350 
352  // Start and stop node indices for lines
354  // Where to start in the ordered_nodes array
356  double* state;
359  double* scratchpad;
360  double* RHS;
361  double* l_diag;
362  double* diag;
363  double* u_diag;
364  // double* deltas;
365 };
366 
367 /***** GLOBALS *******************************************************************/
368 extern double* dt_ptr; // Universal ∆t
369 extern double* t_ptr; // Universal t
370 
371 // static int N = 100; // Number of grid_lists (size of Parallel_grids)
372 extern Grid_node* Parallel_grids[100]; // Array of Grid_node * lists
373 /*********************************************************************************/
374 
375 
376 // Set the global ∆t
377 void make_dt_ptr(PyHocObject* my_dt_ptr);
378 
379 
380 // Create a single Grid_node
381 /* Parameters: Python object that includes array of double pointers,
382  size of x, y, and z dimensions
383  x, y, and z diffusion constants
384  delta x, delta y, and delta z*/
385 
386 // Free a single Grid_node "grid"
387 // void free_Grid(Grid_node *grid);
388 
389 // Insert a Grid_node "new_Grid" into the list located at grid_list_index in Parallel_grids
390 extern "C" int ECS_insert(int grid_list_index,
391  PyHocObject* my_states,
392  int my_num_states_x,
393  int my_num_states_y,
394  int my_num_states_z,
395  double my_dc_x,
396  double my_dc_y,
397  double my_dc_z,
398  double my_dx,
399  double my_dy,
400  double my_dz,
401  PyHocObject* my_alpha,
402  PyHocObject* my_permeability,
403  int,
404  double,
405  double);
406 
408  long num_nodes,
409  long* neighbors,
410  long* x_line_defs,
411  long x_lines_length,
412  long* y_line_defs,
413  long y_lines_length,
414  long* z_line_defs,
415  long z_lines_length,
416  double* dcs,
417  double dx,
418  bool is_diffusable,
419  double atolscale,
420  double* ics_alphas);
421 
422 // Insert an ICS_Grid_node "new_Grid" into the list located at grid_list_index in Parallel_grids
423 extern "C" int ICS_insert(int grid_list_index,
424  PyHocObject* my_states,
425  long num_nodes,
426  long* neighbors,
427  long* x_line_defs,
428  long x_lines_length,
429  long* y_line_defs,
430  long y_lines_length,
431  long* z_line_defs,
432  long z_lines_length,
433  double* dcs,
434  double dx,
435  bool is_diffusable,
436  double atolscale,
437  double* ics_alphas);
438 
439 extern "C" int ICS_insert_inhom(int grid_list_index,
440  PyHocObject* my_states,
441  long num_nodes,
442  long* neighbors,
443  long* x_line_defs,
444  long x_lines_length,
445  long* y_line_defs,
446  long y_lines_length,
447  long* z_line_defs,
448  long z_lines_length,
449  double* dcs,
450  double dx,
451  bool is_diffusable,
452  double atolscale,
453  double* ics_alphas);
454 
455 
456 // Set the diffusion coefficients for a given grid_id
457 extern "C" int set_diffusion(int, int, double*, int);
458 
459 // Delete a specific Grid_node "find" from the list "head"
460 int remove(Grid_node** head, Grid_node* find);
461 
462 // Destroy the list located at list_index and free all memory
463 void empty_list(int list_index);
464 
465 void apply_node_flux(int, long*, double*, PyObject**, double, double*);
double * induced_currents
Definition: grids.h:201
unsigned char multicompartment_inititalized
Definition: grids.h:195
double * induced_currents_scale
Definition: grids.h:203
ECS_Grid_node()
Definition: grids.cpp:50
void apply_node_flux3D(double dt, double *states)
Definition: grids.cpp:962
void set_tortuosity(PyHocObject *)
Definition: grids.cpp:482
int induced_current_count
Definition: grids.h:197
int react_offset_count
Definition: grids.h:189
int dg_adi()
Definition: grids.cpp:1010
int * all_reaction_indices
Definition: grids.h:191
void volume_setup()
Definition: grids.cpp:997
int induced_idx
Definition: grids.h:187
int * proc_induced_current_count
Definition: grids.h:198
void do_grid_currents(double *, double, int)
Definition: grids.cpp:877
void variable_step_diffusion(const double *states, double *ydot)
Definition: grids.cpp:1037
struct ECSAdiDirection * ecs_adi_dir_z
Definition: grids.h:184
double * set_rxd_currents(int, int *, PyHocObject **)
Definition: grids.cpp:935
void initialize_multicompartment_reaction()
Definition: grids.cpp:1111
void set_volume_fraction(PyHocObject *)
Definition: grids.cpp:534
struct ECSAdiDirection * ecs_adi_dir_y
Definition: grids.h:183
int add_multicompartment_reaction(int, int *, int)
Definition: grids.cpp:1068
struct ECSAdiGridData * ecs_tasks
Definition: grids.h:181
void clear_multicompartment_reaction()
Definition: grids.cpp:1094
void variable_step_ode_solve(double *RHS, double dt)
Definition: grids.cpp:1244
int total_reaction_states
Definition: grids.h:194
int * react_offsets
Definition: grids.h:188
void variable_step_hybrid_connections(const double *cvode_states_3d, double *const ydot_3d, const double *cvode_states_1d, double *const ydot_1d)
Definition: grids.cpp:1063
int * proc_num_reaction_states
Definition: grids.h:193
int * proc_induced_current_offset
Definition: grids.h:199
int * proc_num_reactions
Definition: grids.h:192
struct ECSAdiDirection * ecs_adi_dir_x
Definition: grids.h:182
void set_num_threads(const int n)
Definition: grids.cpp:834
void hybrid_connections()
Definition: grids.cpp:1061
void scatter_grid_concentrations()
Definition: grids.cpp:1050
double * all_reaction_states
Definition: grids.h:200
double * local_induced_currents
Definition: grids.h:202
void set_diffusion(double *, int)
Definition: grids.cpp:578
int * reaction_indices
Definition: grids.h:190
void do_multicompartment_reactions(double *)
Definition: grids.cpp:1221
int * induced_currents_index
Definition: grids.h:196
double(* get_alpha)(double *, int)
Definition: grids.h:127
int node_flux_count
Definition: grids.h:138
virtual void apply_node_flux3D(double dt, double *states)=0
double * permeability
Definition: grids.h:122
bool hybrid
Definition: grids.h:101
int * proc_num_fluxes
Definition: grids.h:113
int size_y
Definition: grids.h:92
virtual void variable_step_hybrid_connections(const double *cvode_states_3d, double *const ydot_3d, const double *cvode_states_1d, double *const ydot_1d)=0
int * proc_offsets
Definition: grids.h:110
double * states_x
Definition: grids.h:87
virtual void hybrid_connections()=0
int64_t * ics_surface_nodes_per_seg
Definition: grids.h:131
virtual void variable_step_diffusion(const double *states, double *ydot)=0
Concentration_Pair * concentration_list
Definition: grids.h:104
long * node_flux_idx
Definition: grids.h:139
int size_x
Definition: grids.h:91
double * states_cur
Definition: grids.h:90
bool diffusable
Definition: grids.h:100
double * states
Definition: grids.h:86
double atolscale
Definition: grids.h:129
int * proc_flux_offsets
Definition: grids.h:112
BoundaryConditions * bc
Definition: grids.h:102
double * node_flux_scale
Definition: grids.h:140
double dy
Definition: grids.h:98
double * states_z
Definition: grids.h:89
virtual void volume_setup()=0
double * states_y
Definition: grids.h:88
virtual void set_num_threads(const int n)=0
Grid_node * next
Definition: grids.h:84
double(* get_permeability)(double *, int)
Definition: grids.h:128
virtual void do_grid_currents(double *, double, int)=0
virtual void variable_step_ode_solve(double *RHS, double dt)=0
Hybrid_data * hybrid_data
Definition: grids.h:103
virtual ~Grid_node()
Definition: grids.h:144
int64_t * ics_surface_nodes_per_seg_start_indices
Definition: grids.h:132
PyObject ** node_flux_src
Definition: grids.h:141
int num_all_currents
Definition: grids.h:109
unsigned char VARIABLE_ECS_VOLUME
Definition: grids.h:118
int insert(int grid_list_index)
Definition: grids.cpp:810
double ** ics_current_seg_ptrs
Definition: grids.h:134
double dc_z
Definition: grids.h:96
double * all_currents
Definition: grids.h:115
double * ics_scale_factors
Definition: grids.h:135
double dc_y
Definition: grids.h:95
Current_Triple * current_list
Definition: grids.h:105
int size_z
Definition: grids.h:93
int * proc_num_currents
Definition: grids.h:111
long * current_dest
Definition: grids.h:114
double dc_x
Definition: grids.h:94
virtual int dg_adi()=0
double dz
Definition: grids.h:99
std::vector< neuron::container::data_handle< double > > ics_concentration_seg_handles
Definition: grids.h:133
virtual void set_diffusion(double *, int)=0
double * alpha
Definition: grids.h:124
ssize_t num_currents
Definition: grids.h:106
double dx
Definition: grids.h:97
ssize_t num_concentrations
Definition: grids.h:106
virtual void scatter_grid_concentrations()=0
struct ICSAdiDirection * ics_adi_dir_x
Definition: grids.h:282
long _x_lines_length
Definition: grids.h:267
void run_threaded_ics_dg_adi(struct ICSAdiDirection *)
void scatter_grid_concentrations()
Definition: grids.cpp:1728
long * _sorted_y_lines
Definition: grids.h:263
void hybrid_connections()
Definition: grids.cpp:1717
void apply_node_flux3D(double dt, double *states)
Definition: grids.cpp:1638
struct ICSAdiDirection * ics_adi_dir_y
Definition: grids.h:283
void do_multicompartment_reactions(double *)
void divide_y_work(const int nthreads)
Definition: grids.cpp:1399
long _y_lines_length
Definition: grids.h:268
struct ICSAdiGridData * ics_tasks
Definition: grids.h:281
struct ICSAdiDirection * ics_adi_dir_z
Definition: grids.h:284
int add_multicompartment_reaction(int, int *, int)
void variable_step_ode_solve(double *RHS, double dt)
Definition: grids.cpp:1711
void variable_step_diffusion(const double *states, double *ydot)
Definition: grids.cpp:1692
int dg_adi()
Definition: grids.cpp:1679
long _z_lines_length
Definition: grids.h:269
void divide_x_work(const int nthreads)
Definition: grids.cpp:1302
long * _sorted_x_lines
Definition: grids.h:262
void initialize_multicompartment_reaction()
long _num_nodes
Definition: grids.h:275
void set_diffusion(double *, int)
Definition: grids.cpp:556
void do_grid_currents(double *, double, int)
Definition: grids.cpp:1647
double * _ics_alphas
Definition: grids.h:255
long * _nodes_per_thread
Definition: grids.h:278
void set_num_threads(const int n)
Definition: grids.cpp:1595
long * _sorted_z_lines
Definition: grids.h:264
long * _neighbors
Definition: grids.h:258
long _line_length_max
Definition: grids.h:272
void divide_z_work(const int nthreads)
Definition: grids.cpp:1496
void clear_multicompartment_reaction()
void variable_step_hybrid_connections(const double *cvode_states_3d, double *const ydot_3d, const double *cvode_states_1d, double *const ydot_1d)
Definition: grids.cpp:1721
void volume_setup()
Definition: grids.cpp:1667
double * set_rxd_currents(int, int *, PyHocObject **)
int set_diffusion(int, int, double *, int)
Definition: grids.cpp:453
void make_dt_ptr(PyHocObject *my_dt_ptr)
double * dt_ptr
Definition: grids.cpp:15
int ICS_insert_inhom(int grid_list_index, PyHocObject *my_states, long num_nodes, long *neighbors, long *x_line_defs, long x_lines_length, long *y_line_defs, long y_lines_length, long *z_line_defs, long z_lines_length, double *dcs, double dx, bool is_diffusable, double atolscale, double *ics_alphas)
Definition: grids.cpp:419
int ICS_insert(int grid_list_index, PyHocObject *my_states, long num_nodes, long *neighbors, long *x_line_defs, long x_lines_length, long *y_line_defs, long y_lines_length, long *z_line_defs, long z_lines_length, double *dcs, double dx, bool is_diffusable, double atolscale, double *ics_alphas)
Definition: grids.cpp:385
void(double **, double **, double **, double *, double *, double *, double *, double **, double) ReactionRate
Definition: grids.h:57
double * t_ptr
Definition: grids.cpp:16
void empty_list(int list_index)
Definition: grids.cpp:801
Grid_node * ICS_make_Grid(PyHocObject *my_states, long num_nodes, long *neighbors, long *x_line_defs, long x_lines_length, long *y_line_defs, long y_lines_length, long *z_line_defs, long z_lines_length, double *dcs, double dx, bool is_diffusable, double atolscale, double *ics_alphas)
void(double *, double *, double *, double *) ECSReactionRate
Definition: grids.h:58
void apply_node_flux(int, long *, double *, PyObject **, double, double *)
Definition: rxd.cpp:314
int ECS_insert(int grid_list_index, PyHocObject *my_states, int my_num_states_x, int my_num_states_y, int my_num_states_z, double my_dc_x, double my_dc_y, double my_dc_z, double my_dx, double my_dy, double my_dz, PyHocObject *my_alpha, PyHocObject *my_permeability, int, double, double)
Definition: grids.cpp:198
Grid_node * Parallel_grids[100]
Definition: grids.cpp:17
int remove(Grid_node **head, Grid_node *find)
Definition: grids.cpp:769
#define RHS(i)
Definition: multisplit.cpp:57
int const size_t const size_t n
Definition: nrngsl.h:10
_object PyObject
Definition: nrnpy.h:12
int find(const int, const int, const int, const int, const int)
long copyTo
Definition: grids.h:73
double * copyFrom
Definition: grids.h:72
double value
Definition: grids.h:79
unsigned char type
Definition: grids.h:78
neuron::container::data_handle< double > destination
Definition: grids.h:45
long destination
Definition: grids.h:51
neuron::container::data_handle< double > source
Definition: grids.h:52
double scale_factor
Definition: grids.h:53
double * states_in
Definition: grids.h:236
int line_size
Definition: grids.h:238
double * states_out
Definition: grids.h:237
void(* ecs_dg_adi_dir)(ECS_Grid_node *, const double, const int, const int, double const *const, double *const, double *const)
Definition: grids.h:229
ECS_Grid_node * g
Definition: grids.h:244
ECSAdiDirection * ecs_adi_dir
Definition: grids.h:246
double * state
Definition: grids.h:243
double * scratchpad
Definition: grids.h:247
long * num_3d_indices_per_1d_seg
Definition: grids.h:37
long * indices3d
Definition: grids.h:38
double * volumes1d
Definition: grids.h:40
double * volumes3d
Definition: grids.h:41
double * rates
Definition: grids.h:39
long num_1d_indices
Definition: grids.h:35
long * indices1d
Definition: grids.h:36
double * states_in
Definition: grids.h:338
double * dcgrid
Definition: grids.h:346
long * ordered_start_stop_indices
Definition: grids.h:343
double dc
Definition: grids.h:345
double d
Definition: grids.h:347
long * ordered_nodes
Definition: grids.h:342
void(* ics_dg_adi_dir)(ICS_Grid_node *g, int, int, int, double, double *, double *, double *, double *, double *, double *)
Definition: grids.h:327
long * line_start_stop_indices
Definition: grids.h:344
double * states_out
Definition: grids.h:339
long * ordered_line_defs
Definition: grids.h:341
double * deltas
Definition: grids.h:340
double * state
Definition: grids.h:356
double * RHS
Definition: grids.h:360
double * l_diag
Definition: grids.h:361
ICS_Grid_node * g
Definition: grids.h:357
int line_stop
Definition: grids.h:353
double * diag
Definition: grids.h:362
ICSAdiDirection * ics_adi_dir
Definition: grids.h:358
double * u_diag
Definition: grids.h:363
double * scratchpad
Definition: grids.h:359
int ordered_start
Definition: grids.h:355
int line_start
Definition: grids.h:353
double ** species_states
Definition: grids.h:64
unsigned int region_size
Definition: grids.h:66
uint64_t * mc3d_indices_offsets
Definition: grids.h:67
unsigned char * subregion
Definition: grids.h:65
double ** mc3d_mults
Definition: grids.h:68
Reaction * next
Definition: grids.h:60
unsigned int num_params_involved
Definition: grids.h:63
unsigned int num_species_involved
Definition: grids.h:62
ECSReactionRate * reaction
Definition: grids.h:61