54 std::vector<uint32_t>& nmodlrandom,
55 std::vector<int>& pointer2type);
60 double*& output_threshold,
62 int*& netcon_pntindex,
93 throw std::runtime_error(
"AoS memory layout not implemented.");
96 int n_vars = array_dims.size();
97 int row_width = std::accumulate(array_dims.begin(), array_dims.end(), 0);
100 std::vector<T> tmp(padded_cnt * row_width);
101 std::copy(
data,
data +
cnt * row_width, tmp.begin());
103 size_t offset_var = 0;
104 for (
size_t i_var = 0; i_var < n_vars; ++i_var) {
105 size_t K = array_dims[i_var];
107 for (
size_t i = 0;
i <
cnt; ++
i) {
108 for (
size_t k = 0;
k <
K; ++
k) {
109 size_t i_dst = padded_cnt * offset_var +
i *
K +
k;
110 size_t i_src =
i * row_width + offset_var +
k;
111 data[i_dst] = tmp[i_src];
119 template <
typename T>
121 std::vector<int> array_dims(sz, 1);
152 int n_data = 6 * n_data_padded;
154 n_data += n_data_padded;
174 size_t offset = 6 * n_data_padded;
176 offset += n_data_padded;
190 std::vector<int>
pdata;
198 auto& p2t =
tmls.back().pointer2type;
205 auto& nmodlrandom =
tmls.back().nmodlrandom;
233 int n_vec_play_continuous = F.
read_int();
235 for (
int i = 0;
i < n_vec_play_continuous; ++
i) {
257 for (
int i = 0;
i < n_vec_play_continuous; ++
i) {
260 vecPlay.discon_index = F.
read_int();
261 vecPlay.ubound_index = F.
read_int();
280 int* types_ =
nullptr;
281 int* nodecounts_ =
nullptr;
283 (*nrn2core_get_dat2_1_)(thread_id,
299 delete[] nodecounts_;
305 int n_data = 6 * n_data_padded;
307 n_data += n_data_padded;
319 double* actual_a =
_data + 2 * n_data_padded;
320 double* actual_b =
_data + 3 * n_data_padded;
321 double* actual_v =
_data + 4 * n_data_padded;
322 double* actual_area =
_data + 5 * n_data_padded;
323 double* actual_diam =
n_diam > 0 ?
_data + 6 * n_data_padded :
nullptr;
324 (*nrn2core_get_dat2_2_)(
325 thread_id,
v_parent_index, actual_a, actual_b, actual_area, actual_v, actual_diam);
332 size_t offset = 6 * n_data_padded;
334 offset += n_data_padded;
349 int* nodeindices_ =
nullptr;
350 double* data_ =
_data + offset;
351 int* pdata_ =
const_cast<int*
>(tml.pdata.data());
359 auto& nmodlrandom = tml.nmodlrandom;
361 (*nrn2core_get_dat2_mech_)(thread_id,
363 dparam_sizes[
type] > 0 ? dsz_inst : 0,
370 if (dparam_sizes[
type] > 0) {
375 std::copy(nodeindices_, nodeindices_ +
nodecounts[
i], tml.nodeindices.data());
379 assert(nodeindices_ ==
nullptr);
383 int* output_vindex_ =
nullptr;
384 double* output_threshold_ =
nullptr;
385 int* pnttype_ =
nullptr;
386 int* pntindex_ =
nullptr;
387 double* weight_ =
nullptr;
388 double* delay_ =
nullptr;
389 (*nrn2core_get_dat2_3_)(thread_id,
399 delete[] output_vindex_;
402 delete[] output_threshold_;
405 pnttype = std::vector<int>(pnttype_, pnttype_ + n_netcon);
408 pntindex = std::vector<int>(pntindex_, pntindex_ + n_netcon);
411 weights = std::vector<double>(weight_, weight_ + n_weight);
414 delay = std::vector<double>(delay_, delay_ + n_netcon);
425 int* iArray_ =
nullptr;
427 double* dArray_ =
nullptr;
428 (*nrn2core_get_dat2_corepointer_mech_)(nt.
id,
tmls[
i].type, icnt, dcnt, iArray_, dArray_);
429 tmls[
i].iArray.resize(icnt);
430 std::copy(iArray_, iArray_ + icnt,
tmls[
i].iArray.begin());
433 tmls[
i].dArray.resize(dcnt);
434 std::copy(dArray_, dArray_ + dcnt,
tmls[
i].dArray.begin());
440 std::vector<int> indices_vec_play_continuous;
441 (*nrn2core_get_dat2_vecplay_)(thread_id, indices_vec_play_continuous);
444 for (
auto i: indices_vec_play_continuous) {
448 double *yvec_, *tvec_;
450 (*nrn2core_get_dat2_vecplay_inst_)(thread_id,
463 std::copy(yvec_, yvec_ + sz, item.
yvec.data());
464 std::copy(tvec_, tvec_ + sz, item.
tvec.data());
471 int diff_mech_count = 0;
475 [&](
int e) { return e == mech_types[i]; })) {
477 printf(
"Error: %s is a different MOD file than used by NEURON!\n",
484 if (diff_mech_count > 0) {
487 "Error : NEURON and CoreNEURON must use same mod files for compatibility, %d "
488 "different mod file(s) found. Re-compile special and special-core!\n",
503 for (
int iml = 0; iml <
nodecount; ++iml) {
514 int type = net_buf_receive.second;
555 auto event = std::make_shared<NetConType_>();
562 auto event = std::make_shared<SelfEventType_>();
565 event->point_proc_instance = F.
read_int();
566 event->target_instance = F.
read_int();
574 auto event = std::make_shared<PreSynType_>();
581 auto event = std::make_shared<NetParEvent_>();
587 auto event = std::make_shared<PlayRecordEventType_>();
589 event->play_record_type = F.
read_int();
591 event->vecplay_index = F.
read_int();
608 std::vector<BAMech*> before_after_map(
memb_func.size());
611 before_after_map[
ii] =
nullptr;
616 if (!before_after_map[bam->type]) {
617 before_after_map[bam->type] = bam;
622 for (
auto tml = nt.
tml; tml; tml = tml->
next) {
623 if (before_after_map[tml->index]) {
624 int mtype = tml->index;
625 for (
auto bam = before_after_map[mtype]; bam && bam->type == mtype;
648 std::map<int, size_t> type2itml;
649 for (
size_t i = 0;
i <
tmls.size(); ++
i) {
650 if (
tmls[
i].pointer2type.size()) {
651 type2itml[
tmls[
i].type] =
i;
655 for (
auto tml = nt.
tml; tml; tml = tml->
next) {
656 int type = tml->index;
658 int*
pdata = tml->ml->pdata;
659 int cnt = tml->ml->nodecount;
672 for (
int i = 0;
i < szdp; ++
i) {
673 int s = semantics[
i];
713 for (
int iml = 0; iml <
cnt; ++iml) {
715 int legacy_index = *pd;
716 nrn_assert((legacy_index >= 0) && (legacy_index < ecnt * esz));
726 auto search = type2itml.find(
type);
727 if (search != type2itml.end()) {
728 auto& ptypes =
tmls[type2itml[
type]].pointer2type;
731 for (
int iml = 0; iml <
cnt; ++iml) {
732 for (
int i = 0;
i < szdp; ++
i) {
733 if (semantics[
i] == -5) {
736 int ptype = ptypes[iptype++];
746 const std::vector<int>& array_dims =
776 for (
auto tml = nt.
tml; tml; tml = tml->
next) {
778 tml->dependencies =
nullptr;
779 tml->ndependencies = 0;
787 std::vector<int> actual_mech_deps;
793 for (
int j = 0;
j < deps_cnt;
j++) {
805 std::vector<int> node_intersection;
813 std::back_inserter(node_intersection));
817 if (!node_intersection.empty()) {
818 actual_mech_deps.push_back(mech_deps[
j]);
823 if (!actual_mech_deps.empty()) {
824 tml->ndependencies = actual_mech_deps.size();
825 tml->dependencies = (
int*)
ecalloc(actual_mech_deps.size(),
sizeof(int));
826 std::copy(actual_mech_deps.begin(), actual_mech_deps.end(), tml->dependencies);
842 for (
int i = 0;
i < n_netcon; ++
i) {
858 ntc.delay =
new double[n_netcon];
859 memcpy(ntc.delay,
delay.data(), n_netcon *
sizeof(
double));
861 for (
int i = 0;
i < n_netcon; ++
i) {
873 ntc.bcpicnt =
new int[
n_mech];
874 ntc.bcpdcnt =
new int[
n_mech];
875 ntc.bcptype =
new int[
n_mech];
876 size_t point_proc_id = 0;
885 ntc.bcptype[point_proc_id] =
type;
886 ntc.bcpicnt[point_proc_id] =
tmls[
i].iArray.size();
887 ntc.bcpdcnt[point_proc_id] =
tmls[
i].dArray.size();
897 for (
int j = 0;
j < cntml; ++
j) {
902 double* d = ml->
data;
908 tmls[
i].iArray.data(),
920 assert(dk ==
static_cast<int>(
tmls[
i].dArray.size()));
921 assert(ik ==
static_cast<int>(
tmls[
i].iArray.size()));
943 ntc.vtype[
i] = vecPlay.vtype;
944 ntc.mtype[
i] = vecPlay.mtype;
945 ntc.vecplay_ix[
i] = vecPlay.ix;
982 ntc.mlmap =
new Memb_list_chkpnt*[
memb_func.size()];
984 ntc.mlmap[
i] =
nullptr;
1002 int shadow_rhs_cnt = 0;
1013 Memb_list_chkpnt* mlc =
new Memb_list_chkpnt;
1014 ntc.mlmap[tml->index] = mlc;
1018 tml_last->
next = tml;
1025 if (shadow_rhs_cnt) {
1059 size_t offset = 6 * n_data_padded;
1065 offset += n_data_padded;
1071 for (
auto tml = nt.
tml; tml; tml = tml->
next) {
1073 int type = tml->index;
1093 ntc.parent =
new int[nt.
end];
1095 ntc.area =
new double[nt.
end];
1100 std::vector<int> pnt_offset(
memb_func.size());
1106 for (
auto tml = nt.
tml; tml; tml = tml->
next, ++itml) {
1107 int type = tml->index;
1119 mech_data_layout_transform<double>(ml->
data,
n, array_dims, layout);
1124 mech_data_layout_transform<int>(ml->
pdata,
n, szdp, layout);
1127 Memb_list_chkpnt* mlc = ntc.mlmap[
type];
1130 for (
int i = 0;
i <
n; ++
i) {
1131 for (
int j = 0;
j < szdp; ++
j) {
1132 mlc->pdata_not_permuted[
i * szdp +
j] = ml->
pdata[
i * szdp +
j];
1137 for (
int i = 0;
i <
n; ++
i) {
1138 for (
int j = 0;
j < szdp; ++
j) {
1139 mlc->pdata_not_permuted[
i * szdp +
j] = ml->
pdata[
i +
j * align_cnt];
1145 ml->
pdata =
nullptr;
1151 pnt_offset[
type] = synoffset;
1153 for (
int i = 0;
i <
cnt; ++
i) {
1162 auto& r =
tmls[itml].nmodlrandom;
1165 uint32_t n_randomvar = r[ix++];
1166 assert(r.size() == 1 + n_randomvar + 5 * n_randomvar *
n);
1167 std::vector<uint32_t> indices(n_randomvar);
1168 for (uint32_t
i = 0;
i < n_randomvar; ++
i) {
1169 indices[
i] = r[ix++];
1172 for (
auto index: indices) {
1176 for (
int i = 0;
i <
n; ++
i) {
1223 for (
int i = 0;
i < nt.
end; ++
i) {
1231 for (
auto tml = nt.
tml; tml; tml = tml->
next) {
1232 if (tml->ml->nodeindices) {
1236 for (
auto tml = nt.
tml; tml; tml = tml->
next) {
1237 if (tml->ml->nodeindices) {
1260 for (
auto tml = nt.
tml; tml; tml = tml->
next) {
1268 for (
auto tml = nt.
tml; tml; tml = tml->
next) {
1292 ntc.output_vindex =
new int[nt.
n_presyn];
1313 int index = ix / 1000;
1314 int type = ix % 1000;
1318 int ip2ps = pnttype2presyn[pnt->
_type];
1345 ntc.pnttype =
new int[nnetcon];
1346 ntc.pntindex =
new int[nnetcon];
1347 memcpy(ntc.pnttype,
pnttype.data(), nnetcon *
sizeof(
int));
1348 memcpy(ntc.pntindex,
pntindex.data(), nnetcon *
sizeof(
int));
1350 for (
int i = 0;
i < nnetcon; ++
i) {
void restore_tqueue(NrnThread &, const Phase2 &p2)
auto & get_pnt_receive_size()
auto & get_prop_dparam_size()
auto & get_net_buf_receive()
auto & get_net_buf_send_type()
auto & get_mech_data_layout()
auto & get_different_mechanism_type()
auto & get_has_net_event()
auto & get_is_artificial()
auto & get_pnttype2presyn()
auto & get_prop_param_size()
T * read_array(T *p, size_t count)
Read an integer array of fixed length.
std::vector< T > read_vector(size_t count)
void record_checkpoint()
Record current chkpnt state.
bool eof()
nothing more to read
int read_int()
Parse a single integer entry.
union coreneuron::NetCon::@0 u
void set_net_send_buffer(Memb_list **ml_list, const std::vector< int > &pnt_offset)
std::vector< int > pntindex
std::vector< int > mech_types
std::vector< int > nodecounts
std::vector< double > weights
void pdata_relocation(const NrnThread &nt, const std::vector< Memb_func > &memb_func)
void set_vec_play(NrnThread &nt, NrnThreadChkpnt &ntc)
void handle_weights(NrnThread &nt, int n_netcon, NrnThreadChkpnt &ntc)
void get_info_from_bbcore(NrnThread &nt, const std::vector< Memb_func > &memb_func, NrnThreadChkpnt &ntc)
void check_mechanism()
Check if MOD file used between NEURON and CoreNEURON is same.
void transform_int_data(int elem0, int nodecount, int *pdata, int i, int dparam_size, int layout, int n_node_)
Perform in memory transformation between AoS<>SoA for integer data.
void restore_events(FileHandler &F)
std::vector< double > output_threshold
std::vector< int > preSynConditionEventFlags
std::vector< int > pnttype
std::vector< VecPlayContinuous_ > vec_play_continuous
void read_direct(int thread_id, const NrnThread &nt)
std::vector< int > output_vindex
void read_file(FileHandler &F, const NrnThread &nt)
void set_dependencies(const NrnThread &nt, const std::vector< Memb_func > &memb_func)
std::vector< double > delay
std::vector< std::pair< int, std::shared_ptr< EventTypeBase > > > events
void populate(NrnThread &nt, const UserParams &userParams)
void fill_before_after_lists(NrnThread &nt, const std::vector< Memb_func > &memb_func)
#define VecPlayContinuousType
#define PlayRecordEventType
void nrnran123_setseq(nrnran123_State *s, std::uint32_t seq, char which)
Set a Random123 sequence for a sequnece ID and which selector.
bool nrn_semantics_is_ion(int i)
int nrn_semantics_ion_type(int i)
#define BEFORE_AFTER_SIZE
void move(Item *q1, Item *q2, Item *q3)
THIS FILE IS AUTO GENERATED DONT MODIFY IT.
void setup_fornetcon_info(NrnThread &nt)
If FOR_NETCON in use, setup NrnThread fornetcon related info.
int soaos2cnrn_index(const std::array< int, 3 > &soaos_indices, const std::vector< int > &array_dims, int padded_node_count, int *permute)
Compute the CoreNEURON index given an SoAoS index.
int nrn_i_layout(int icnt, int cnt, int isz, int sz, int layout)
This function return the index in a flat array of a matrix coordinate (icnt, isz).
fixed_vector< double > IvocVect
nrnran123_State * nrnran123_newstream3(uint32_t id1, uint32_t id2, uint32_t id3, bool use_unified_memory)
Allocate a new Random123 stream.
void nrn_abort(int errcode)
void * ecalloc_align(size_t n, size_t size, size_t alignment)
int nrn_extra_thread0_vdata
int interleave_permute_type
const char * nrn_get_mechname(int type)
void mech_data_layout_transform(T *data, int cnt, const std::vector< int > &array_dims, int layout)
int nrn_mech_depend(int type, int *dependencies)
std::array< int, 3 > legacy2soaos_index(int legacy_index, const std::vector< int > &array_dims)
Split a legacy index into the three SoAoS indices.
void * ecalloc(size_t n, size_t size)
static void * emalloc(size_t size)
NrnThreadChkpnt * nrnthread_chkpnt
size_t nrn_soa_byte_align(size_t size)
return the new offset considering the byte aligment settings
int nrn_soa_padded_size(int cnt, int layout)
calculate size after padding for specific memory layout
NrnThreadMembList * create_tml(NrnThread &nt, int mech_id, Memb_func &memb_func, int &shadow_rhs_cnt, const std::vector< int > &mech_types, const std::vector< int > &nodecounts)
void permute_nodeindices(Memb_list *ml, int *permute)
void permute_ml(Memb_list *ml, int type, NrnThread &nt)
void permute_data(double *vec, int n, int *p)
std::vector< int > interleave_order(int ith, int ncell, int nnode, int *parent)
Function that performs the permutation of the cells such that the execution threads access coalesced ...
void permute_ptr(int *vec, int n, int *p)
#define nrn_assert(x)
assert()-like macro, independent of NDEBUG status
int * nrn_prop_dparam_size_
int const size_t const size_t n
int * nrn_prop_param_size_
std::vector< Memb_func > memb_func
int(* nrn2core_get_dat2_mech_)(int tid, size_t i, int dsz_inst, int *&nodeindices, double *&data, int *&pdata, std::vector< uint32_t > &nmodlrandom, std::vector< int > &pointer2type)
int(* nrn2core_get_dat2_3_)(int tid, int nweight, int *&output_vindex, double *&output_threshold, int *&netcon_pnttype, int *&netcon_pntindex, double *&weights, double *&delays)
int(* nrn2core_get_dat2_corepointer_mech_)(int tid, int type, int &icnt, int &dcnt, int *&iarray, double *&darray)
int(* nrn2core_get_dat2_vecplay_inst_)(int tid, int i, int &vptype, int &mtype, int &ix, int &sz, double *&yvec, double *&tvec, int &last_index, int &discon_index, int &ubound_index)
int(* nrn2core_get_dat2_corepointer_)(int tid, int &n)
int(* nrn2core_get_dat2_2_)(int tid, int *&v_parent_index, double *&a, double *&b, double *&area, double *&v, double *&diamvec)
int(* nrn2core_get_dat2_1_)(int tid, int &n_real_cell, int &ngid, int &n_real_gid, int &nnode, int &ndiam, int &nmech, int *&tml_index, int *&ml_nodecount, int &nidata, int &nvdata, int &nweight)
int(* nrn2core_get_dat2_vecplay_)(int tid, std::vector< int > &indices)
NetSendBuffer_t * _net_send_buffer
NetReceiveBuffer_t * _net_receive_buffer
int _net_send_buffer_size
NrnThreadBAList * tbl[BEFORE_AFTER_SIZE]
std::vector< int > _pnt_offset
This structure is data needed is several part of nrn_setup, phase1 and phase2.
const int *const gidgroups
Array of cell group numbers (indices)
CheckPoints & checkPoints