Nov 9, 2015
Updated the code with correct license.
|
|
|
1 |
/* |
|
2 |
* Copyright (c) 2015 University of Lübeck |
|
3 |
* |
|
4 |
* Permission is hereby granted, free of charge, to any person obtaining a copy |
|
5 |
* of this software and associated documentation files (the "Software"), to deal |
|
6 |
* in the Software without restriction, including without limitation the rights |
|
7 |
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell |
|
8 |
* copies of the Software, and to permit persons to whom the Software is |
|
9 |
* furnished to do so, subject to the following conditions: |
|
10 |
* |
|
11 |
* The above copyright notice and this permission notice shall be included in |
|
12 |
* all copies or substantial portions of the Software. |
|
13 |
* |
|
14 |
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
|
15 |
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
|
16 |
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE |
|
17 |
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |
|
18 |
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, |
|
19 |
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN |
|
20 |
* THE SOFTWARE. |
|
21 |
* |
|
22 |
* AUTHORS: Michael Schellenberger Costa: mschellenbergercosta@gmail.com |
|
23 |
* |
|
24 |
* Based on: A thalamocortical neural mass model of the EEG during NREM sleep and its response |
|
25 |
* to auditory stimulation. |
|
26 |
* M Schellenberger Costa, A Weigenand, H-VV Ngo, L Marshall, J Born, T Martinetz, |
|
27 |
* JC Claussen. |
Sep 13, 2016
Major cleanup and moderinization
|
|
|
51 |
/******************************************************************************/ |
|
52 |
/* Fixed simulation settings */ |
|
53 |
/******************************************************************************/ |
|
54 |
extern const int onset = 20; /* Time until data is stored in s */ |
|
55 |
extern const int res = 1E4; /* Number of iteration steps per s */ |
|
56 |
extern const int red = 1E2; /* Number of iterations steps not saved */ |
|
57 |
extern const double dt = 1E3/res; /* Duration of a time step in ms */ |
|
58 |
extern const double h = sqrt(dt); /* Square root of dt for SRK iteration */ |
|
59 |
|
|
60 |
/******************************************************************************/ |
|
61 |
/* Simulation routine */ |
|
62 |
/* lhs defines outputs */ |
|
63 |
/* rhs defines inputs */ |
|
64 |
/******************************************************************************/ |
Sep 13, 2016
Major cleanup and moderinization
|
|
|
66 |
/* Initialize the seeder */ |
|
67 |
srand(time(NULL)); |
|
68 |
|
|
69 |
/* Fetch inputs */ |
|
70 |
const int T = (int) (mxGetScalar(prhs[0])); /* Duration of simulation in s */ |
|
71 |
const int Time = (T+onset)*res; /* Total number of iteration steps */ |
|
72 |
double* Param_Cortex = mxGetPr (prhs[1]); /* Parameters of cortical module */ |
|
73 |
double* Param_Thalamus = mxGetPr (prhs[2]); /* Parameters of thalamic module */ |
|
74 |
double* Connections = mxGetPr (prhs[3]); /* Connectivity values C <-> T */ |
|
75 |
double* var_stim = mxGetPr (prhs[4]); /* Parameters of stimulation protocol */ |
|
76 |
|
|
77 |
/* Initialize the populations */ |
|
78 |
Cortical_Column Cortex = Cortical_Column(Param_Cortex, Connections); |
|
79 |
Thalamic_Column Thalamus = Thalamic_Column(Param_Thalamus, Connections); |
|
80 |
|
|
81 |
/* Link both modules */ |
|
82 |
Cortex.get_Thalamus(Thalamus); |
|
83 |
Thalamus.get_Cortex(Cortex); |
|
84 |
|
|
85 |
/* Initialize the stimulation protocol */ |
|
86 |
Stim Stimulation(Cortex, Thalamus, var_stim); |
Sep 13, 2016
Major cleanup and moderinization
|
|
|
88 |
/* Create data containers */ |
|
89 |
std::vector<mxArray*> dataArray; |
|
90 |
dataArray.reserve(4); |
|
91 |
dataArray.push_back(GetMexArray(1, T*res/red)); // Vt |
|
92 |
dataArray.push_back(GetMexArray(1, T*res/red)); // Vr |
|
93 |
dataArray.push_back(GetMexArray(1, T*res/red)); // Ca |
|
94 |
dataArray.push_back(GetMexArray(1, T*res/red)); // act_h |
Sep 13, 2016
Major cleanup and moderinization
|
|
|
96 |
/* Pointer to the data blocks */ |
|
97 |
std::vector<double*> dataPointer; |
|
98 |
dataPointer.reserve(dataArray.size()); |
|
99 |
for (auto &dataptr : dataArray) { |
|
100 |
dataPointer.push_back(mxGetPr(dataptr)); |
|
101 |
} |
|
102 |
|
|
103 |
/* Simulation */ |
|
104 |
int count = 0; |
|
105 |
for (unsigned t=0; t < Time; ++t) { |
|
106 |
ODE (Cortex, Thalamus); |
|
107 |
Stimulation.check_stim(t); |
|
108 |
if(t >= onset*res && t%red == 0){ |
|
109 |
get_data(count, Cortex, Thalamus, dataPointer); |
|
110 |
++count; |
|
111 |
} |
|
112 |
} |
|
113 |
|
|
114 |
/* Return the data containers */ |
|
115 |
nlhs = dataArray.size()+1; |
|
116 |
for (auto &dataptr : dataArray) { |
|
117 |
plhs[std::distance(&dataptr, dataArray.data())] = dataptr; |
|
118 |
} |
|
119 |
plhs[dataArray.size()] = get_marker(Stimulation); |
|
120 |
|
|
121 |
return; |
|
122 |
} |
|
123 |
|
|
124 |
/******************************************************************************/ |
|
125 |
/* Create MATLAB data containers */ |
|
126 |
/******************************************************************************/ |
Sep 13, 2016
Major cleanup and moderinization
|
|
|
128 |
mxArray* Array = mxCreateDoubleMatrix(0, 0, mxREAL); |
|
129 |
mxSetM(Array, N); |
|
130 |
mxSetN(Array, M); |
|
131 |
{mxSetData(Array, mxMalloc(sizeof(double)*M*N));} |
|
132 |
return Array; |
|
133 |
} |
|
134 |
|
|
135 |
mxArray* get_marker(Stim &stim) { |
|
136 |
extern const int red; |
|
137 |
mxArray* marker = mxCreateDoubleMatrix(0, 0, mxREAL); |
|
138 |
mxSetM(marker, 1); |
|
139 |
mxSetN(marker, stim.marker_stimulation.size()); |
|
140 |
mxSetData(marker, mxMalloc(sizeof(double)*stim.marker_stimulation.size())); |
|
141 |
double* Pr_Marker = mxGetPr(marker); |
|
142 |
unsigned counter = 0; |
|
143 |
/* Division by res transforms marker time from dt to sampling rate */ |
|
144 |
for(auto & elem : stim.marker_stimulation) { |
|
145 |
Pr_Marker[counter++] = elem/red; |
|
146 |
} |
|
147 |
return marker; |